X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=src%2Fmonitorscene.cpp;h=e6be3de10188933da55b54a6b60c13e3dd682076;hb=56aee6aedeeed3efd10ada8fe3c229eddc01ef05;hp=857caab990d0a56ee7b64c9bfda77f659efc5ada;hpb=bd08944c74ebd91de5d41e45bf5ea15b17921002;p=kdenlive diff --git a/src/monitorscene.cpp b/src/monitorscene.cpp index 857caab9..e6be3de1 100644 --- a/src/monitorscene.cpp +++ b/src/monitorscene.cpp @@ -20,64 +20,75 @@ #include "monitorscene.h" #include "renderer.h" +#include "onmonitoritems/rotoscoping/bpointitem.h" +#include "onmonitoritems/rotoscoping/splineitem.h" #include "kdenlivesettings.h" #include #include #include +#include + MonitorScene::MonitorScene(Render *renderer, QObject* parent) : QGraphicsScene(parent), m_renderer(renderer), m_view(NULL), - m_selectedItem(NULL), - m_resizeMode(NoResize), - m_clickPoint(0, 0), m_backgroundImage(QImage()), m_enabled(true), - m_modified(false), - m_zoom(1.0) + m_zoom(1.0), + m_groupMove(false) { setBackgroundBrush(QBrush(QColor(KdenliveSettings::window_background().name()))); - QPen framepen(Qt::SolidLine); + QPen framepen(Qt::DotLine); framepen.setColor(Qt::red); - m_frameBorder = new QGraphicsRectItem(QRectF(0, 0, m_renderer->renderWidth(), m_renderer->renderHeight())); + m_frameBorder = new QGraphicsRectItem(QRectF(0, 0, m_renderer->frameRenderWidth(), m_renderer->renderHeight())); m_frameBorder->setPen(framepen); - m_frameBorder->setZValue(-2); + m_frameBorder->setZValue(-1); m_frameBorder->setBrush(Qt::transparent); m_frameBorder->setFlags(0); addItem(m_frameBorder); - m_lastUpdate.start(); + m_lastUpdate = QTime::currentTime(); m_background = new QGraphicsPixmapItem(); - m_background->setZValue(-1); + m_background->setZValue(-2); m_background->setFlags(0); m_background->setShapeMode(QGraphicsPixmapItem::BoundingRectShape); m_background->setTransformationMode(Qt::FastTransformation); - QPixmap bg(m_renderer->renderWidth(), m_renderer->renderHeight()); + QPixmap bg(m_renderer->frameRenderWidth(), m_renderer->renderHeight()); bg.fill(); m_background->setPixmap(bg); addItem(m_background); - //connect(m_renderer, SIGNAL(rendererPosition(int)), this, SLOT(slotUpdateBackground())); connect(m_renderer, SIGNAL(frameUpdated(QImage)), this, SLOT(slotSetBackgroundImage(QImage))); } +void MonitorScene::centerView() +{ + if (m_view) m_view->centerOn(m_frameBorder); +} + +void MonitorScene::cleanup() +{ + // Reset scene rect + setSceneRect(m_frameBorder->boundingRect()); +} + void MonitorScene::setUp() { - if (views().count() > 0) + if (!views().isEmpty()) { m_view = views().at(0); - else + m_view->setViewportUpdateMode(QGraphicsView::FullViewportUpdate); + } else { m_view = NULL; - - m_view->setViewportUpdateMode(QGraphicsView::FullViewportUpdate); + } } void MonitorScene::resetProfile() { - const QRectF border(0, 0, m_renderer->renderWidth(), m_renderer->renderHeight()); + const QRectF border(0, 0, m_renderer->frameRenderWidth(), m_renderer->renderHeight()); m_frameBorder->setRect(border); } @@ -89,18 +100,13 @@ void MonitorScene::setEnabled(bool enabled) void MonitorScene::slotUpdateBackground() { if (m_view && m_view->isVisible()) { - if (m_lastUpdate.elapsed() > 200) { - m_background->setPixmap(QPixmap::fromImage(m_backgroundImage, Qt::ThresholdDither)); - m_lastUpdate.start(); + if (m_lastUpdate.msecsTo(QTime::currentTime()) > 50) { + m_background->setPixmap(QPixmap::fromImage(m_backgroundImage)); + m_lastUpdate = QTime::currentTime(); } } } -void MonitorScene::slotSetDirectUpdate(bool directUpdate) -{ - KdenliveSettings::setMonitorscene_directupdate(directUpdate); -} - void MonitorScene::slotSetBackgroundImage(const QImage &image) { if (m_view && m_view->isVisible()) { @@ -109,13 +115,12 @@ void MonitorScene::slotSetBackgroundImage(const QImage &image) } } - void MonitorScene::slotZoom(int value) { if (m_view) { m_zoom = value / 100.0; m_view->resetTransform(); - m_view->scale(m_zoom, m_zoom); + m_view->scale(m_renderer->renderWidth() * m_zoom / m_renderer->frameRenderWidth(), m_zoom); emit zoomChanged(value); } } @@ -123,10 +128,10 @@ void MonitorScene::slotZoom(int value) void MonitorScene::slotZoomFit() { if (m_view) { - m_view->fitInView(m_frameBorder, Qt::KeepAspectRatio); + int xzoom = 100 * m_view->viewport()->height() / m_renderer->renderHeight(); + int yzoom = 100 * m_view->viewport()->width() / m_renderer->renderWidth(); + slotZoom(qMin(xzoom, yzoom)); m_view->centerOn(m_frameBorder); - m_zoom = m_view->matrix().m11(); - emit zoomChanged((int)(m_zoom * 100)); } } @@ -137,231 +142,138 @@ void MonitorScene::slotZoomOriginal() m_view->centerOn(m_frameBorder); } -void MonitorScene::slotZoomOut() +void MonitorScene::slotZoomOut(int by) { - slotZoom(qMax(0, (int)(m_zoom * 100 - 1))); + slotZoom(qMax(0, (int)(m_zoom * 100 - by))); } -void MonitorScene::slotZoomIn() +void MonitorScene::slotZoomIn(int by) { - slotZoom(qMin(300, (int)(m_zoom * 100 + 1))); + slotZoom(qMin(300, (int)(m_zoom * 100 + by + 0.5))); } - -resizeModes MonitorScene::getResizeMode(QGraphicsRectItem *item, QPoint pos) +void MonitorScene::mousePressEvent(QGraphicsSceneMouseEvent* event) { - if (!m_view) - return NoResize; - - QRectF rect = item->rect().normalized(); - // Item mapped coordinates - QPolygon pol = item->deviceTransform(m_view->viewportTransform()).map(rect).toPolygon(); - QPainterPath top(pol.point(0)); - top.lineTo(pol.point(1)); - QPainterPath bottom(pol.point(2)); - bottom.lineTo(pol.point(3)); - QPainterPath left(pol.point(0)); - left.lineTo(pol.point(3)); - QPainterPath right(pol.point(1)); - right.lineTo(pol.point(2)); - - QPainterPath mouseArea; - mouseArea.addRect(pos.x() - 4, pos.y() - 4, 8, 8); - - // Check for collisions between the mouse and the borders - if (mouseArea.contains(pol.point(0))) - return TopLeft; - else if (mouseArea.contains(pol.point(2))) - return BottomRight; - else if (mouseArea.contains(pol.point(1))) - return TopRight; - else if (mouseArea.contains(pol.point(3))) - return BottomLeft; - else if (top.intersects(mouseArea)) - return Top; - else if (bottom.intersects(mouseArea)) - return Bottom; - else if (right.intersects(mouseArea)) - return Right; - else if (left.intersects(mouseArea)) - return Left; - else - return NoResize; -} + QList selected = selectedItems(); -void MonitorScene::mousePressEvent(QGraphicsSceneMouseEvent *event) -{ - if (!m_enabled) - return; - - m_resizeMode = NoResize; - m_selectedItem = NULL; + QGraphicsScene::mousePressEvent(event); - m_clickPoint = event->scenePos(); - QList itemList = items(QRectF(m_clickPoint - QPoint(4, 4), QSizeF(4, 4)).toRect()); + if (selected.count() < selectedItems().count()) { + // mouse click on item not in selection group + // -> select only this item + foreach (QGraphicsItem *item, selected) { + if (item) + item->setSelected(false); + } + } - for (int i = 0; i < itemList.count(); ++i) { - if (itemList.at(i)->zValue() >= 0 && itemList.at(i)->flags() & QGraphicsItem::ItemIsMovable) { - m_selectedItem = itemList.at(i); - // Rect - if (itemList.at(i)->type() == 3) { - m_resizeMode = getResizeMode((QGraphicsRectItem*)m_selectedItem, m_view->mapFromScene(m_clickPoint)); - break; + if (event->isAccepted() && selectedItems().count() > 1) { + // multiple items selected + mouse pressed on an item + selected = selectedItems(); + foreach (QGraphicsItem *item, selected) { + if (qgraphicsitem_cast(item)) { + // works with rotoscoping only for now + m_groupMove = true; + m_lastPos = event->scenePos(); + return; } } } - QGraphicsScene::mousePressEvent(event); + if (!event->isAccepted() && event->buttons() & Qt::LeftButton) { + if (event->modifiers() == Qt::ControlModifier) + m_view->setDragMode(QGraphicsView::ScrollHandDrag); + else if (event->modifiers() == Qt::ShiftModifier) + m_view->setDragMode(QGraphicsView::RubberBandDrag); + } } void MonitorScene::mouseMoveEvent(QGraphicsSceneMouseEvent *event) { - if (!m_enabled) - return; - - /*if (event->buttons() != Qt::NoButton && (event->screenPos() - m_screenClickPoint).manhattanLength() < QApplication::startDragDistance()) { - event->accept(); - return; - }*/ - - QPointF mousePos = event->scenePos(); - - if (m_selectedItem && event->buttons() & Qt::LeftButton) { - // Rect - if (m_selectedItem->type() == 3) { - QGraphicsRectItem *item = static_cast (m_selectedItem); - QRectF rect = item->rect().normalized(); - QPointF pos = item->pos(); - QPointF mousePosInRect = item->mapFromScene(mousePos); - switch (m_resizeMode) { - case TopLeft: - if (mousePos.x() < pos.x() + rect.height() && mousePos.y() < pos.y() + rect.height()) { - item->setRect(rect.adjusted(0, 0, -mousePosInRect.x(), -mousePosInRect.y())); - item->setPos(mousePos); - m_modified = true; - } - break; - case Top: - if (mousePos.y() < pos.y() + rect.height()) { - rect.setBottom(rect.height() - mousePosInRect.y()); - item->setRect(rect); - item->setPos(QPointF(pos.x(), mousePos.y())); - m_modified = true; + if (m_groupMove) { + // we want to move multiple items + // rotoscoping only for now + QPointF diff = event->scenePos() - m_lastPos; + if (diff != QPointF(0, 0)) { + m_lastPos = event->scenePos(); + QList selected = selectedItems(); + int first = -1; + int i = 0; + foreach (QGraphicsItem *item, selected) { + BPointItem *bpoint = qgraphicsitem_cast(item); + if (bpoint) { + if (first < 0) + first = i; + BPoint p = bpoint->getPoint(); + p.setP(p.p + diff); + bpoint->setPoint(p); } - break; - case TopRight: - if (mousePos.x() > pos.x() && mousePos.y() < pos.y() + rect.height()) { - rect.setBottomRight(QPointF(mousePosInRect.x(), rect.bottom() - mousePosInRect.y())); - item->setRect(rect); - item->setPos(QPointF(pos.x(), mousePos.y())); - m_modified = true; - } - break; - case Left: - if (mousePos.x() < pos.x() + rect.width()) { - rect.setRight(rect.width() - mousePosInRect.x()); - item->setRect(rect); - item->setPos(QPointF(mousePos.x(), pos.y())); - m_modified = true; - } - break; - case Right: - if (mousePos.x() > pos.x()) { - rect.setRight(mousePosInRect.x()); - item->setRect(rect); - m_modified = true; - } - break; - case BottomLeft: - if (mousePos.x() < pos.x() + rect.width() && mousePos.y() > pos.y()) { - rect.setBottomRight(QPointF(rect.width() - mousePosInRect.x(), mousePosInRect.y())); - item->setRect(rect); - item->setPos(QPointF(mousePos.x(), pos.y())); - m_modified = true; - } - break; - case Bottom: - if (mousePos.y() > pos.y()) { - rect.setBottom(mousePosInRect.y()); - item->setRect(rect); - m_modified = true; - } - break; - case BottomRight: - if (mousePos.x() > pos.x() && mousePos.y() > pos.y()) { - rect.setBottomRight(mousePosInRect); - item->setRect(rect); - m_modified = true; + ++i; + } + + if (first >= 0) { + QGraphicsItem *item = selected.at(first); + if (item->parentItem()) { + SplineItem *parent = qgraphicsitem_cast(item->parentItem()); + if (parent) + parent->updateSpline(true); } - break; - default: - QPointF diff = mousePos - m_clickPoint; - m_clickPoint = mousePos; - item->moveBy(diff.x(), diff.y()); - m_modified = true; - break; } } } else { - mousePos -= QPoint(4, 4); - bool itemFound = false; - QList itemList = items(QRectF(mousePos, QSizeF(4, 4)).toRect()); - - foreach(const QGraphicsItem* item, itemList) { - if (item->zValue() >= 0 && item->flags() &QGraphicsItem::ItemIsMovable) { - // Rect - if (item->type() == 3) { - if (m_view == NULL) - continue; - - itemFound = true; - - switch (getResizeMode((QGraphicsRectItem*)item, m_view->mapFromScene(event->scenePos()))) { - case TopLeft: - case BottomRight: - m_view->setCursor(Qt::SizeFDiagCursor); - break; - case TopRight: - case BottomLeft: - m_view->setCursor(Qt::SizeBDiagCursor); - break; - case Top: - case Bottom: - m_view->setCursor(Qt::SizeVerCursor); - break; - case Left: - case Right: - m_view->setCursor(Qt::SizeHorCursor); - break; - default: - m_view->setCursor(Qt::OpenHandCursor); - } + QGraphicsScene::mouseMoveEvent(event); + } +} + +void MonitorScene::mouseReleaseEvent(QGraphicsSceneMouseEvent* event) +{ + if (m_groupMove) { + QList selected = selectedItems(); + foreach (QGraphicsItem *item, selected) { + if (qgraphicsitem_cast(item) && item->parentItem()) { + SplineItem *parent = qgraphicsitem_cast(item->parentItem()); + if (parent) { + parent->updateSpline(false); break; } } } - - if (!itemFound && m_view) - m_view->setCursor(Qt::ArrowCursor); - - QGraphicsScene::mouseMoveEvent(event); - } - if (m_modified && KdenliveSettings::monitorscene_directupdate()) { - emit actionFinished(); - m_modified = false; + m_groupMove = false; } + QGraphicsScene::mouseReleaseEvent(event); + m_view->setDragMode(QGraphicsView::NoDrag); } - -void MonitorScene::mouseReleaseEvent(QGraphicsSceneMouseEvent *event) +void MonitorScene::mouseDoubleClickEvent(QGraphicsSceneMouseEvent* event) { + Q_UNUSED(event) + if (!m_enabled) - return; + emit addKeyframe(); +} - QGraphicsScene::mouseReleaseEvent(event); - if (m_modified) { - m_modified = false; - emit actionFinished(); +void MonitorScene::wheelEvent(QGraphicsSceneWheelEvent* event) +{ + if (event->modifiers() == Qt::ControlModifier) { + if (event->delta() > 0) { + m_view->setTransformationAnchor(QGraphicsView::AnchorUnderMouse); + slotZoomIn(5); + m_view->setTransformationAnchor(QGraphicsView::AnchorViewCenter); + } else { + slotZoomOut(5); + } + } else { + QAbstractSlider::SliderAction action; + if (event->delta() > 0) + action = QAbstractSlider::SliderSingleStepSub; + else + action = QAbstractSlider::SliderSingleStepAdd; + if (event->orientation() == Qt::Horizontal) + m_view->horizontalScrollBar()->triggerAction(action); + else + m_view->verticalScrollBar()->triggerAction(action); } + + event->accept(); } #include "monitorscene.moc"