diff --git a/src/qtgui/reslist.cpp b/src/qtgui/reslist.cpp index a59adec2..c3fc7ddb 100644 --- a/src/qtgui/reslist.cpp +++ b/src/qtgui/reslist.cpp @@ -562,12 +562,13 @@ void ResList::resPageUpOrBack() if (vpos == verticalScrollBar()->value()) resultPageBack(); #else - QWebFrame *frame = page()->mainFrame(); - int vpos = frame->scrollBarValue(Qt::Vertical); - if (vpos != frame->scrollBarMinimum(Qt::Vertical)) - frame->scroll(0, -int(0.9*geometry().height())); - else + if (scrollIsAtTop()) { resultPageBack(); + } else { + QWebFrame *frame = page()->mainFrame(); + frame->scroll(0, -int(0.9*geometry().height())); + } + setupArrows(); #endif } @@ -581,21 +582,70 @@ void ResList::resPageDownOrNext() if (vpos == verticalScrollBar()->value()) resultPageNext(); #else - QWebFrame *frame = page()->mainFrame(); - int vpos = frame->scrollBarValue(Qt::Vertical); - if (vpos != frame->scrollBarMaximum(Qt::Vertical)) - frame->scroll(0, int(0.9*geometry().height())); - else + if (scrollIsAtBottom()) { resultPageNext(); + } else { + QWebFrame *frame = page()->mainFrame(); + frame->scroll(0, int(0.9*geometry().height())); + } + setupArrows(); #endif } +void ResList::setupArrows() +{ + emit prevPageAvailable(m_pager->hasPrev() || !scrollIsAtTop()); + emit nextPageAvailable(m_pager->hasNext() || !scrollIsAtBottom()); +} + +bool ResList::scrollIsAtBottom() +{ +#ifdef RESLIST_TEXTBROWSER + return false; +#else + QWebFrame *frame = page()->mainFrame(); + bool ret; + if (!frame || frame->scrollBarGeometry(Qt::Vertical).isEmpty()) { + ret = true; + } else { + int max = frame->scrollBarMaximum(Qt::Vertical); + int cur = frame->scrollBarValue(Qt::Vertical); + ret = (max != 0) && (cur == max); + LOGDEB2(("Scrollatbottom: cur %d max %d\n", cur, max)); + } + LOGDEB2(("scrollIsAtBottom: returning %d\n", ret)); + return ret; +#endif +} + +bool ResList::scrollIsAtTop() +{ +#ifdef RESLIST_TEXTBROWSER + return false; +#else + QWebFrame *frame = page()->mainFrame(); + bool ret; + if (!frame || frame->scrollBarGeometry(Qt::Vertical).isEmpty()) { + ret = true; + } else { + int cur = frame->scrollBarValue(Qt::Vertical); + int min = frame->scrollBarMinimum(Qt::Vertical); + LOGDEB(("Scrollattop: cur %d min %d\n", cur, min)); + ret = (cur == min); + } +#endif + LOGDEB2(("scrollIsAtTop: returning %d\n", ret)); + return ret; +} + // Show previous page of results. We just set the current number back // 2 pages and show next page. void ResList::resultPageBack() { - m_pager->resultPageBack(); - displayPage(); + if (m_pager->hasPrev()) { + m_pager->resultPageBack(); + displayPage(); + } } // Go to the first page @@ -607,6 +657,21 @@ void ResList::resultPageFirst() displayPage(); } +// Fill up result list window with next screen of hits +void ResList::resultPageNext() +{ + if (m_pager->hasNext()) { + m_pager->resultPageNext(); + displayPage(); + } +} + +void ResList::resultPageFor(int docnum) +{ + m_pager->resultPageFor(docnum); + displayPage(); +} + void ResList::append(const QString &text) { LOGDEB2(("QtGuiReslistPager::appendQString : %s\n", @@ -618,19 +683,6 @@ void ResList::append(const QString &text) #endif } -// Fill up result list window with next screen of hits -void ResList::resultPageNext() -{ - m_pager->resultPageNext(); - displayPage(); -} - -void ResList::resultPageFor(int docnum) -{ - m_pager->resultPageFor(docnum); - displayPage(); -} - void ResList::displayPage() { resetView(); @@ -641,10 +693,10 @@ void ResList::displayPage() setHtml(m_text); #endif - LOGDEB0(("ResList::resultPageNext: hasNext %d hasPrev %d\n", - m_pager->hasPrev(), m_pager->hasNext())); - emit prevPageAvailable(m_pager->hasPrev()); - emit nextPageAvailable(m_pager->hasNext()); + LOGDEB0(("ResList::displayPg: hasNext %d atBot %d hasPrev %d at Top %d \n", + m_pager->hasPrev(), scrollIsAtBottom(), + m_pager->hasNext(), scrollIsAtTop())); + setupArrows(); // Possibly color paragraph of current preview if any previewExposed(m_curPvDoc); diff --git a/src/qtgui/reslist.h b/src/qtgui/reslist.h index cb22e681..45eb55d0 100644 --- a/src/qtgui/reslist.h +++ b/src/qtgui/reslist.h @@ -134,6 +134,9 @@ class ResList : public RESLIST_PARENTCLASS virtual void displayPage(); // Display current page static int newListId(); void resetView(); + bool scrollIsAtTop(); + bool scrollIsAtBottom(); + void setupArrows(); }; diff --git a/src/query/reslistpager.cpp b/src/query/reslistpager.cpp index 01c04c5e..59a6a09e 100644 --- a/src/query/reslistpager.cpp +++ b/src/query/reslistpager.cpp @@ -49,8 +49,9 @@ static PlainToRichHtReslist g_hiliter; ResListPager::ResListPager(int pagesize) : m_pagesize(pagesize), m_newpagesize(pagesize), + m_resultsInCurrentPage(0), m_winfirst(-1), - m_hasNext(false), + m_hasNext(true), m_hiliter(&g_hiliter) { } @@ -71,12 +72,19 @@ void ResListPager::resultPageNext() } else { m_winfirst += m_respage.size(); } - // Get the next page of results. + // Get the next page of results. Note that we look ahead by one to + // determine if there is actually a next page vector npage; - int pagelen = m_docSource->getSeqSlice(m_winfirst, m_pagesize, npage); + int pagelen = m_docSource->getSeqSlice(m_winfirst, m_pagesize + 1, npage); // If page was truncated, there is no next - m_hasNext = (pagelen == m_pagesize); + m_hasNext = (pagelen == m_pagesize + 1); + + // Get rid of the possible excess result + if (pagelen == m_pagesize + 1) { + npage.resize(m_pagesize); + pagelen--; + } if (pagelen <= 0) { // No results ? This can only happen on the first page or if the @@ -94,6 +102,7 @@ void ResListPager::resultPageNext() } return; } + m_resultsInCurrentPage = pagelen; m_respage = npage; } diff --git a/src/query/reslistpager.h b/src/query/reslistpager.h index d13b1d34..e795dfc4 100644 --- a/src/query/reslistpager.h +++ b/src/query/reslistpager.h @@ -44,7 +44,7 @@ public: { m_pagesize = m_newpagesize; m_winfirst = winfirst; - m_hasNext = false; + m_hasNext = true; m_docSource = src; m_respage.clear(); } @@ -78,7 +78,7 @@ public: } void resultPageBack() { if (m_winfirst <= 0) return; - m_winfirst -= 2 * m_pagesize; + m_winfirst -= m_resultsInCurrentPage + m_pagesize; resultPageNext(); } void resultPageNext(); @@ -120,6 +120,7 @@ public: private: int m_pagesize; int m_newpagesize; + int m_resultsInCurrentPage; // First docnum (from docseq) in current page int m_winfirst; bool m_hasNext;