Commit 60d534a5 authored by Dan Dennedy's avatar Dan Dennedy

Update scopes using a frame image from the consumer-frame-show event

handler instead of requesting it from the producer with possibly an
undesirable seek as a side effect.


svn path=/trunk/kdenlive/; revision=4691
parent c199c097
......@@ -60,4 +60,4 @@ add_subdirectory(titles)
add_subdirectory(po)
add_subdirectory(man)
configure_file(${CMAKE_SOURCE_DIR}/kdenlive-config.h.cmake kdenlive-config.h @ONLY)
\ No newline at end of file
configure_file(${CMAKE_SOURCE_DIR}/kdenlive-config.h.cmake kdenlive-config.h @ONLY)
......@@ -68,7 +68,7 @@ AbstractScopeWidget::AbstractScopeWidget(Monitor *projMonitor, Monitor *clipMoni
b &= connect(this, SIGNAL(customContextMenuRequested(QPoint)), this, SLOT(customContextMenuRequested(QPoint)));
b &= connect(m_activeRender, SIGNAL(rendererPosition(int)), this, SLOT(slotRenderZoneUpdated()));
b &= connect(m_activeRender, SIGNAL(frameUpdated(int)), this, SLOT(slotRenderZoneUpdated()));
b &= connect(m_activeRender, SIGNAL(frameUpdated(QImage)), this, SLOT(slotRenderZoneUpdated(QImage)));
b &= connect(this, SIGNAL(signalHUDRenderingFinished(uint,uint)), this, SLOT(slotHUDRenderingFinished(uint,uint)));
b &= connect(this, SIGNAL(signalScopeRenderingFinished(uint,uint)), this, SLOT(slotScopeRenderingFinished(uint,uint)));
......@@ -122,7 +122,7 @@ void AbstractScopeWidget::prodScopeThread()
// See http://doc.qt.nokia.com/latest/qtconcurrentrun.html#run about
// running member functions in a thread
m_threadScope = QtConcurrent::run(this, &AbstractScopeWidget::renderScope, m_accelFactorScope);
m_threadScope = QtConcurrent::run(this, &AbstractScopeWidget::renderScope, m_accelFactorScope, m_scopeImage);
qDebug() << "Scope thread started in " << widgetName();
......@@ -328,7 +328,7 @@ void AbstractScopeWidget::slotActiveMonitorChanged(bool isClipMonitor)
m_activeRender = (isClipMonitor) ? m_clipMonitor->render : m_projMonitor->render;
b &= connect(m_activeRender, SIGNAL(rendererPosition(int)), this, SLOT(slotRenderZoneUpdated()));
b &= connect(m_activeRender, SIGNAL(frameUpdated(int)), this, SLOT(slotRenderZoneUpdated()));
b &= connect(m_activeRender, SIGNAL(frameUpdated(QImage)), this, SLOT(slotRenderZoneUpdated(QImage)));
Q_ASSERT(b);
// Update the scope for the new monitor.
......@@ -357,6 +357,12 @@ void AbstractScopeWidget::slotRenderZoneUpdated()
}
}
void AbstractScopeWidget::slotRenderZoneUpdated(QImage frame)
{
m_scopeImage = frame;
slotRenderZoneUpdated();
}
void AbstractScopeWidget::slotResetRealtimeFactor(bool realtimeChecked)
{
if (!realtimeChecked) {
......
......@@ -125,7 +125,7 @@ protected:
/** @brief Scope renderer. Must emit signalScopeRenderingFinished()
when calculation has finished, to allow multi-threading.
accelerationFactor hints how much faster than usual the calculation should be accomplished, if possible. */
virtual QImage renderScope(uint accelerationFactor) = 0;
virtual QImage renderScope(uint accelerationFactor, QImage) = 0;
/** @brief Background renderer. Must emit signalBackgroundRenderingFinished(). @see renderScope */
virtual QImage renderBackground(uint accelerationFactor) = 0;
......@@ -193,6 +193,8 @@ private:
QFuture<QImage> m_threadScope;
QFuture<QImage> m_threadBackground;
QImage m_scopeImage;
bool initialDimensionUpdateDone;
void prodHUDThread();
void prodScopeThread();
......@@ -206,6 +208,7 @@ private slots:
void slotActiveMonitorChanged(bool isClipMonitor);
void customContextMenuRequested(const QPoint &pos);
void slotRenderZoneUpdated();
void slotRenderZoneUpdated(QImage);
void slotHUDRenderingFinished(uint mseconds, uint accelerationFactor);
void slotScopeRenderingFinished(uint mseconds, uint accelerationFactor);
void slotBackgroundRenderingFinished(uint mseconds, uint accelerationFactor);
......
......@@ -65,7 +65,7 @@ QImage Histogram::renderHUD(uint)
emit signalHUDRenderingFinished(0, 1);
return QImage();
}
QImage Histogram::renderScope(uint accelFactor)
QImage Histogram::renderScope(uint accelFactor, QImage qimage)
{
QTime start = QTime::currentTime();
start.start();
......@@ -75,7 +75,7 @@ QImage Histogram::renderScope(uint accelFactor)
| (ui->cbG->isChecked() ? 1 : 0) * HistogramGenerator::ComponentG
| (ui->cbB->isChecked() ? 1 : 0) * HistogramGenerator::ComponentB;
QImage histogram = m_histogramGenerator->calculateHistogram(m_scopeRect.size(), m_activeRender->extractFrame(m_activeRender->seekFramePosition()),
QImage histogram = m_histogramGenerator->calculateHistogram(m_scopeRect.size(), qimage,
componentFlags, m_aUnscaled->isChecked(), accelFactor);
emit signalScopeRenderingFinished(start.elapsed(), accelFactor);
......
......@@ -34,7 +34,7 @@ private:
bool isScopeDependingOnInput() const;
bool isBackgroundDependingOnInput() const;
QImage renderHUD(uint accelerationFactor);
QImage renderScope(uint accelerationFactor);
QImage renderScope(uint accelerationFactor, QImage);
QImage renderBackground(uint accelerationFactor);
Ui::Histogram_UI *ui;
......
......@@ -65,6 +65,8 @@ static void consumer_frame_show(mlt_consumer, Render * self, mlt_frame frame_ptr
#endif
self->emitFrameNumber(mlt_frame_get_position(frame_ptr));
if (frame_ptr->convert_image)
self->emitFrameUpdated(frame);
if (frame.get_double("_speed") == 0.0) {
self->emitConsumerStopped();
} else if (frame.get_double("_speed") < 0.0 && mlt_frame_get_position(frame_ptr) <= 0) {
......@@ -1438,12 +1440,19 @@ const QString & Render::rendererName() const
return m_name;
}
void Render::emitFrameUpdated(Mlt::Frame& frame)
{
mlt_image_format format = mlt_image_rgb24a;
int width = 0;
int height = 0;
const uchar* image = frame.get_image(format, width, height);
QImage qimage(width, height, QImage::Format_ARGB32);
memcpy(qimage.bits(), image, width * height * 4);
emit frameUpdated(qimage);
}
void Render::emitFrameNumber(double position)
{
if (position == m_framePosition) {
emit frameUpdated((int) position);
return;
}
m_framePosition = position;
emit rendererPosition((int) position);
}
......
......@@ -161,6 +161,7 @@ Q_OBJECT public:
GenTime seekPosition() const;
int seekFramePosition() const;
void emitFrameUpdated(Mlt::Frame&);
void emitFrameNumber(double position);
void emitConsumerStopped();
......@@ -344,7 +345,7 @@ signals:
* Used in Mac OS X. */
void showImageSignal(QImage);
/** @brief The renderer refreshed the current frame, but no seeking was done. */
void frameUpdated(int);
void frameUpdated(QImage);
public slots:
......
......@@ -37,11 +37,11 @@ QRect RGBParade::scopeRect()
}
QImage RGBParade::renderHUD(uint) { return QImage(); }
QImage RGBParade::renderScope(uint accelerationFactor)
QImage RGBParade::renderScope(uint accelerationFactor, QImage qimage)
{
QTime start = QTime::currentTime();
start.start();
QImage parade = m_rgbParadeGenerator->calculateRGBParade(m_scopeRect.size(), m_activeRender->extractFrame(m_activeRender->seekFramePosition()),
QImage parade = m_rgbParadeGenerator->calculateRGBParade(m_scopeRect.size(), qimage,
true, accelerationFactor);
emit signalScopeRenderingFinished(start.elapsed(), accelerationFactor);
return parade;
......
......@@ -39,7 +39,7 @@ private:
bool isBackgroundDependingOnInput() const;
QImage renderHUD(uint accelerationFactor);
QImage renderScope(uint accelerationFactor);
QImage renderScope(uint accelerationFactor, QImage);
QImage renderBackground(uint accelerationFactor);
};
......
......@@ -192,7 +192,7 @@ QImage Vectorscope::renderHUD(uint)
return hud;
}
QImage Vectorscope::renderScope(uint accelerationFactor)
QImage Vectorscope::renderScope(uint accelerationFactor, QImage qimage)
{
QTime start = QTime::currentTime();
QImage scope;
......@@ -202,7 +202,7 @@ QImage Vectorscope::renderScope(uint accelerationFactor)
} else {
scope = m_vectorscopeGenerator->calculateVectorscope(m_scopeRect.size(),
m_activeRender->extractFrame(m_activeRender->seekFramePosition()),
qimage,
m_gain, (VectorscopeGenerator::PaintMode) ui->paintMode->itemData(ui->paintMode->currentIndex()).toInt(),
m_aAxisEnabled->isChecked(), accelerationFactor);
......
......@@ -41,7 +41,7 @@ protected:
///// Implemented methods /////
QRect scopeRect();
QImage renderHUD(uint accelerationFactor);
QImage renderScope(uint accelerationFactor);
QImage renderScope(uint accelerationFactor, QImage);
QImage renderBackground(uint accelerationFactor);
bool isHUDDependingOnInput() const;
bool isScopeDependingOnInput() const;
......
......@@ -58,13 +58,13 @@ QImage Waveform::renderHUD(uint)
return QImage();
}
QImage Waveform::renderScope(uint accelFactor)
QImage Waveform::renderScope(uint accelFactor, QImage qimage)
{
QTime start = QTime::currentTime();
start.start();
QImage wave = m_waveformGenerator->calculateWaveform(scopeRect().size(),
m_activeRender->extractFrame(m_activeRender->seekFramePosition()), true, accelFactor);
qimage, true, accelFactor);
emit signalScopeRenderingFinished(start.elapsed(), 1);
return wave;
......
......@@ -39,7 +39,7 @@ private:
/// Implemented methods ///
QRect scopeRect();
QImage renderHUD(uint);
QImage renderScope(uint);
QImage renderScope(uint, QImage);
QImage renderBackground(uint);
bool isHUDDependingOnInput() const;
bool isScopeDependingOnInput() const;
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment