diff --git a/app/widget/nodeview/nodeview.cpp b/app/widget/nodeview/nodeview.cpp index 7168c4f23..624ced728 100644 --- a/app/widget/nodeview/nodeview.cpp +++ b/app/widget/nodeview/nodeview.cpp @@ -505,8 +505,11 @@ void NodeView::mousePressEvent(QMouseEvent *event) if (HandPress(event)) return; if (event->button() == Qt::LeftButton) { + // See if we're dragging the arrow of an edge + QPointF scene_pt = mapToScene(event->pos()); + foreach (NodeViewEdge *edge_item, scene_.edges()) { - if (edge_item->arrow_bounding_rect().contains(mapToScene(event->pos()))) { + if (edge_item->arrow_bounding_rect().contains(scene_pt)) { create_edge_src_ = scene_.NodeToUIObject(edge_item->output().node()); create_edge_src_output_ = edge_item->output().output(); create_edge_ = edge_item; @@ -514,6 +517,14 @@ void NodeView::mousePressEvent(QMouseEvent *event) return; } } + + // See if we're dragging the arrow of a node + foreach (NodeViewItem *node_item, scene_.item_map()) { + if (node_item->GetOutputTriangle().boundingRect().translated(node_item->pos()).contains(scene_pt)) { + CreateNewEdge(node_item); + return; + } + } } QGraphicsItem* item = itemAt(event->pos()); @@ -535,15 +546,7 @@ void NodeView::mousePressEvent(QMouseEvent *event) if (event->modifiers() & Qt::ControlModifier) { NodeViewItem* node_item = dynamic_cast(item); if (node_item) { - create_edge_ = new NodeViewEdge(); - create_edge_src_ = node_item; - create_edge_src_output_ = Node::kDefaultOutput; - create_edge_already_exists_ = false; - - create_edge_->SetCurved(scene_.GetEdgesAreCurved()); - create_edge_->SetFlowDirection(scene_.GetFlowDirection()); - - scene_.addItem(create_edge_); + CreateNewEdge(node_item); return; } } @@ -1501,6 +1504,19 @@ Menu *NodeView::CreateAddMenu(Menu *parent) return add_menu; } +void NodeView::CreateNewEdge(NodeViewItem *output_item) +{ + create_edge_ = new NodeViewEdge(); + create_edge_src_ = output_item; + create_edge_src_output_ = Node::kDefaultOutput; + create_edge_already_exists_ = false; + + create_edge_->SetCurved(scene_.GetEdgesAreCurved()); + create_edge_->SetFlowDirection(scene_.GetFlowDirection()); + + scene_.addItem(create_edge_); +} + NodeView::NodeViewAttachNodesToCursor::NodeViewAttachNodesToCursor(NodeView *view, const QVector &nodes) : view_(view), nodes_(nodes) diff --git a/app/widget/nodeview/nodeview.h b/app/widget/nodeview/nodeview.h index 5fccd9b54..4eff25c02 100644 --- a/app/widget/nodeview/nodeview.h +++ b/app/widget/nodeview/nodeview.h @@ -136,6 +136,8 @@ private: Menu *CreateAddMenu(Menu *parent); + void CreateNewEdge(NodeViewItem *output_item); + class NodeViewAttachNodesToCursor : public UndoCommand { public: diff --git a/app/widget/nodeview/nodeviewitem.cpp b/app/widget/nodeview/nodeviewitem.cpp index 7978d6c32..0b53720e4 100644 --- a/app/widget/nodeview/nodeviewitem.cpp +++ b/app/widget/nodeview/nodeviewitem.cpp @@ -65,6 +65,8 @@ NodeViewItem::NodeViewItem(QGraphicsItem *parent) : title_bar_rect_ = QRectF(-widget_width/2, -widget_height/2, widget_width, widget_height); setRect(title_bar_rect_); + + output_triangle_.resize(3); } QPointF NodeViewItem::GetNodePosition() const @@ -341,6 +343,41 @@ void NodeViewItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *opti painter->setBrush(Qt::NoBrush); painter->drawRect(rect()); + + // Draw output triangle + painter->setPen(Qt::NoPen); + painter->setBrush(app_pal.color(QPalette::Text)); + int triangle_sz = qMin(rect().width(), rect().height()) / 2; + int triangle_sz_half = triangle_sz / 2; + + switch (flow_dir_) { + case NodeViewCommon::kLeftToRight: + // Triangle pointing right + output_triangle_[0] = QPointF(rect().right(), rect().center().y() - triangle_sz_half); + output_triangle_[1] = QPointF(rect().right() + triangle_sz_half, rect().center().y()); + output_triangle_[2] = QPointF(rect().right(), rect().center().y() + triangle_sz_half); + break; + case NodeViewCommon::kTopToBottom: + // Triangle pointing down + output_triangle_[0] = QPointF(rect().center().x() - triangle_sz_half, rect().bottom()); + output_triangle_[1] = QPointF(rect().center().x(), rect().bottom() + triangle_sz_half); + output_triangle_[2] = QPointF(rect().center().x() + triangle_sz_half, rect().bottom()); + break; + case NodeViewCommon::kBottomToTop: + // Triangle pointing up + output_triangle_[0] = QPointF(rect().center().x() - triangle_sz_half, rect().top()); + output_triangle_[1] = QPointF(rect().center().x(), rect().top() - triangle_sz_half); + output_triangle_[2] = QPointF(rect().center().x() + triangle_sz_half, rect().top()); + break; + case NodeViewCommon::kRightToLeft: + // Triangle pointing left + output_triangle_[0] = QPointF(rect().left(), rect().center().y() - triangle_sz_half); + output_triangle_[1] = QPointF(rect().left() - triangle_sz_half, rect().center().y()); + output_triangle_[2] = QPointF(rect().left(), rect().center().y() + triangle_sz_half); + break; + } + + painter->drawPolygon(output_triangle_); } void NodeViewItem::mousePressEvent(QGraphicsSceneMouseEvent *event) diff --git a/app/widget/nodeview/nodeviewitem.h b/app/widget/nodeview/nodeviewitem.h index ffe3e0859..a7a6854f0 100644 --- a/app/widget/nodeview/nodeviewitem.h +++ b/app/widget/nodeview/nodeviewitem.h @@ -125,6 +125,11 @@ public: return prevent_removing_; } + const QPolygonF &GetOutputTriangle() const + { + return output_triangle_; + } + protected: virtual void paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget = nullptr) override; @@ -190,6 +195,8 @@ private: bool prevent_removing_; + QPolygonF output_triangle_; + }; }