summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorShawn Rutledge <shawn.rutledge@theqtcompany.com>2014-12-15 15:23:45 +0100
committerShawn Rutledge <shawn.rutledge@theqtcompany.com>2014-12-15 16:40:08 +0100
commit19c5571e0434990cbc529d4bb948e3c2e88cca21 (patch)
tree012270890b6f53079b547d3d9ba2deaafc41bf2d
parentc1ecb9b0e46b5b86a329b6b03a26e13bf8f0c659 (diff)
initial single-threaded implementation of pdfviewer example
-rw-r--r--examples/widgets/pdfviewer/main.cpp15
-rw-r--r--examples/widgets/pdfviewer/mainwindow.cpp39
-rw-r--r--examples/widgets/pdfviewer/mainwindow.h34
-rw-r--r--examples/widgets/pdfviewer/mainwindow.ui67
-rw-r--r--examples/widgets/pdfviewer/pdfviewer.pro12
-rw-r--r--examples/widgets/pdfviewer/sequentialpagewidget.cpp63
-rw-r--r--examples/widgets/pdfviewer/sequentialpagewidget.h34
7 files changed, 264 insertions, 0 deletions
diff --git a/examples/widgets/pdfviewer/main.cpp b/examples/widgets/pdfviewer/main.cpp
new file mode 100644
index 0000000..51a3f98
--- /dev/null
+++ b/examples/widgets/pdfviewer/main.cpp
@@ -0,0 +1,15 @@
+#include "mainwindow.h"
+#include <QApplication>
+#include <QUrl>
+
+int main(int argc, char *argv[])
+{
+ QApplication a(argc, argv);
+ MainWindow w;
+ QStringList args = a.arguments();
+ w.show();
+ if (args.length() > 1)
+ w.open(QUrl::fromLocalFile(args[1]));
+
+ return a.exec();
+}
diff --git a/examples/widgets/pdfviewer/mainwindow.cpp b/examples/widgets/pdfviewer/mainwindow.cpp
new file mode 100644
index 0000000..1316ded
--- /dev/null
+++ b/examples/widgets/pdfviewer/mainwindow.cpp
@@ -0,0 +1,39 @@
+#include "mainwindow.h"
+#include "ui_mainwindow.h"
+
+#include <QFileDialog>
+#include <QMessageBox>
+#include <QPdfDocument>
+
+Q_LOGGING_CATEGORY(lcExample, "qt.examples.pdfviewer")
+
+MainWindow::MainWindow(QWidget *parent)
+ : QMainWindow(parent)
+ , ui(new Ui::MainWindow)
+ , m_doc(new QPdfDocument(this))
+{
+ ui->setupUi(this);
+ ui->pageWidget->setDocument(m_doc);
+}
+
+MainWindow::~MainWindow()
+{
+ delete ui;
+}
+
+void MainWindow::open(const QUrl &docLocation)
+{
+ if (docLocation.isLocalFile())
+ m_doc->load(docLocation.toLocalFile());
+ else {
+ qCDebug(lcExample) << docLocation << "is not a valid local file";
+ QMessageBox::critical(this, tr("Failed to open"), tr("%1 is not a valid local file").arg(docLocation.toString()));
+ }
+}
+
+void MainWindow::on_actionOpen_triggered()
+{
+ QUrl toOpen = QFileDialog::getOpenFileUrl(this);
+ if (toOpen.isValid())
+ open(toOpen);
+}
diff --git a/examples/widgets/pdfviewer/mainwindow.h b/examples/widgets/pdfviewer/mainwindow.h
new file mode 100644
index 0000000..e31f0b9
--- /dev/null
+++ b/examples/widgets/pdfviewer/mainwindow.h
@@ -0,0 +1,34 @@
+#ifndef MAINWINDOW_H
+#define MAINWINDOW_H
+
+#include <QMainWindow>
+#include <QLoggingCategory>
+
+Q_DECLARE_LOGGING_CATEGORY(lcExample)
+
+namespace Ui {
+class MainWindow;
+}
+
+class QPdfDocument;
+
+class MainWindow : public QMainWindow
+{
+ Q_OBJECT
+
+public:
+ explicit MainWindow(QWidget *parent = 0);
+ ~MainWindow();
+
+public slots:
+ void open(const QUrl &docLocation);
+
+private slots:
+ void on_actionOpen_triggered();
+
+private:
+ Ui::MainWindow *ui;
+ QPdfDocument *m_doc;
+};
+
+#endif // MAINWINDOW_H
diff --git a/examples/widgets/pdfviewer/mainwindow.ui b/examples/widgets/pdfviewer/mainwindow.ui
new file mode 100644
index 0000000..16994fa
--- /dev/null
+++ b/examples/widgets/pdfviewer/mainwindow.ui
@@ -0,0 +1,67 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ui version="4.0">
+ <class>MainWindow</class>
+ <widget class="QMainWindow" name="MainWindow">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>400</width>
+ <height>300</height>
+ </rect>
+ </property>
+ <property name="windowTitle">
+ <string>MainWindow</string>
+ </property>
+ <widget class="QWidget" name="centralWidget">
+ <layout class="QVBoxLayout" name="verticalLayout">
+ <item>
+ <widget class="SequentialPageWidget" name="pageWidget" native="true"/>
+ </item>
+ </layout>
+ </widget>
+ <widget class="QMenuBar" name="menuBar">
+ <property name="geometry">
+ <rect>
+ <x>0</x>
+ <y>0</y>
+ <width>400</width>
+ <height>19</height>
+ </rect>
+ </property>
+ <widget class="QMenu" name="menuFile">
+ <property name="title">
+ <string>File</string>
+ </property>
+ <addaction name="actionOpen"/>
+ </widget>
+ <addaction name="menuFile"/>
+ </widget>
+ <widget class="QToolBar" name="mainToolBar">
+ <attribute name="toolBarArea">
+ <enum>TopToolBarArea</enum>
+ </attribute>
+ <attribute name="toolBarBreak">
+ <bool>false</bool>
+ </attribute>
+ <addaction name="actionOpen"/>
+ </widget>
+ <widget class="QStatusBar" name="statusBar"/>
+ <action name="actionOpen">
+ <property name="text">
+ <string>Open...</string>
+ </property>
+ </action>
+ </widget>
+ <layoutdefault spacing="6" margin="11"/>
+ <customwidgets>
+ <customwidget>
+ <class>SequentialPageWidget</class>
+ <extends>QWidget</extends>
+ <header>sequentialpagewidget.h</header>
+ <container>1</container>
+ </customwidget>
+ </customwidgets>
+ <resources/>
+ <connections/>
+</ui>
diff --git a/examples/widgets/pdfviewer/pdfviewer.pro b/examples/widgets/pdfviewer/pdfviewer.pro
new file mode 100644
index 0000000..47a13f5
--- /dev/null
+++ b/examples/widgets/pdfviewer/pdfviewer.pro
@@ -0,0 +1,12 @@
+QT += core gui widgets pdf
+TARGET = pdfviewer
+TEMPLATE = app
+
+SOURCES += main.cpp\
+ mainwindow.cpp \
+ sequentialpagewidget.cpp
+
+HEADERS += mainwindow.h \
+ sequentialpagewidget.h
+
+FORMS += mainwindow.ui
diff --git a/examples/widgets/pdfviewer/sequentialpagewidget.cpp b/examples/widgets/pdfviewer/sequentialpagewidget.cpp
new file mode 100644
index 0000000..5de4f2e
--- /dev/null
+++ b/examples/widgets/pdfviewer/sequentialpagewidget.cpp
@@ -0,0 +1,63 @@
+#include "sequentialpagewidget.h"
+#include <QPaintEvent>
+#include <QPainter>
+#include <QPdfDocument>
+#include <QGuiApplication>
+#include <QScreen>
+#include <QLoggingCategory>
+
+Q_DECLARE_LOGGING_CATEGORY(lcExample)
+
+SequentialPageWidget::SequentialPageWidget(QWidget *parent)
+ : QWidget(parent)
+ , m_doc(Q_NULLPTR)
+ , m_background(Qt::darkGray)
+ , m_pageSpacing(3)
+ , m_zoom(1.)
+ , m_top(0.)
+ , m_screenResolution(QGuiApplication::primaryScreen()->logicalDotsPerInch() / 72.0)
+{
+}
+
+SequentialPageWidget::~SequentialPageWidget()
+{
+
+}
+
+void SequentialPageWidget::setDocument(QPdfDocument *doc)
+{
+ m_doc = doc;
+}
+
+void SequentialPageWidget::setZoom(qreal factor)
+{
+ m_zoom = factor;
+ m_pageCache.clear();
+ update();
+}
+
+void SequentialPageWidget::paintEvent(QPaintEvent * event)
+{
+ QPainter painter(this);
+ if (!m_doc) {
+ painter.drawText(rect(), Qt::AlignCenter, tr("no document loaded"));
+ return;
+ }
+
+ painter.fillRect(event->rect(), m_background);
+ qCDebug(lcExample) << event->rect() << m_doc->pageCount();
+
+ int page = 0; // qFloor(m_top);
+ int y = 0; // TODO event->rect().top();
+ while (y < event->rect().bottom() && page < m_doc->pageCount()) {
+ QSizeF size = m_doc->pageSize(page) * m_screenResolution * m_zoom;
+ if (!m_pageCache.contains(page)) {
+ qCDebug(lcExample) << "rendering page" << page << "to size" << size;
+ m_pageCache.insert(page, QPixmap::fromImage(m_doc->render(page, size)));
+ }
+ const QPixmap &pm = m_pageCache[page];
+ painter.drawPixmap(0, y, pm);
+ y += pm.height() + m_pageSpacing;
+ ++page;
+ }
+}
diff --git a/examples/widgets/pdfviewer/sequentialpagewidget.h b/examples/widgets/pdfviewer/sequentialpagewidget.h
new file mode 100644
index 0000000..6741fe3
--- /dev/null
+++ b/examples/widgets/pdfviewer/sequentialpagewidget.h
@@ -0,0 +1,34 @@
+#ifndef SEQUENTIALPAGEWIDGET_H
+#define SEQUENTIALPAGEWIDGET_H
+
+#include <QWidget>
+
+class QPdfDocument;
+
+class SequentialPageWidget : public QWidget
+{
+ Q_OBJECT
+public:
+ explicit SequentialPageWidget(QWidget *parent = 0);
+ ~SequentialPageWidget();
+
+ void paintEvent(QPaintEvent * event);
+
+public slots:
+ void setDocument(QPdfDocument *doc);
+ void setZoom(qreal factor);
+
+private:
+ void render(int page);
+
+private:
+ QPdfDocument *m_doc;
+ QHash<int, QPixmap> m_pageCache;
+ QBrush m_background;
+ int m_pageSpacing;
+ qreal m_zoom;
+ qreal m_top; // 1.5 means start from the bottom half of page 1
+ qreal m_screenResolution; // pixels per point
+};
+
+#endif // SEQUENTIALPAGEWIDGET_H