From d1bb9318547366db89eae148a684687f47b03da2 Mon Sep 17 00:00:00 2001 From: itsmattkc <34096995+itsmattkc@users.noreply.github.com> Date: Tue, 26 Apr 2022 14:23:19 -0700 Subject: [PATCH] nodeparamview: implemented add button --- app/node/audio/pan/pan.cpp | 3 ++ app/node/audio/volume/volume.cpp | 3 ++ app/node/block/clip/clip.cpp | 2 + .../cornerpin/cornerpindistortnode.cpp | 3 ++ app/node/distort/crop/cropdistortnode.cpp | 3 ++ app/node/distort/flip/flipdistortnode.cpp | 3 ++ .../transform/transformdistortnode.cpp | 3 ++ app/node/effect/opacity/opacityeffect.cpp | 3 ++ app/node/factory.cpp | 6 ++- app/node/factory.h | 2 +- app/node/filter/blur/blur.cpp | 3 ++ app/node/filter/mosaic/mosaicfilternode.cpp | 3 ++ app/node/filter/stroke/stroke.cpp | 3 ++ .../colordifferencekey/colordifferencekey.cpp | 6 ++- app/node/keying/despill/despill.cpp | 3 ++ app/node/node.cpp | 4 +- app/node/node.h | 23 +++++++++- .../nodeparamview/nodeparamviewcontext.cpp | 42 ++++++++++++++++++- .../nodeparamview/nodeparamviewcontext.h | 2 + 19 files changed, 114 insertions(+), 6 deletions(-) diff --git a/app/node/audio/pan/pan.cpp b/app/node/audio/pan/pan.cpp index 9eb8e0766..e6458bfaa 100644 --- a/app/node/audio/pan/pan.cpp +++ b/app/node/audio/pan/pan.cpp @@ -35,6 +35,9 @@ PanNode::PanNode() SetInputProperty(kPanningInput, QStringLiteral("min"), -1.0); SetInputProperty(kPanningInput, QStringLiteral("max"), 1.0); SetInputProperty(kPanningInput, QStringLiteral("view"), FloatSlider::kPercentage); + + SetFlags(kAudioEffect); + SetEffectInput(kSamplesInput); } Node *PanNode::copy() const diff --git a/app/node/audio/volume/volume.cpp b/app/node/audio/volume/volume.cpp index e6c26b50e..6617dcae3 100644 --- a/app/node/audio/volume/volume.cpp +++ b/app/node/audio/volume/volume.cpp @@ -34,6 +34,9 @@ VolumeNode::VolumeNode() AddInput(kVolumeInput, NodeValue::kFloat, 1.0); SetInputProperty(kVolumeInput, QStringLiteral("min"), 0.0); SetInputProperty(kVolumeInput, QStringLiteral("view"), FloatSlider::kDecibel); + + SetFlags(kAudioEffect); + SetEffectInput(kSamplesInput); } Node *VolumeNode::copy() const diff --git a/app/node/block/clip/clip.cpp b/app/node/block/clip/clip.cpp index 4e5cfdb81..f5afb79fa 100644 --- a/app/node/block/clip/clip.cpp +++ b/app/node/block/clip/clip.cpp @@ -57,6 +57,8 @@ ClipBlock::ClipBlock() : PrependInput(kBufferIn, NodeValue::kNone, InputFlags(kInputFlagNotKeyframable)); SetValueHintForInput(kBufferIn, ValueHint(NodeValue::kBuffer)); + + SetEffectInput(kBufferIn); } Node *ClipBlock::copy() const diff --git a/app/node/distort/cornerpin/cornerpindistortnode.cpp b/app/node/distort/cornerpin/cornerpindistortnode.cpp index e4429ede7..54c5870da 100644 --- a/app/node/distort/cornerpin/cornerpindistortnode.cpp +++ b/app/node/distort/cornerpin/cornerpindistortnode.cpp @@ -48,6 +48,9 @@ CornerPinDistortNode::CornerPinDistortNode() gizmo_resize_handle_[1] = AddDraggableGizmo({NodeKeyframeTrackReference(NodeInput(this, kTopRightInput), 0), NodeKeyframeTrackReference(NodeInput(this, kTopRightInput), 1)}); gizmo_resize_handle_[2] = AddDraggableGizmo({NodeKeyframeTrackReference(NodeInput(this, kBottomRightInput), 0), NodeKeyframeTrackReference(NodeInput(this, kBottomRightInput), 1)}); gizmo_resize_handle_[3] = AddDraggableGizmo({NodeKeyframeTrackReference(NodeInput(this, kBottomLeftInput), 0), NodeKeyframeTrackReference(NodeInput(this, kBottomLeftInput), 1)}); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } void CornerPinDistortNode::Retranslate() diff --git a/app/node/distort/crop/cropdistortnode.cpp b/app/node/distort/crop/cropdistortnode.cpp index b204c7eda..e60b9afe3 100644 --- a/app/node/distort/crop/cropdistortnode.cpp +++ b/app/node/distort/crop/cropdistortnode.cpp @@ -56,6 +56,9 @@ CropDistortNode::CropDistortNode() point_gizmo_[kGizmoScaleBottomRight] = AddDraggableGizmo({kRightInput, kBottomInput}); point_gizmo_[kGizmoScaleCenterLeft] = AddDraggableGizmo({kLeftInput}); point_gizmo_[kGizmoScaleCenterRight] = AddDraggableGizmo({kRightInput}); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } void CropDistortNode::Retranslate() diff --git a/app/node/distort/flip/flipdistortnode.cpp b/app/node/distort/flip/flipdistortnode.cpp index 577437fe5..3bc78536d 100644 --- a/app/node/distort/flip/flipdistortnode.cpp +++ b/app/node/distort/flip/flipdistortnode.cpp @@ -33,6 +33,9 @@ FlipDistortNode::FlipDistortNode() AddInput(kHorizontalInput, NodeValue::kBoolean, false); AddInput(kVerticalInput, NodeValue::kBoolean, false); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } Node* FlipDistortNode::copy() const diff --git a/app/node/distort/transform/transformdistortnode.cpp b/app/node/distort/transform/transformdistortnode.cpp index 59ec09bc2..0f2bcfac2 100644 --- a/app/node/distort/transform/transformdistortnode.cpp +++ b/app/node/distort/transform/transformdistortnode.cpp @@ -64,6 +64,9 @@ TransformDistortNode::TransformDistortNode() point_gizmo_[i]->AddInput(NodeKeyframeTrackReference(NodeInput(this, kScaleInput), 1)); point_gizmo_[i]->SetDragValueBehavior(PointGizmo::kAbsolute); } + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } void TransformDistortNode::Retranslate() diff --git a/app/node/effect/opacity/opacityeffect.cpp b/app/node/effect/opacity/opacityeffect.cpp index b8ac2d017..b4dcba646 100644 --- a/app/node/effect/opacity/opacityeffect.cpp +++ b/app/node/effect/opacity/opacityeffect.cpp @@ -24,6 +24,9 @@ OpacityEffect::OpacityEffect() SetInputProperty(kValueInput, QStringLiteral("view"), FloatSlider::kPercentage); SetInputProperty(kValueInput, QStringLiteral("min"), 0.0); SetInputProperty(kValueInput, QStringLiteral("max"), 1.0); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } void OpacityEffect::Retranslate() diff --git a/app/node/factory.cpp b/app/node/factory.cpp index 3f32fe17a..cf5e3b0c4 100644 --- a/app/node/factory.cpp +++ b/app/node/factory.cpp @@ -86,7 +86,7 @@ void NodeFactory::Destroy() library_.clear(); } -Menu *NodeFactory::CreateMenu(QWidget* parent, bool create_none_item, Node::CategoryID restrict_to) +Menu *NodeFactory::CreateMenu(QWidget* parent, bool create_none_item, Node::CategoryID restrict_to, uint64_t restrict_flags) { Menu* menu = new Menu(parent); menu->setToolTipsVisible(true); @@ -99,6 +99,10 @@ Menu *NodeFactory::CreateMenu(QWidget* parent, bool create_none_item, Node::Cate continue; } + if (restrict_flags && !(n->GetFlags() & restrict_flags)) { + continue; + } + if (hidden_.contains(i)) { // Skip this node continue; diff --git a/app/node/factory.h b/app/node/factory.h index 0a461892f..56192cc7b 100644 --- a/app/node/factory.h +++ b/app/node/factory.h @@ -81,7 +81,7 @@ public: static void Destroy(); - static Menu* CreateMenu(QWidget *parent, bool create_none_item = false, Node::CategoryID restrict_to = Node::kCategoryUnknown); + static Menu* CreateMenu(QWidget *parent, bool create_none_item = false, Node::CategoryID restrict_to = Node::kCategoryUnknown, uint64_t restrict_flags = 0); static Node* CreateFromMenuAction(QAction* action); diff --git a/app/node/filter/blur/blur.cpp b/app/node/filter/blur/blur.cpp index c488b8008..aa159dcce 100644 --- a/app/node/filter/blur/blur.cpp +++ b/app/node/filter/blur/blur.cpp @@ -43,6 +43,9 @@ BlurFilterNode::BlurFilterNode() AddInput(kVertInput, NodeValue::kBoolean, true); AddInput(kRepeatEdgePixelsInput, NodeValue::kBoolean, true); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } Node *BlurFilterNode::copy() const diff --git a/app/node/filter/mosaic/mosaicfilternode.cpp b/app/node/filter/mosaic/mosaicfilternode.cpp index 242d5682f..0dc562218 100644 --- a/app/node/filter/mosaic/mosaicfilternode.cpp +++ b/app/node/filter/mosaic/mosaicfilternode.cpp @@ -35,6 +35,9 @@ MosaicFilterNode::MosaicFilterNode() AddInput(kVertInput, NodeValue::kFloat, 18.0); SetInputProperty(kVertInput, QStringLiteral("min"), 1.0); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } void MosaicFilterNode::Retranslate() diff --git a/app/node/filter/stroke/stroke.cpp b/app/node/filter/stroke/stroke.cpp index 7818d7e46..d6e784146 100644 --- a/app/node/filter/stroke/stroke.cpp +++ b/app/node/filter/stroke/stroke.cpp @@ -46,6 +46,9 @@ StrokeFilterNode::StrokeFilterNode() SetInputProperty(kOpacityInput, QStringLiteral("max"), 1.0f); AddInput(kInnerInput, NodeValue::kBoolean, false); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } Node *StrokeFilterNode::copy() const diff --git a/app/node/keying/colordifferencekey/colordifferencekey.cpp b/app/node/keying/colordifferencekey/colordifferencekey.cpp index 1f2ca4d1c..a805ab550 100644 --- a/app/node/keying/colordifferencekey/colordifferencekey.cpp +++ b/app/node/keying/colordifferencekey/colordifferencekey.cpp @@ -25,7 +25,8 @@ const QString ColorDifferenceKeyNode::kShadowsInput = QStringLiteral("shadows_in const QString ColorDifferenceKeyNode::kHighlightsInput = QStringLiteral("highlights_in"); const QString ColorDifferenceKeyNode::kMaskOnlyInput = QStringLiteral("mask_only_in"); -ColorDifferenceKeyNode::ColorDifferenceKeyNode() { +ColorDifferenceKeyNode::ColorDifferenceKeyNode() +{ AddInput(kTextureInput, NodeValue::kTexture, InputFlags(kInputFlagNotKeyframable)); AddInput(kGarbageMatteInput, NodeValue::kTexture, InputFlags(kInputFlagNotKeyframable)); @@ -41,6 +42,9 @@ ColorDifferenceKeyNode::ColorDifferenceKeyNode() { SetInputProperty(kShadowsInput, QStringLiteral("min"), 0.0); AddInput(kMaskOnlyInput, NodeValue::kBoolean, false); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } Node *ColorDifferenceKeyNode::copy() const diff --git a/app/node/keying/despill/despill.cpp b/app/node/keying/despill/despill.cpp index 147ee60df..09a8f2f45 100644 --- a/app/node/keying/despill/despill.cpp +++ b/app/node/keying/despill/despill.cpp @@ -33,6 +33,9 @@ DespillNode::DespillNode() AddInput(kMethodInput, NodeValue::kCombo, 0); AddInput(kPreserveLuminanceInput, NodeValue::kBoolean, false); + + SetFlags(kVideoEffect); + SetEffectInput(kTextureInput); } Node* DespillNode::copy() const diff --git a/app/node/node.cpp b/app/node/node.cpp index c8afb1f12..b0a7ec8aa 100644 --- a/app/node/node.cpp +++ b/app/node/node.cpp @@ -48,7 +48,9 @@ Node::Node() : folder_(nullptr), operation_stack_(0), cache_result_(false), - flags_(kNone) + flags_(kNone), + effect_element_(-1), + bypass_(false) { } diff --git a/app/node/node.h b/app/node/node.h index 6d2c27144..66b5497fe 100644 --- a/app/node/node.h +++ b/app/node/node.h @@ -95,7 +95,9 @@ public: enum Flag { kNone = 0, - kDontShowInParamView = 0x1 + kDontShowInParamView = 0x1, + kVideoEffect = 0x2, + kAudioEffect = 0x4 }; Node(); @@ -539,6 +541,11 @@ public: int InputArraySize(const QString& id) const; + NodeInput GetEffectInput() + { + return effect_input_.isEmpty() ? NodeInput() : NodeInput(this, effect_input_, effect_element_); + } + class ValueHint { public: explicit ValueHint(const QVector &types = QVector(), int index = -1, const QString &tag = QString()) : @@ -889,6 +896,9 @@ public: cache_result_ = e; } + bool IsBypassed() const { return bypass_; } + void SetBypassed(bool e) { bypass_ = e; } + class ArrayRemoveCommand : public UndoCommand { public: @@ -1027,6 +1037,12 @@ protected: virtual void childEvent(QChildEvent *event) override; + void SetEffectInput(const QString &input, int element = -1) + { + effect_input_ = input; + effect_element_ = element; + } + void SetToolTip(const QString& s) { tooltip_ = s; @@ -1342,6 +1358,11 @@ private: QVector gizmos_; + QString effect_input_; + int effect_element_; + + bool bypass_; + private slots: /** * @brief Slot when a keyframe's time changes to keep the keyframes correctly sorted by time diff --git a/app/widget/nodeparamview/nodeparamviewcontext.cpp b/app/widget/nodeparamview/nodeparamviewcontext.cpp index a07c3975b..8fe70ca7a 100644 --- a/app/widget/nodeparamview/nodeparamviewcontext.cpp +++ b/app/widget/nodeparamview/nodeparamviewcontext.cpp @@ -23,6 +23,8 @@ #include #include "node/block/clip/clip.h" +#include "node/factory.h" +#include "widget/nodeview/nodeviewundo.h" namespace olive { @@ -130,7 +132,45 @@ void NodeParamViewContext::Retranslate() void NodeParamViewContext::AddEffectButtonClicked() { - QMessageBox::information(this, tr("STUB"), tr("This feature is coming soon. Thanks for testing development builds of Olive :)")); + Menu *m = NodeFactory::CreateMenu(this, false, Node::kCategoryUnknown, Node::kVideoEffect); + connect(m, &Menu::triggered, this, &NodeParamViewContext::AddEffectMenuItemTriggered); + m->exec(QCursor::pos()); + delete m; +} + +void NodeParamViewContext::AddEffectMenuItemTriggered(QAction *a) +{ + Node *n = NodeFactory::CreateFromMenuAction(a); + + if (n) { + NodeInput new_node_input = n->GetEffectInput(); + MultiUndoCommand *command = new MultiUndoCommand(); + + QVector graphs_added_to; + + foreach (Node *ctx, contexts_) { + NodeInput ctx_input = ctx->GetEffectInput(); + + if (!graphs_added_to.contains(ctx->parent())) { + command->add_child(new NodeAddCommand(ctx->parent(), n)); + graphs_added_to.append(ctx->parent()); + } + + command->add_child(new NodeSetPositionCommand(n, ctx, ctx->GetNodePositionInContext(ctx))); + command->add_child(new NodeSetPositionCommand(ctx, ctx, ctx->GetNodePositionInContext(ctx) + QPointF(1, 0))); + + if (ctx_input.IsConnected()) { + Node *prev_output = ctx_input.GetConnectedOutput(); + + command->add_child(new NodeEdgeRemoveCommand(prev_output, ctx_input)); + command->add_child(new NodeEdgeAddCommand(prev_output, new_node_input)); + } + + command->add_child(new NodeEdgeAddCommand(n, ctx_input)); + } + + Core::instance()->undo_stack()->pushIfHasChildren(command); + } } } diff --git a/app/widget/nodeparamview/nodeparamviewcontext.h b/app/widget/nodeparamview/nodeparamviewcontext.h index 5652277e9..29be6dd58 100644 --- a/app/widget/nodeparamview/nodeparamviewcontext.h +++ b/app/widget/nodeparamview/nodeparamviewcontext.h @@ -91,6 +91,8 @@ private: private slots: void AddEffectButtonClicked(); + void AddEffectMenuItemTriggered(QAction *a); + }; }