void SearchDocumentJob::run() { Q_ASSERT(m_document); for (int i = 0; i < m_document->numPages(); ++i) { int ipage = (startPage + i) % m_document->numPages(); Poppler::Page *page = m_document->page(ipage); double sLeft, sTop, sRight, sBottom; float scaleW = 1.f / page->pageSizeF().width(); float scaleH = 1.f / page->pageSizeF().height(); bool found; found = page->search(m_search, sLeft, sTop, sRight, sBottom, Poppler::Page::FromTop, Poppler::Page::IgnoreCase); while (found) { QRectF result; result.setLeft(sLeft * scaleW); result.setTop(sTop * scaleH); result.setRight(sRight * scaleW); result.setBottom(sBottom * scaleH); m_matches.append(QPair<int, QRectF>(ipage, result)); found = page->search(m_search, sLeft, sTop, sRight, sBottom, Poppler::Page::NextResult, Poppler::Page::IgnoreCase); } delete page; } }
void SearchWorker::run() { while (1) { bar->search_mutex.lock(); stop = false; if (die) { break; } // always clear results -> empty search == stop search emit clear_hits(); // get search string bar->term_mutex.lock(); if (bar->term.isEmpty()) { bar->term_mutex.unlock(); emit update_label_text("done."); continue; } int start = bar->start_page; QString search_term = bar->term; forward = bar->forward; bar->term_mutex.unlock(); // check if term contains upper case letters; if so, do case sensitive search (smartcase) bool has_upper_case = false; for (QString::const_iterator it = search_term.begin(); it != search_term.end(); ++it) { if (it->isUpper()) { has_upper_case = true; break; } } #ifdef DEBUG cerr << "'" << search_term.toUtf8().constData() << "'" << endl; #endif emit update_label_text(QString("[%1] 0\% searched, 0 hits") .arg(has_upper_case ? "Case" : "no case")); // search all pages int hit_count = 0; int page = start; do { Poppler::Page *p = bar->doc->page(page); if (p == NULL) { cerr << "failed to load page " << page << endl; continue; } // collect all occurrences QList<QRectF> *hits = new QList<QRectF>; #if POPPLER_VERSION < POPPLER_VERSION_CHECK(0, 22, 0) // old search interface, slow for many hits per page double x = 0, y = 0, x2 = 0, y2 = 0; while (!stop && !die && p->search(search_term, x, y, x2, y2, Poppler::Page::NextResult, has_upper_case ? Poppler::Page::CaseSensitive : Poppler::Page::CaseInsensitive)) { hits->push_back(QRectF(x, y, x2 - x, y2 - y)); } #elif POPPLER_VERSION < POPPLER_VERSION_CHECK(0, 31, 0) // new search interface QList<QRectF> tmp = p->search(search_term, has_upper_case ? Poppler::Page::CaseSensitive : Poppler::Page::CaseInsensitive); hits->swap(tmp); #else // even newer interface QList<QRectF> tmp = p->search(search_term, has_upper_case ? (Poppler::Page::SearchFlags) 0 : Poppler::Page::IgnoreCase); // TODO support Poppler::Page::WholeWords hits->swap(tmp); #endif #ifdef DEBUG if (hits->size() > 0) { cerr << hits->size() << " hits on page " << page << endl; } #endif delete p; // clean up when interrupted if (stop || die) { delete hits; break; } if (hits->size() > 0) { hit_count += hits->size(); emit search_done(page, hits); } else { delete hits; } // update progress label next to the search bar int percent; if (forward) { percent = page + bar->doc->numPages() - start; } else { percent = start + bar->doc->numPages() - page; } percent = (percent % bar->doc->numPages()) * 100 / bar->doc->numPages(); QString progress = QString("[%1] %2\% searched, %3 hits") .arg(has_upper_case ? "Case" : "no case") .arg(percent) .arg(hit_count); emit update_label_text(progress); if (forward) { if (++page == bar->doc->numPages()) { page = 0; } } else { if (--page == -1) { page = bar->doc->numPages() - 1; } } } while (page != start); #ifdef DEBUG cerr << "done!" << endl; #endif emit update_label_text(QString("[%1] done, %2 hits") .arg(has_upper_case ? "Case" : "no case") .arg(hit_count)); } }