From 75418056d8017c75af11d0a332c43befcbbbef65 Mon Sep 17 00:00:00 2001 From: ZackaryWelch Date: Fri, 16 Feb 2018 17:17:56 -0500 Subject: Added highlighting for search results --- src-qt5/desktop-utils/lumina-pdf/PrintWidget.cpp | 18 +++-- src-qt5/desktop-utils/lumina-pdf/PrintWidget.h | 3 +- src-qt5/desktop-utils/lumina-pdf/lumina-pdf.pro | 3 +- src-qt5/desktop-utils/lumina-pdf/mainUI.cpp | 85 ++++++++++++++---------- src-qt5/desktop-utils/lumina-pdf/mainUI.h | 9 +-- src-qt5/desktop-utils/lumina-pdf/mainUI.ui | 2 +- src-qt5/desktop-utils/lumina-pdf/textData.h | 31 +++++++++ 7 files changed, 100 insertions(+), 51 deletions(-) create mode 100644 src-qt5/desktop-utils/lumina-pdf/textData.h (limited to 'src-qt5/desktop-utils') diff --git a/src-qt5/desktop-utils/lumina-pdf/PrintWidget.cpp b/src-qt5/desktop-utils/lumina-pdf/PrintWidget.cpp index 5fa8e517..790ae2ad 100644 --- a/src-qt5/desktop-utils/lumina-pdf/PrintWidget.cpp +++ b/src-qt5/desktop-utils/lumina-pdf/PrintWidget.cpp @@ -126,10 +126,18 @@ void PrintWidget::setCurrentPage(int pageNumber) { } } -void PrintWidget::highlightText(int pageNum, fz_rect &rect) { - //PageItem *item = static_cast(pages[pageNum]); - QPainter painter(this); - painter.fillRect(QRectF(QPointF(rect.x0, rect.y0), QPointF(rect.x1, rect.y1)), QColor(255, 255, 177, 128)); +void PrintWidget::highlightText(TextData *text) { + //Creates a rectangle around the text if the text has not already been highlighted + if(!text->highlighted()) { + //qDebug() << "Highlighting text: " << text->text() << "At page: " << text->page(); + fz_rect rect = text->loc(); + double pageHeight = pages.at(0)->boundingRect().height(); + QRectF textRect(QPointF(rect.x0, rect.y0+(pageHeight*(text->page()-1))), QPointF(rect.x1, rect.y1 + (pageHeight*(text->page()-1)))); + QBrush highlightFill(QColor(255, 255, 177, 50)); + QPen highlightOutline(QColor(255, 255, 100, 98)); + scene->addRect(textRect, highlightOutline, highlightFill); + text->highlighted(true); + } } //Private functions @@ -194,7 +202,7 @@ void PrintWidget::populateScene() QImage pagePicture = pictures->value(i); if(degrees != 0) { pagePicture = pagePicture.transformed(rotMatrix, Qt::SmoothTransformation); - qDebug() << "Rotating by: " << degrees << " degrees"; + //qDebug() << "Rotating by: " << degrees << " degrees"; } if(pagePicture.isNull()) { qDebug() << "NULL IMAGE ON PAGE " << i; diff --git a/src-qt5/desktop-utils/lumina-pdf/PrintWidget.h b/src-qt5/desktop-utils/lumina-pdf/PrintWidget.h index ba432845..fa2869b6 100644 --- a/src-qt5/desktop-utils/lumina-pdf/PrintWidget.h +++ b/src-qt5/desktop-utils/lumina-pdf/PrintWidget.h @@ -20,6 +20,7 @@ #include #include +#include "textData.h" #include class PageItem : public QGraphicsItem { @@ -137,7 +138,7 @@ public slots: void zoomOut(double factor=1.2); void setCurrentPage(int); void setVisible(bool) Q_DECL_OVERRIDE; - void highlightText(int, fz_rect&); + void highlightText(TextData*); void receiveDocument(fz_document*); void setDegrees(int); diff --git a/src-qt5/desktop-utils/lumina-pdf/lumina-pdf.pro b/src-qt5/desktop-utils/lumina-pdf/lumina-pdf.pro index c0717d6d..bf0d3665 100644 --- a/src-qt5/desktop-utils/lumina-pdf/lumina-pdf.pro +++ b/src-qt5/desktop-utils/lumina-pdf/lumina-pdf.pro @@ -25,7 +25,8 @@ SOURCES += main.cpp \ HEADERS += mainUI.h \ PrintWidget.h \ PresentationLabel.h \ - PropDialog.h + PropDialog.h \ + textData.h FORMS += mainUI.ui \ propDialog.ui diff --git a/src-qt5/desktop-utils/lumina-pdf/mainUI.cpp b/src-qt5/desktop-utils/lumina-pdf/mainUI.cpp index b64b8902..92e5cb65 100644 --- a/src-qt5/desktop-utils/lumina-pdf/mainUI.cpp +++ b/src-qt5/desktop-utils/lumina-pdf/mainUI.cpp @@ -25,7 +25,7 @@ MainUI::MainUI() : QMainWindow(), ui(new Ui::MainUI()){ ui->setupUi(this); - this->setWindowTitle(tr("Lumina PDF Viewer")); + //this->setWindowTitle(tr("Lumina PDF Viewer")); this->setWindowIcon( LXDG::findIcon("application-pdf","unknown")); presentationLabel = 0; CurrentPage = 1; @@ -53,7 +53,7 @@ MainUI::MainUI() : QMainWindow(), ui(new Ui::MainUI()){ //Now put the widgets into the UI //ui->bookmarksFrame->setParent(WIDGET); //ui->findGroup->setParent(WIDGET); - qDebug() << "Setting central widget"; + //qDebug() << "Setting central widget"; this->centralWidget()->layout()->replaceWidget(ui->label_replaceme, WIDGET); //setCentralWidget(WIDGET); ui->label_replaceme->setVisible(false); WIDGET->setContextMenuPolicy(Qt::CustomContextMenu); @@ -196,6 +196,8 @@ MainUI::MainUI() : QMainWindow(), ui(new Ui::MainUI()){ ui->actionSettings->setIcon(LXDG::findIcon("document-properties","")); ui->findNextB->setIcon(LXDG::findIcon("go-down-search")); ui->findPrevB->setIcon(LXDG::findIcon("go-up-search")); + ui->actionClearHighlights->setIcon(LXDG::findIcon("format-text-clear","")); + ui->findNextB->setIcon(LXDG::findIcon("go-down-search")); ui->matchCase->setIcon(LXDG::findIcon("format-text-italic")); ui->closeFind->setIcon(LXDG::findIcon("dialog-close")); ui->closeBookmarks->setIcon(LXDG::findIcon("dialog-close")); @@ -210,9 +212,10 @@ MainUI::MainUI() : QMainWindow(), ui(new Ui::MainUI()){ ui->findGroup->setVisible(false); ui->bookmarksFrame->setVisible(false); - ui->menuSettings->setEnabled(TESTING); - ui->menuSettings->setVisible(TESTING); + ui->actionSettings->setEnabled(TESTING); + ui->actionSettings->setVisible(TESTING); ui->actionBookmarks->setEnabled(TESTING); + ui->actionBookmarks->setVisible(TESTING); ui->actionScroll_Mode->setEnabled(TESTING); ui->actionScroll_Mode->setVisible(TESTING); ui->actionSelect_Mode->setEnabled(TESTING); @@ -259,7 +262,6 @@ void MainUI::loadFile(QString path){ if(pdf_obj *obj = pdf_dict_gets(CTX, info, (char *)"Title")) this->setWindowTitle(pdf_to_utf8(CTX, obj)); } - qDebug() << this->windowTitle(); if(this->windowTitle().isEmpty()){ this->setWindowTitle(path.section("/",-1)); } //Setup the Document @@ -468,6 +470,7 @@ void MainUI::slotPageLoaded(int page){ ui->actionStart_Here->setEnabled(true); ui->actionStart_Begin->setEnabled(true); pageAct->setVisible(true); + qDebug() << " - Document Setup: All pages loaded"; }else{ progress->setValue(finished); } @@ -625,39 +628,50 @@ void MainUI::wheelEvent(QWheelEvent *event) { void MainUI::find(QString text, bool forward) { if(!text.isEmpty()) { - qDebug() << "Finding Text"; - bool newText = results.empty(); - bool research = false; - if(!newText) - research = !(results[0].text == text); - //Clear results if the user gives a new search string - if(research) - results.clear(); - - if(research or newText) { + static bool previousMatchCase = matchCase; + //qDebug() << "Finding Text"; + //Detemine if it is the first time searching or a new search string + bool newSearch = results.empty() || !(results[0]->text() == text); + + //Also search again if match case is turned on/off + if(previousMatchCase != matchCase) { + newSearch = true; + previousMatchCase = matchCase; + } + + //Clear results and highlights if the user gives a new search string + if(newSearch) { + if(!results.empty()) { + foreach (TextData* td, results) + delete td; + results.clear(); + } + QTimer::singleShot(10, WIDGET, SLOT(updatePreview())); ui->resultsLabel->setText(""); fz_rect rectBuffer[1000]; for(int i = 0; i < numPages; i++) { int count = fz_search_page_number(CTX, DOC, i, text.toLatin1().data(), rectBuffer, 1000); - qDebug() << count; + //qDebug() << "Page " << i+1 << ": Count, " << count; for(int j = 0; j < count; j++) { - textData t; - t.loc = rectBuffer[j]; - t.text = text; - t.page = i; - /*fz_stext_sheet *sheet = fz_new_stext_sheet(CTX); - fz_stext_page *sPage = fz_new_stext_page_from_page_number(CTX, DOC, results.first(), sheet, NULL); - if(QString(fz_copy_selection(CTX, sPage, rectBuffer[j])).contains( - text, (matchCase) ? Qt::CaseSensitive : Qt::CaseInsensitive)) {*/ - results.append(t); - //} - } + TextData *t = new TextData(rectBuffer[j], i+1, text); + + //MuPDF search does not match case, so retrieve the exact text at the location found and determine whether or not it matches the case of the search text if the user selected to match case + if(matchCase){ + fz_stext_sheet *sheet = fz_new_stext_sheet(CTX); + fz_stext_page *sPage = fz_new_stext_page_from_page_number(CTX, DOC, i, sheet, NULL); + QString currentStr = QString(fz_copy_selection(CTX, sPage, rectBuffer[j])); + if(currentStr.contains(text, Qt::CaseSensitive)) + results.append(t); + }else{ + results.append(t); + } + } } - qDebug() << results.size(); + //qDebug() << "Total Results: " << results.size(); currentHighlight = (forward) ? -1 : results.size(); } - qDebug() << "Jumping to next result"; + //qDebug() << "Jumping to next result"; if(!results.empty()) { //Jump to the location of the next or previous textbox and highlight if(forward) { @@ -674,16 +688,15 @@ void MainUI::find(QString text, bool forward) { ui->resultsLabel->setText(QString::number(currentHighlight+1) + " of " + QString::number(results.size()) + " results"); - textData currentText = results[currentHighlight]; - WIDGET->setCurrentPage(currentText.page); - - qDebug() << "Jump to location: " << currentText.page; + TextData *currentText = results[currentHighlight]; + WIDGET->setCurrentPage(currentText->page()); - WIDGET->highlightText(currentHighlight, currentText.loc); + //qDebug() << "Jump to page: " << currentText.page; - //QTimer::singleShot(10, WIDGET, SLOT(updatePreview())); + //Current Bug: Does not highlight results[0] + WIDGET->highlightText(currentText); }else{ - //Print "No results found" + ui->resultsLabel->setText("No results found"); } } } diff --git a/src-qt5/desktop-utils/lumina-pdf/mainUI.h b/src-qt5/desktop-utils/lumina-pdf/mainUI.h index ca602abb..bc121f7c 100644 --- a/src-qt5/desktop-utils/lumina-pdf/mainUI.h +++ b/src-qt5/desktop-utils/lumina-pdf/mainUI.h @@ -24,17 +24,12 @@ #include "PresentationLabel.h" #include "propDialog.h" #include "PrintWidget.h" +#include "textData.h" namespace Ui{ class MainUI; }; -typedef struct textData { - fz_rect loc; - int page; - QString text; -}textData; - class MainUI : public QMainWindow{ Q_OBJECT public: @@ -54,7 +49,7 @@ private: QPrintDialog *PrintDLG; QString lastdir; bool matchCase; - QList results; + QList results; int currentHighlight; //Other Interface elements diff --git a/src-qt5/desktop-utils/lumina-pdf/mainUI.ui b/src-qt5/desktop-utils/lumina-pdf/mainUI.ui index b8518cf5..0e9bfcc0 100644 --- a/src-qt5/desktop-utils/lumina-pdf/mainUI.ui +++ b/src-qt5/desktop-utils/lumina-pdf/mainUI.ui @@ -11,7 +11,7 @@ - MainWindow + diff --git a/src-qt5/desktop-utils/lumina-pdf/textData.h b/src-qt5/desktop-utils/lumina-pdf/textData.h new file mode 100644 index 00000000..aa134cbb --- /dev/null +++ b/src-qt5/desktop-utils/lumina-pdf/textData.h @@ -0,0 +1,31 @@ +#ifndef textData_H +#define textData_H + +#include + +class TextData { + private: + fz_rect _loc; + bool _highlighted=false; + int _page=0; + QString _text=""; + + public: + TextData(fz_rect _loc, int _page, QString _text) { + this->_loc = _loc; + this->_page = _page; + this->_text = _text; + } + + fz_rect loc() { return this->_loc; } + bool highlighted() { return this->_highlighted; } + int page() { return this->_page; } + QString text() { return this->_text; } + + void loc(fz_rect loc) { this->_loc = loc; } + void highlighted(bool highlighted) { this->_highlighted = highlighted; } + void page(int page) { this->_page = page; } + void text(QString text) { this->_text = text; } +}; + +#endif -- cgit