diff options
Diffstat (limited to 'notebookview.cc')
-rw-r--r-- | notebookview.cc | 194 |
1 files changed, 194 insertions, 0 deletions
diff --git a/notebookview.cc b/notebookview.cc new file mode 100644 index 0000000..2605792 --- /dev/null +++ b/notebookview.cc @@ -0,0 +1,194 @@ +#include <QtCore/QDebug> +#include <QtGui/QResizeEvent> +#include "notebookview.h" + +#define VIEW_MARGIN 2 +#define PAGE_SEPARATION 100 + +NotebookView::NotebookView(QWidget *parent) : + QGraphicsView(parent), _nb(new AfdNotebook(this)), + _zoom(100), _curPage(0) +{ + setScene(new QGraphicsScene(this)); + setTransformationAnchor(AnchorUnderMouse); + setDragMode(ScrollHandDrag); + setRenderHints(QPainter::Antialiasing); +} + +void NotebookView::setNotebook(const QString &path) +{ + removePages(); + if (!path.isEmpty()) { + if (_nb->open(path)) { + _nbPath = path; + if (_zoom > 100) { + _zoom = 100; + emit zoomChanged(); + } + createPages(); + emit pageNumbersChanged(); + if (!_pages.isEmpty()) { + _curPage = _pages.begin().key(); + centerOn(_pages[_curPage]); + emit curPageChanged(); + } + } else { + qWarning() << "Could not open notebook:" << _nbPath; + } + } +} + +QString NotebookView::notebook() const +{ + return _nbPath; +} + +QList<int> NotebookView::pageNumbers() const +{ + return _pages.keys(); +} + +int NotebookView::curPage() const +{ + return _curPage; +} + +void NotebookView::setCurPage(int page) +{ + if (page != _curPage) { + _curPage = page; + if (_zoom > 100) { + setZoom(100); + } + if (_pages.contains(_curPage)) { + centerOn(_pages[_curPage]); + } + emit curPageChanged(); + } +} + +int NotebookView::zoom() const +{ + return _zoom; +} + +void NotebookView::setZoom(int zoom) +{ + if (zoom != _zoom) { + _zoom = zoom; + calculateScale(); + } +} + +void NotebookView::clear() +{ + removePages(); + emit pageNumbersChanged(); +} + +void NotebookView::prevPage() +{ + QMap<int, PageItem*>::iterator it = _pages.lowerBound(_curPage); + if (it != _pages.end() && it != _pages.begin()) { + --it; + setCurPage(it.key()); + } +} + +void NotebookView::nextPage() +{ + QMap<int, PageItem*>::iterator it = _pages.upperBound(_curPage); + if (it != _pages.end()) { + setCurPage(it.key()); + } +} + +void NotebookView::resizeEvent(QResizeEvent *event) +{ + QGraphicsView::resizeEvent(event); + calculateScale(); +} + +void NotebookView::scrollContentsBy(int dx, int dy) +{ + QGraphicsView::scrollContentsBy(dx, dy); + QGraphicsItem *item = itemAt(size().width() / 2, size().height() / 2); + while (item && item->type() != PageItem::Type) { + item = item->parentItem(); + } + if (item && item->type() == PageItem::Type) { + PageItem * page = static_cast<PageItem*>(item); + int centerPage = page->pageNum(); + if (centerPage != _curPage) { + _curPage = centerPage; + emit curPageChanged(); + } + } +} + +void NotebookView::removePages() +{ + _pages.clear(); + scene()->clear(); + scene()->setSceneRect(QRectF()); + _nb->close(); + _nbPath.clear(); + _maxPageSize.setWidth(0); + _maxPageSize.setHeight(0); + resetTransform(); +} + +void NotebookView::createPages() +{ + QStringList pens = _nb->penSerials(); + if (pens.isEmpty()) return; + + QList<int> pagesWithStrokes = _nb->pagesWithStrokes(pens.first()); + Q_ASSERT(_pages.isEmpty()); + + _maxPageSize.setWidth(0); + _maxPageSize.setHeight(0); + foreach (int pageNum, pagesWithStrokes) { + PageItem *page = new PageItem(_nb, pageNum); + QRectF box = page->boundingRect(); + if (box.width() > _maxPageSize.width()) { + _maxPageSize.setWidth(box.width()); + } + if (box.height() > _maxPageSize.height()) { + _maxPageSize.setHeight(box.height()); + } + _pages.insert(pageNum, page); + } + + calculateScale(); + + qreal curY = 0; + foreach (PageItem *page, _pages) { + QRectF box = page->boundingRect(); + page->setPos((_maxPageSize.width() - box.width()) / 2.0, curY); + curY += box.height(); + curY += PAGE_SEPARATION; + + scene()->addItem(page); + } + + scene()->setSceneRect(0, 0, _maxPageSize.width(), curY); +} + +void NotebookView::calculateScale() +{ + if (_pages.isEmpty() || _maxPageSize.isEmpty()) return; + const int margin = VIEW_MARGIN; + QRectF viewRect = viewport()->rect().adjusted(margin, margin, -margin, margin); + qreal baseScale = qMin(viewRect.width() / _maxPageSize.width(), + viewRect.height() / _maxPageSize.height()); + resetTransform(); + scale(baseScale, baseScale); + if (_zoom < 100) { + qreal s = 0.25 + ((_zoom / 100.0) * 0.75); + scale(s, s); + } else if (_zoom > 100) { + qreal s = 1.0 + (_zoom - 100) * 0.015; + scale(s, s); + } +} |