]> git.sesse.net Git - kdenlive/blobdiff - src/abstractmonitor.cpp
Const'ref
[kdenlive] / src / abstractmonitor.cpp
index 8ba3527bdcdd2807a37b00dc5d8b076fc8816e98..eac998a99784ae16d177404a9011031ef7d0d1a5 100644 (file)
 
 #include "abstractmonitor.h"
 #include "kdenlivesettings.h"
+#include "monitormanager.h"
 
 #include <KDebug>
 
 #include <QPaintEvent>
+#include <QDesktopWidget>
+#include <QVBoxLayout>
 
-VideoPreviewContainer::VideoPreviewContainer(QWidget *parent) :
-    QFrame(parent),
-    m_dar(1.0),
-    m_refresh(false)
+
+AbstractMonitor::AbstractMonitor(Kdenlive::MONITORID id, MonitorManager *manager, QWidget *parent): 
+    QWidget(parent),
+    videoSurface(NULL),
+    m_id(id),
+    m_monitorManager(manager)
 {
-    setFrameShape(QFrame::NoFrame);
-    setFocusPolicy(Qt::ClickFocus);
-    setAttribute(Qt::WA_PaintOnScreen);
-    setAttribute(Qt::WA_OpaquePaintEvent);
-    setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding);
-    connect(&m_refreshTimer, SIGNAL(timeout()), this, SLOT(update()));
-    m_refreshTimer.setSingleShot(false);
-    m_refreshTimer.setInterval(200);
+    videoBox = new VideoContainer(this);
 }
 
-VideoPreviewContainer::~VideoPreviewContainer()
+
+AbstractMonitor::~AbstractMonitor()
 {
-    qDeleteAll(m_imageQueue);
+    delete videoSurface;
 }
 
-//virtual
-void VideoPreviewContainer::resizeEvent( QResizeEvent * /*event*/ )
+void AbstractMonitor::createVideoSurface()
 {
-    updateDisplayZone();
+    QVBoxLayout *lay = new QVBoxLayout;
+    lay->setContentsMargins(0, 0, 0, 0);
+    videoSurface = new VideoSurface;
+    lay->addWidget(videoSurface);
+    videoBox->setLayout(lay);
 }
 
-void VideoPreviewContainer::setRatio(double ratio)
+bool AbstractMonitor::isActive() const
 {
-    m_dar = ratio;
-    updateDisplayZone();
+    return m_monitorManager->isActive(m_id);
 }
 
+bool AbstractMonitor::slotActivateMonitor(bool forceRefresh)
+{
+    return m_monitorManager->activateMonitor(m_id, forceRefresh);
+}
 
-void VideoPreviewContainer::updateDisplayZone()
+VideoContainer::VideoContainer(AbstractMonitor* monitor, QWidget *parent) :
+    QFrame(parent)
+    , m_monitor(monitor)
 {
-    QRect rect = this->frameRect();
-    int paintW = rect.height() * m_dar + 0.5;
-    if (paintW > rect.width()) {
-        int paintH = rect.width() / m_dar + 0.5;
-        int diff = (rect.height() - paintH)  / 2;
-        rect.adjust(0, diff, 0, 0);
-        rect.setHeight(paintH);
-    }
-    else {
-        int diff = (rect.width() - paintW)  / 2;
-        rect.adjust(diff, 0, 0, 0);
-        rect.setWidth(paintW);
-    }
-    m_displayRect = rect;
-    m_refresh = true;
+    setFrameShape(QFrame::NoFrame);
+    setFocusPolicy(Qt::ClickFocus);
+    //setEnabled(false);
+    setContentsMargins(0, 0, 0, 0);
+    setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding);
 }
 
-void VideoPreviewContainer::setImage(QImage img)
+// virtual
+void VideoContainer::mouseReleaseEvent(QMouseEvent * event)
 {
-    if (m_imageQueue.count() > 2) {
-        delete m_imageQueue.takeLast();
+    if (event->button() != Qt::RightButton) {
+        if (m_monitor->isActive()) {
+            m_monitor->slotPlay();
+        }
     }
-    m_imageQueue.prepend(new QImage(img));
-    update();
 }
 
-void VideoPreviewContainer::stop()
+// virtual
+void VideoContainer::keyPressEvent(QKeyEvent *event)
 {
-    //m_refreshTimer.stop();
-    qDeleteAll(m_imageQueue);
-    m_imageQueue.clear();
+    // Exit fullscreen with Esc key
+    if (event->key() == Qt::Key_Escape && isFullScreen()) {
+        switchFullScreen();
+        event->setAccepted(true);
+    } else event->setAccepted(false);
 }
 
-void VideoPreviewContainer::start()
+// virtual
+void VideoContainer::wheelEvent(QWheelEvent * event)
 {
-    //m_refreshTimer.start();
+    m_monitor->slotMouseSeek(event->delta(), event->modifiers() == Qt::ControlModifier);
+    event->accept();
 }
 
-// virtual
-void VideoPreviewContainer::paintEvent(QPaintEvent *event)
+void VideoContainer::mouseDoubleClickEvent(QMouseEvent * event)
+{
+    if (!KdenliveSettings::openglmonitors())
+        switchFullScreen();
+    event->accept();
+}
+
+void VideoContainer::switchFullScreen()
 {
-    if (m_imageQueue.isEmpty()) return;
-    QImage *img = m_imageQueue.takeFirst();
-    QPainter painter(this);
-    if (m_refresh) {
-        painter.fillRect(event->rect(), QColor(KdenliveSettings::window_background()));
-        m_refresh = false;
+    // TODO: disable screensaver?
+    Qt::WindowFlags flags = windowFlags();
+    if (!isFullScreen()) {
+        // Check if we ahave a multiple monitor setup
+        setUpdatesEnabled(false);
+#if QT_VERSION >= 0x040600
+        int monitors = QApplication::desktop()->screenCount();
+#else
+        int monitors = QApplication::desktop()->numScreens();
+#endif
+        if (monitors > 1) {
+            QRect screenres;
+            // Move monitor widget to the second screen (one screen for Kdenlive, the other one for the Monitor widget
+            int currentScreen = QApplication::desktop()->screenNumber(this);
+            if (currentScreen < monitors - 1)
+                screenres = QApplication::desktop()->screenGeometry(currentScreen + 1);
+            else
+                screenres = QApplication::desktop()->screenGeometry(currentScreen - 1);
+            move(QPoint(screenres.x(), screenres.y()));
+            resize(screenres.width(), screenres.height());
+        }
+
+        m_baseFlags = flags & (Qt::Window | Qt::SubWindow);
+        flags |= Qt::Window;
+        flags ^= Qt::SubWindow;
+        setWindowFlags(flags);
+#ifdef Q_WS_X11
+        // This works around a bug with Compiz
+        // as the window must be visible before we can set the state
+        show();
+        raise();
+        setWindowState(windowState() | Qt::WindowFullScreen);   // set
+#else
+        setWindowState(windowState() | Qt::WindowFullScreen);   // set
+        setUpdatesEnabled(true);
+        show();
+#endif
+        setEnabled(true);
+    } else {
+        setUpdatesEnabled(false);
+        flags ^= (Qt::Window | Qt::SubWindow); //clear the flags...
+        flags |= m_baseFlags; //then we reset the flags (window and subwindow)
+        setWindowFlags(flags);
+        setWindowState(windowState()  ^ Qt::WindowFullScreen);   // reset
+        setUpdatesEnabled(true);
+        setEnabled(false);
+        show();
     }
-    painter.drawImage(m_displayRect, *img);
-    delete img;
+}
+
+VideoSurface::VideoSurface(QWidget* parent) :
+    QWidget(parent)
+{
+    // MonitorRefresh is used as container for the SDL display (it's window id is passed to SDL)
+    setAttribute(Qt::WA_PaintOnScreen);
+    setAttribute(Qt::WA_OpaquePaintEvent);
+    setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding);
+    setAttribute(Qt::WA_NoSystemBackground);
+    //setUpdatesEnabled(false);
+}
+
+void VideoSurface::paintEvent(QPaintEvent *event)
+{
+    Q_UNUSED(event);
+    //WARNING: This might trigger unnecessary refreshes from MLT's producer, but without this,
+    // as soon as monitor is covered by a popup menu or another window, image is corrupted.
+    emit refreshMonitor();
 }
 
 
+#include "abstractmonitor.moc"