nodes: fix loop mode regression
This commit is contained in:
@@ -293,7 +293,7 @@ bool Decoder::RetrieveAudioFromConform(SampleBuffer &sample_buffer, const QVecto
|
||||
const qint64 buffer_length_in_bytes = sample_buffer.sample_count() * input_params.bytes_per_sample_per_channel();
|
||||
|
||||
while (write_index < buffer_length_in_bytes) {
|
||||
if (loop_mode == kLoopModeLoop) {
|
||||
if (loop_mode == LoopMode::kLoopModeLoop) {
|
||||
while (read_index >= input.size()) {
|
||||
read_index -= input.size();
|
||||
}
|
||||
|
||||
+1
-8
@@ -31,12 +31,11 @@ extern "C" {
|
||||
#include <QWaitCondition>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "codec/frame.h"
|
||||
#include "codec/samplebuffer.h"
|
||||
#include "common/rational.h"
|
||||
#include "node/block/block.h"
|
||||
#include "node/project/footage/footagedescription.h"
|
||||
#include "task/task.h"
|
||||
#include "render/cancelatom.h"
|
||||
|
||||
namespace olive {
|
||||
|
||||
@@ -71,12 +70,6 @@ public:
|
||||
kIndexUnavailable
|
||||
};
|
||||
|
||||
enum LoopMode {
|
||||
kLoopModeOff,
|
||||
kLoopModeLoop,
|
||||
kLoopModeClamp
|
||||
};
|
||||
|
||||
Decoder();
|
||||
|
||||
/**
|
||||
|
||||
@@ -100,9 +100,9 @@ SpeedDurationDialog::SpeedDurationDialog(const QVector<ClipBlock *> &clips, cons
|
||||
loop_layout->addWidget(new QLabel(tr("Loop:")), row, 0);
|
||||
|
||||
loop_combo_ = new QComboBox();
|
||||
loop_combo_->addItem(tr("None"), Decoder::kLoopModeOff);
|
||||
loop_combo_->addItem(tr("Loop"), Decoder::kLoopModeLoop);
|
||||
loop_combo_->addItem(tr("Clamp"), Decoder::kLoopModeClamp);
|
||||
loop_combo_->addItem(tr("None"), int(LoopMode::kLoopModeOff));
|
||||
loop_combo_->addItem(tr("Loop"), int(LoopMode::kLoopModeLoop));
|
||||
loop_combo_->addItem(tr("Clamp"), int(LoopMode::kLoopModeClamp));
|
||||
loop_layout->addWidget(loop_combo_, row, 1);
|
||||
}
|
||||
|
||||
@@ -117,7 +117,7 @@ SpeedDurationDialog::SpeedDurationDialog(const QVector<ClipBlock *> &clips, cons
|
||||
start_duration_ = clips.first()->length();
|
||||
start_reverse_ = clips.first()->reverse();
|
||||
start_maintain_audio_pitch_ = clips.first()->maintain_audio_pitch();
|
||||
start_loop_ = clips.first()->loop_mode();
|
||||
start_loop_ = int(clips.first()->loop_mode());
|
||||
for (int i=1; i<clips.size(); i++) {
|
||||
ClipBlock *c = clips.at(i);
|
||||
|
||||
@@ -141,7 +141,7 @@ SpeedDurationDialog::SpeedDurationDialog(const QVector<ClipBlock *> &clips, cons
|
||||
start_maintain_audio_pitch_ = -1;
|
||||
}
|
||||
|
||||
if (start_loop_ != -1 && c->loop_mode() != start_loop_) {
|
||||
if (start_loop_ != -1 && int(c->loop_mode()) != start_loop_) {
|
||||
start_loop_ = -1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -453,6 +453,8 @@ void ClipBlock::InputValueChangedEvent(const QString &input, int element)
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (input == kLoopModeInput) {
|
||||
emit PreviewChanged();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -188,12 +188,12 @@ public:
|
||||
/**
|
||||
* @brief Get currently set loop mode
|
||||
*/
|
||||
Decoder::LoopMode loop_mode() const
|
||||
LoopMode loop_mode() const
|
||||
{
|
||||
return static_cast<Decoder::LoopMode>(GetStandardValue(kLoopModeInput).toInt());
|
||||
return static_cast<LoopMode>(GetStandardValue(kLoopModeInput).toInt());
|
||||
}
|
||||
|
||||
void set_loop_mode(Decoder::LoopMode l)
|
||||
void set_loop_mode(LoopMode l)
|
||||
{
|
||||
SetStandardValue(kLoopModeInput, int(l));
|
||||
}
|
||||
|
||||
+11
-2
@@ -25,6 +25,7 @@
|
||||
|
||||
#include "common/timerange.h"
|
||||
#include "render/audioparams.h"
|
||||
#include "render/loopmode.h"
|
||||
#include "render/videoparams.h"
|
||||
|
||||
namespace olive {
|
||||
@@ -34,10 +35,16 @@ class NodeGlobals
|
||||
public:
|
||||
NodeGlobals(){}
|
||||
|
||||
NodeGlobals(const VideoParams &vparam, const AudioParams &aparam, const TimeRange &time) :
|
||||
NodeGlobals(const VideoParams &vparam, const AudioParams &aparam, const TimeRange &time, LoopMode loop_mode) :
|
||||
video_params_(vparam),
|
||||
audio_params_(aparam),
|
||||
time_(time)
|
||||
time_(time),
|
||||
loop_mode_(loop_mode)
|
||||
{
|
||||
}
|
||||
|
||||
NodeGlobals(const VideoParams &vparam, const AudioParams &aparam, const rational &time, LoopMode loop_mode) :
|
||||
NodeGlobals(vparam, aparam, TimeRange(time, time + vparam.frame_rate_as_time_base()), loop_mode)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -46,11 +53,13 @@ public:
|
||||
const AudioParams &aparams() const { return audio_params_; }
|
||||
const VideoParams &vparams() const { return video_params_; }
|
||||
const TimeRange &time() const { return time_; }
|
||||
LoopMode loop_mode() const { return loop_mode_; }
|
||||
|
||||
private:
|
||||
VideoParams video_params_;
|
||||
AudioParams audio_params_;
|
||||
TimeRange time_;
|
||||
LoopMode loop_mode_;
|
||||
|
||||
};
|
||||
|
||||
|
||||
@@ -265,7 +265,7 @@ void Footage::Value(const NodeValueRow &value, const NodeGlobals &globals, NodeV
|
||||
// Push each stream as a footage job
|
||||
for (int i=0; i<GetTotalStreamCount(); i++) {
|
||||
Track::Reference ref = GetReferenceFromRealIndex(i);
|
||||
FootageJob job(globals.time(), decoder_, filename(), ref.type(), GetLength());
|
||||
FootageJob job(globals.time(), decoder_, filename(), ref.type(), GetLength(), globals.loop_mode());
|
||||
|
||||
if (ref.type() == Track::kVideo) {
|
||||
VideoParams vp = GetVideoParams(ref.index());
|
||||
@@ -337,7 +337,7 @@ bool TimeIsOutOfBounds(const rational& time, const rational& length)
|
||||
return time < 0 || time >= length;
|
||||
}
|
||||
|
||||
rational Footage::AdjustTimeByLoopMode(rational time, Decoder::LoopMode loop_mode, const rational &length, VideoParams::Type type, const rational& timebase)
|
||||
rational Footage::AdjustTimeByLoopMode(rational time, LoopMode loop_mode, const rational &length, VideoParams::Type type, const rational& timebase)
|
||||
{
|
||||
if (type == VideoParams::kVideoTypeStill) {
|
||||
// No looping for still images
|
||||
@@ -346,15 +346,15 @@ rational Footage::AdjustTimeByLoopMode(rational time, Decoder::LoopMode loop_mod
|
||||
|
||||
if (TimeIsOutOfBounds(time, length)) {
|
||||
switch (loop_mode) {
|
||||
case Decoder::kLoopModeOff:
|
||||
case LoopMode::kLoopModeOff:
|
||||
// Return no time to indicate no frame should be shown here
|
||||
time = rational::NaN;
|
||||
break;
|
||||
case Decoder::kLoopModeClamp:
|
||||
case LoopMode::kLoopModeClamp:
|
||||
// Clamp footage time to length
|
||||
time = clamp(time, rational(0), length - timebase);
|
||||
break;
|
||||
case Decoder::kLoopModeLoop:
|
||||
case LoopMode::kLoopModeLoop:
|
||||
// Loop footage time around job length
|
||||
do {
|
||||
if (time >= length) {
|
||||
|
||||
@@ -173,7 +173,7 @@ public:
|
||||
|
||||
virtual Node *GetConnectedSampleOutput() override;
|
||||
|
||||
static rational AdjustTimeByLoopMode(rational time, Decoder::LoopMode loop_mode, const rational& length, VideoParams::Type type, const rational &timebase);
|
||||
static rational AdjustTimeByLoopMode(rational time, LoopMode loop_mode, const rational& length, VideoParams::Type type, const rational &timebase);
|
||||
|
||||
virtual void LoadFinishedEvent() override;
|
||||
|
||||
|
||||
@@ -32,7 +32,7 @@ NodeValueDatabase NodeTraverser::GenerateDatabase(const Node* node, const TimeRa
|
||||
NodeValueDatabase database;
|
||||
|
||||
// HACK: Pick up loop mode from clips
|
||||
Decoder::LoopMode old_loop_mode = loop_mode_;
|
||||
LoopMode old_loop_mode = loop_mode_;
|
||||
if (const ClipBlock *clip = dynamic_cast<const ClipBlock*>(node)) {
|
||||
loop_mode_ = clip->loop_mode();
|
||||
}
|
||||
@@ -184,11 +184,6 @@ void NodeTraverser::Transform(QTransform *transform, const Node *start, const No
|
||||
transform_ = nullptr;
|
||||
}
|
||||
|
||||
NodeGlobals NodeTraverser::GenerateGlobals(const VideoParams &vparams, const AudioParams &aparams, const TimeRange &time)
|
||||
{
|
||||
return NodeGlobals(vparams, aparams, time);
|
||||
}
|
||||
|
||||
NodeValueTable NodeTraverser::ProcessInput(const Node* node, const QString& input, const TimeRange& range)
|
||||
{
|
||||
// If input is connected, retrieve value directly
|
||||
@@ -259,7 +254,7 @@ void NodeTraverser::ProcessInputElement(NodeValueTableArray &array_tbl, const No
|
||||
NodeTraverser::NodeTraverser() :
|
||||
cancel_(nullptr),
|
||||
transform_(nullptr),
|
||||
loop_mode_(Decoder::kLoopModeOff)
|
||||
loop_mode_(LoopMode::kLoopModeOff)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -309,7 +304,7 @@ NodeValueTable NodeTraverser::GenerateTable(const Node *n, const TimeRange& rang
|
||||
table = database.Merge();
|
||||
|
||||
// By this point, the node should have all the inputs it needs to render correctly
|
||||
NodeGlobals globals = GenerateGlobals(video_params_, audio_params_, range);
|
||||
NodeGlobals globals(video_params_, audio_params_, range, loop_mode_);
|
||||
n->Value(row, globals, &table);
|
||||
|
||||
// `transform_now_` is the next node in the path that needs to be traversed. It only ever goes
|
||||
@@ -430,7 +425,7 @@ void NodeTraverser::ResolveJobs(NodeValue &val)
|
||||
|
||||
} else if (FootageJob *fj = dynamic_cast<FootageJob*>(base_job)) {
|
||||
|
||||
rational footage_time = Footage::AdjustTimeByLoopMode(fj->time().in(), loop_mode_, fj->length(), fj->video_params().video_type(), fj->video_params().frame_rate_as_time_base());
|
||||
rational footage_time = Footage::AdjustTimeByLoopMode(fj->time().in(), fj->loop_mode(), fj->length(), fj->video_params().video_type(), fj->video_params().frame_rate_as_time_base());
|
||||
|
||||
TexturePtr tex;
|
||||
|
||||
|
||||
@@ -54,12 +54,6 @@ public:
|
||||
|
||||
void Transform(QTransform *transform, const Node *start, const Node *end, const TimeRange &range);
|
||||
|
||||
static NodeGlobals GenerateGlobals(const VideoParams &vparams, const AudioParams &aparams, const TimeRange &time);
|
||||
static NodeGlobals GenerateGlobals(const VideoParams &vparams, const AudioParams &aparams, const rational &time)
|
||||
{
|
||||
return GenerateGlobals(vparams, aparams, TimeRange(time, time + vparams.frame_rate_as_time_base()));
|
||||
}
|
||||
|
||||
const VideoParams& GetCacheVideoParams() const
|
||||
{
|
||||
return video_params_;
|
||||
@@ -144,7 +138,7 @@ protected:
|
||||
return block_stack_.empty() ? nullptr : block_stack_.back();
|
||||
}
|
||||
|
||||
Decoder::LoopMode loop_mode() const { return loop_mode_; }
|
||||
LoopMode loop_mode() const { return loop_mode_; }
|
||||
|
||||
virtual bool UseCache() const { return false; }
|
||||
|
||||
@@ -163,7 +157,7 @@ private:
|
||||
|
||||
std::list<Block*> block_stack_;
|
||||
|
||||
Decoder::LoopMode loop_mode_;
|
||||
LoopMode loop_mode_;
|
||||
|
||||
QHash<const Node*, QHash<TimeRange, NodeValueTable> > value_cache_;
|
||||
QHash<Texture*, TexturePtr> resolved_texture_cache_;
|
||||
|
||||
@@ -38,6 +38,7 @@ set(OLIVE_SOURCES
|
||||
render/framehashcache.h
|
||||
render/framemanager.cpp
|
||||
render/framemanager.h
|
||||
render/loopmode.h
|
||||
render/managedcolor.cpp
|
||||
render/managedcolor.h
|
||||
render/playbackcache.cpp
|
||||
|
||||
@@ -33,12 +33,13 @@ public:
|
||||
{
|
||||
}
|
||||
|
||||
FootageJob(const TimeRange &time, const QString& decoder, const QString& filename, Track::Type type, const rational& length) :
|
||||
FootageJob(const TimeRange &time, const QString& decoder, const QString& filename, Track::Type type, const rational& length, LoopMode loop_mode) :
|
||||
time_(time),
|
||||
decoder_(decoder),
|
||||
filename_(filename),
|
||||
type_(type),
|
||||
length_(length)
|
||||
length_(length),
|
||||
loop_mode_(loop_mode)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -99,6 +100,9 @@ public:
|
||||
|
||||
const TimeRange &time() const { return time_; }
|
||||
|
||||
LoopMode loop_mode() const { return loop_mode_; }
|
||||
void set_loop_mode(LoopMode m) { loop_mode_ = m; }
|
||||
|
||||
private:
|
||||
TimeRange time_;
|
||||
|
||||
@@ -116,6 +120,8 @@ private:
|
||||
|
||||
rational length_;
|
||||
|
||||
LoopMode loop_mode_;
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,14 @@
|
||||
#ifndef LOOPMODE_H
|
||||
#define LOOPMODE_H
|
||||
|
||||
namespace olive {
|
||||
|
||||
enum class LoopMode {
|
||||
kLoopModeOff,
|
||||
kLoopModeLoop,
|
||||
kLoopModeClamp
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif // LOOPMODE_H
|
||||
@@ -532,18 +532,18 @@ void TimelineView::DrawBlock(QPainter *painter, bool foreground, Block *block, q
|
||||
qreal zebra_right = TimeToScene(clip->in() - clip->media_in());
|
||||
|
||||
switch (clip->loop_mode()) {
|
||||
case Decoder::kLoopModeOff:
|
||||
case LoopMode::kLoopModeOff:
|
||||
// Draw stripes for sections of clip < 0
|
||||
if (zebra_right > GetTimelineLeftBound()) {
|
||||
DrawZebraStripes(painter, QRectF(block_left, block_top, zebra_right - block_left, block_height));
|
||||
}
|
||||
break;
|
||||
case Decoder::kLoopModeLoop:
|
||||
case LoopMode::kLoopModeLoop:
|
||||
for (qreal i=zebra_right; i>block_left; i-=TimeToScene(clip->connected_viewer()->GetLength())) {
|
||||
painter->drawLine(i, block_top, i, block_top + block_height);
|
||||
}
|
||||
break;
|
||||
case Decoder::kLoopModeClamp:
|
||||
case LoopMode::kLoopModeClamp:
|
||||
painter->drawLine(zebra_right, block_top, zebra_right, block_top + block_height);
|
||||
break;
|
||||
}
|
||||
@@ -552,18 +552,18 @@ void TimelineView::DrawBlock(QPainter *painter, bool foreground, Block *block, q
|
||||
if (clip->length() + clip->media_in() > clip->connected_viewer()->GetLength()) {
|
||||
qreal zebra_left = TimeToScene(clip->out() - (clip->media_in() + clip->length() - clip->connected_viewer()->GetLength()));
|
||||
switch (clip->loop_mode()) {
|
||||
case Decoder::kLoopModeOff:
|
||||
case LoopMode::kLoopModeOff:
|
||||
// Draw stripes for sections for clip > clip length
|
||||
if (zebra_left < GetTimelineRightBound()) {
|
||||
DrawZebraStripes(painter, QRectF(zebra_left, block_top, block_right - zebra_left, block_height));
|
||||
}
|
||||
break;
|
||||
case Decoder::kLoopModeLoop:
|
||||
case LoopMode::kLoopModeLoop:
|
||||
for (qreal i=zebra_left; i<block_right; i+=TimeToScene(clip->connected_viewer()->GetLength())) {
|
||||
painter->drawLine(i, block_top, i, block_top + block_height);
|
||||
}
|
||||
break;
|
||||
case Decoder::kLoopModeClamp:
|
||||
case LoopMode::kLoopModeClamp:
|
||||
painter->drawLine(zebra_left, block_top, zebra_left, block_top + block_height);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -380,15 +380,7 @@ void ViewerDisplayWidget::OnPaint()
|
||||
VideoParams device_params = GetViewportParams();
|
||||
|
||||
if (push_mode_ == kPushBlank) {
|
||||
if (blank_shader_.isNull()) {
|
||||
blank_shader_ = renderer()->CreateNativeShader(ShaderCode());
|
||||
}
|
||||
|
||||
ShaderJob job;
|
||||
job.Insert(QStringLiteral("ove_mvpmat"), NodeValue(NodeValue::kMatrix, combined_matrix_flipped_));
|
||||
job.Insert(QStringLiteral("ove_cropmatrix"), NodeValue(NodeValue::kMatrix, crop_matrix_));
|
||||
|
||||
renderer()->Blit(blank_shader_, job, device_params, false);
|
||||
DrawBlank(device_params);
|
||||
} else if (color_service()) {
|
||||
if (FramePtr frame = load_frame_.value<FramePtr>()) {
|
||||
// This is a CPU frame, upload it now
|
||||
@@ -415,35 +407,39 @@ void ViewerDisplayWidget::OnPaint()
|
||||
|
||||
TexturePtr texture_to_draw = texture_;
|
||||
|
||||
if (deinterlace_) {
|
||||
if (deinterlace_shader_.isNull()) {
|
||||
deinterlace_shader_ = renderer()->CreateNativeShader(ShaderCode(FileFunctions::ReadFileAsString(QStringLiteral(":/shaders/deinterlace.frag"))));
|
||||
if (!texture_to_draw || texture_to_draw->IsDummy()) {
|
||||
DrawBlank(device_params);
|
||||
} else {
|
||||
if (deinterlace_) {
|
||||
if (deinterlace_shader_.isNull()) {
|
||||
deinterlace_shader_ = renderer()->CreateNativeShader(ShaderCode(FileFunctions::ReadFileAsString(QStringLiteral(":/shaders/deinterlace.frag"))));
|
||||
}
|
||||
|
||||
if (!deinterlace_texture_
|
||||
|| deinterlace_texture_->params() != texture_to_draw->params()) {
|
||||
// (Re)create texture
|
||||
deinterlace_texture_ = renderer()->CreateTexture(texture_to_draw->params());
|
||||
}
|
||||
|
||||
ShaderJob job;
|
||||
job.Insert(QStringLiteral("resolution_in"), NodeValue(NodeValue::kVec2, QVector2D(texture_to_draw->width(), texture_to_draw->height())));
|
||||
job.Insert(QStringLiteral("ove_maintex"), NodeValue(NodeValue::kTexture, QVariant::fromValue(texture_to_draw)));
|
||||
|
||||
renderer()->BlitToTexture(deinterlace_shader_, job, deinterlace_texture_.get());
|
||||
|
||||
texture_to_draw = deinterlace_texture_;
|
||||
}
|
||||
|
||||
if (!deinterlace_texture_
|
||||
|| deinterlace_texture_->params() != texture_to_draw->params()) {
|
||||
// (Re)create texture
|
||||
deinterlace_texture_ = renderer()->CreateTexture(texture_to_draw->params());
|
||||
}
|
||||
ColorTransformJob ctj;
|
||||
ctj.SetColorProcessor(color_service());
|
||||
ctj.SetInputTexture(texture_to_draw);
|
||||
ctj.SetInputAlphaAssociation(OLIVE_CONFIG("ReassocLinToNonLin").toBool() ? kAlphaAssociated : kAlphaNone);
|
||||
ctj.SetClearDestinationEnabled(false);
|
||||
ctj.SetTransformMatrix(combined_matrix_flipped_);
|
||||
ctj.SetCropMatrix(crop_matrix_);
|
||||
|
||||
ShaderJob job;
|
||||
job.Insert(QStringLiteral("resolution_in"), NodeValue(NodeValue::kVec2, QVector2D(texture_to_draw->width(), texture_to_draw->height())));
|
||||
job.Insert(QStringLiteral("ove_maintex"), NodeValue(NodeValue::kTexture, QVariant::fromValue(texture_to_draw)));
|
||||
|
||||
renderer()->BlitToTexture(deinterlace_shader_, job, deinterlace_texture_.get());
|
||||
|
||||
texture_to_draw = deinterlace_texture_;
|
||||
renderer()->BlitColorManaged(ctj, device_params);
|
||||
}
|
||||
|
||||
ColorTransformJob ctj;
|
||||
ctj.SetColorProcessor(color_service());
|
||||
ctj.SetInputTexture(texture_to_draw);
|
||||
ctj.SetInputAlphaAssociation(OLIVE_CONFIG("ReassocLinToNonLin").toBool() ? kAlphaAssociated : kAlphaNone);
|
||||
ctj.SetClearDestinationEnabled(false);
|
||||
ctj.SetTransformMatrix(combined_matrix_flipped_);
|
||||
ctj.SetCropMatrix(crop_matrix_);
|
||||
|
||||
renderer()->BlitColorManaged(ctj, device_params);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -455,7 +451,7 @@ void ViewerDisplayWidget::OnPaint()
|
||||
|
||||
p.setWorldTransform(gizmo_last_draw_transform_);
|
||||
|
||||
gizmos_->UpdateGizmoPositions(gizmo_db_, NodeTraverser::GenerateGlobals(gizmo_params_, gizmo_audio_params_, gizmo_draw_time_));
|
||||
gizmos_->UpdateGizmoPositions(gizmo_db_, NodeGlobals(gizmo_params_, gizmo_audio_params_, gizmo_draw_time_, LoopMode::kLoopModeOff));
|
||||
foreach (NodeGizmo *gizmo, gizmos_->GetGizmos()) {
|
||||
if (gizmo->IsVisible()) {
|
||||
gizmo->Draw(&p);
|
||||
@@ -831,7 +827,7 @@ bool ViewerDisplayWidget::OnMousePress(QMouseEvent *event)
|
||||
// Handle gizmo click
|
||||
gizmo_start_drag_ = event->pos();
|
||||
gizmo_last_drag_ = gizmo_start_drag_;
|
||||
current_gizmo_->SetGlobals(NodeTraverser::GenerateGlobals(gizmo_params_, gizmo_audio_params_, GenerateGizmoTime()));
|
||||
current_gizmo_->SetGlobals(NodeGlobals(gizmo_params_, gizmo_audio_params_, GenerateGizmoTime(), LoopMode::kLoopModeOff));
|
||||
|
||||
} else {
|
||||
|
||||
@@ -1213,6 +1209,19 @@ void ViewerDisplayWidget::GenerateGizmoTransforms()
|
||||
gizmo_last_draw_transform_inverted_ = gizmo_last_draw_transform_.inverted();
|
||||
}
|
||||
|
||||
void ViewerDisplayWidget::DrawBlank(const VideoParams &device_params)
|
||||
{
|
||||
if (blank_shader_.isNull()) {
|
||||
blank_shader_ = renderer()->CreateNativeShader(ShaderCode());
|
||||
}
|
||||
|
||||
ShaderJob job;
|
||||
job.Insert(QStringLiteral("ove_mvpmat"), NodeValue(NodeValue::kMatrix, combined_matrix_flipped_));
|
||||
job.Insert(QStringLiteral("ove_cropmatrix"), NodeValue(NodeValue::kMatrix, crop_matrix_));
|
||||
|
||||
renderer()->Blit(blank_shader_, job, device_params, false);
|
||||
}
|
||||
|
||||
void ViewerDisplayWidget::SetShowFPS(bool e)
|
||||
{
|
||||
show_fps_ = e;
|
||||
|
||||
@@ -306,6 +306,8 @@ private:
|
||||
|
||||
void GenerateGizmoTransforms();
|
||||
|
||||
void DrawBlank(const VideoParams &device_params);
|
||||
|
||||
/**
|
||||
* @brief Internal reference to the OpenGL texture to draw. Set in SetTexture() and used in paintGL().
|
||||
*/
|
||||
|
||||
Reference in New Issue
Block a user