From 1b156600aac2e42942bf1772b9c418d155061fc4 Mon Sep 17 00:00:00 2001 From: Ivan Yossi Date: Tue, 16 Apr 2019 18:33:08 -0500 Subject: [PATCH 1/4] Enable Shift + Click to show only current layer Differential Revision: https://phabricator.kde.org/D20591 BUG:376086 --- plugins/dockers/layerdocker/NodeDelegate.cpp | 214 ++++++++++++++----- 1 file changed, 159 insertions(+), 55 deletions(-) diff --git a/plugins/dockers/layerdocker/NodeDelegate.cpp b/plugins/dockers/layerdocker/NodeDelegate.cpp index 90ec1eec41..d508020342 100644 --- a/plugins/dockers/layerdocker/NodeDelegate.cpp +++ b/plugins/dockers/layerdocker/NodeDelegate.cpp @@ -65,7 +65,16 @@ public: OptionalProperty findProperty(KisBaseNode::PropertyList &props, const OptionalProperty &refProp) const; OptionalProperty findVisibilityProperty(KisBaseNode::PropertyList &props) const; - void toggleProperty(KisBaseNode::PropertyList &props, OptionalProperty prop, bool controlPressed, const QModelIndex &index); + void toggleProperty(KisBaseNode::PropertyList &props, OptionalProperty prop, const Qt::KeyboardModifiers modifier, const QModelIndex &index); + void togglePropertyRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty, const QList &items, bool record, bool mode); + + bool stasisIsDirty(const QModelIndex &root, const OptionalProperty &clickedProperty, bool on = false, bool off = false); + void resetPropertyStateRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty); + + void getParentsIndex(QList &items, const QModelIndex &index); + void getChildrenIndex(QList &items, const QModelIndex &index); + void getSiblingsIndex(QList &items, const QModelIndex &index); + }; NodeDelegate::NodeDelegate(NodeView *view, QObject *parent) @@ -480,6 +489,151 @@ OptionalProperty NodeDelegate::Private::findVisibilityProperty(KisBaseNode::Prop return 0; } +void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, OptionalProperty clickedProperty, const Qt::KeyboardModifiers modifier, const QModelIndex &index) +{ + QModelIndex root(view->rootIndex()); + + if ((modifier & Qt::ShiftModifier) == Qt::ShiftModifier && clickedProperty->canHaveStasis) { + if(stasisIsDirty(root, clickedProperty)){ // clean inStasis if mixed! + resetPropertyStateRecursive(root, clickedProperty); + } + KisBaseNode::PropertyList props = index.data(KisNodeModel::PropertiesRole).value(); + OptionalProperty prop = findProperty(props, clickedProperty); + + bool mode = true; + bool record = prop->isInStasis; + QList items; + + if(modifier == (Qt::ControlModifier | Qt::ShiftModifier)) { + mode = false; // inverted mode + items.insert(0, index); // important! + getSiblingsIndex(items, index); + } else { + getParentsIndex(items, index); + getChildrenIndex(items, index); + } + togglePropertyRecursive(root, clickedProperty, items, record, mode); + + } else { + resetPropertyStateRecursive(root, clickedProperty); + clickedProperty->state = !clickedProperty->state.toBool(); + view->model()->setData(index, QVariant::fromValue(props), KisNodeModel::PropertiesRole); + } +} + +void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty, const QList &items, bool record, bool mode) +{ + int rowCount = view->model()->rowCount(root); + + for (int i = 0; i < rowCount; i++) { + QModelIndex idx = view->model()->index(i, 0, root); + + // The entire property list has to be altered because model->setData cannot set individual properties + KisBaseNode::PropertyList props = idx.data(KisNodeModel::PropertiesRole).value(); + OptionalProperty prop = findProperty(props, clickedProperty); + + if (!prop) continue; + if (record){ // record + prop->stateInStasis = prop->state.toBool(); + prop->isInStasis = false; + if(mode) { //include mode + prop->state = (items.contains(idx))? QVariant(true) : QVariant(false); + } else { // exclude + prop->state = (!items.contains(idx))? prop->state : + (items.at(0) == idx)? QVariant(true) : QVariant(false); + } + } else { // recover + prop->state = QVariant(prop->stateInStasis); + prop->isInStasis = true; + } + view->model()->setData(idx, QVariant::fromValue(props), KisNodeModel::PropertiesRole); + + togglePropertyRecursive(idx,clickedProperty, items, record, mode); + } +} + +bool NodeDelegate::Private::stasisIsDirty(const QModelIndex &root, const OptionalProperty &clickedProperty, bool on, bool off) +{ + + int rowCount = view->model()->rowCount(root); + bool result = false; + + for (int i = 0; i < rowCount; i++) { + if (result) break; // return on first find + QModelIndex idx = view->model()->index(i, 0, root); + // The entire property list has to be altered because model->setData cannot set individual properties + KisBaseNode::PropertyList props = idx.data(KisNodeModel::PropertiesRole).value(); + OptionalProperty prop = findProperty(props, clickedProperty); + + if (!prop) continue; + if(prop->isInStasis) { + on = true; + } else { + off = true; + } + // stop if both states exist + if (on && off) { + return true; + } + + result = stasisIsDirty(idx,clickedProperty, on, off); + } + return result; +} + +void NodeDelegate::Private::resetPropertyStateRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty) +{ + if (!clickedProperty->canHaveStasis) return; + int rowCount = view->model()->rowCount(root); + + for (int i = 0; i < rowCount; i++) { + QModelIndex idx = view->model()->index(i, 0, root); + // The entire property list has to be altered because model->setData cannot set individual properties + KisBaseNode::PropertyList props = idx.data(KisNodeModel::PropertiesRole).value(); + OptionalProperty prop = findProperty(props, clickedProperty); + + if (!prop) continue; + prop->stateInStasis = prop->state.toBool(); + prop->isInStasis = true; + view->model()->setData(idx, QVariant::fromValue(props), KisNodeModel::PropertiesRole); + + resetPropertyStateRecursive(idx,clickedProperty); + } +} + +void NodeDelegate::Private::getParentsIndex(QList &items, const QModelIndex &index) +{ + if(!index.isValid()) return; + items.append(index); + getParentsIndex(items, index.parent()); +} + +void NodeDelegate::Private::getChildrenIndex(QList &items, const QModelIndex &index) +{ + qint32 childs = view->model()->rowCount(index); + QModelIndex child; + // STEP 1: Go. + for (quint16 i = 0; i < childs; ++i) { + child = view->model()->index(i, 0, index); + items.append(child); + getChildrenIndex(items, child); + } +} + +void NodeDelegate::Private::getSiblingsIndex(QList &items, const QModelIndex &index) +{ + qint32 numberOfLeaves = view->model()->rowCount(index.parent()); + QModelIndex item; + // STEP 1: Go. + for (quint16 i = 0; i < numberOfLeaves; ++i) { + item = view->model()->index(i, 0, index.parent()); + if (item != index) { + items.append(item); + } + } +} + + void NodeDelegate::drawIcons(QPainter *p, const QStyleOptionViewItem &option, const QModelIndex &index) const { KisNodeViewColorScheme scm; @@ -660,58 +814,6 @@ void NodeDelegate::drawExpandButton(QPainter *p, const QStyleOptionViewItem &opt p->drawPixmap(rc.bottomLeft()-QPoint(0, scm.decorationSize()-1), pixmap); } -void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, OptionalProperty clickedProperty, bool controlPressed, const QModelIndex &index) -{ - QAbstractItemModel *model = view->model(); - - // Using Ctrl+click to enter stasis - if (controlPressed && clickedProperty->canHaveStasis) { - // STEP 0: Prepare to Enter or Leave control key stasis - quint16 numberOfLeaves = model->rowCount(index.parent()); - QModelIndex eachItem; - // STEP 1: Go. - if (clickedProperty->isInStasis == false) { // Enter - /* Make every leaf of this node go State = False, saving the old property value to stateInStasis */ - for (quint16 i = 0; i < numberOfLeaves; ++i) { // Foreach leaf in the node (index.parent()) - eachItem = model->index(i, 1, index.parent()); - // The entire property list has to be altered because model->setData cannot set individual properties - KisBaseNode::PropertyList eachPropertyList = eachItem.data(KisNodeModel::PropertiesRole).value(); - OptionalProperty prop = findProperty(eachPropertyList, clickedProperty); - if (!prop) continue; - prop->stateInStasis = prop->state.toBool(); - prop->state = eachItem == index; - prop->isInStasis = true; - model->setData(eachItem, QVariant::fromValue(eachPropertyList), KisNodeModel::PropertiesRole); - - } - - for (quint16 i = 0; i < numberOfLeaves; ++i) { // Foreach leaf in the node (index.parent()) - eachItem = model->index(i, 1, index.parent()); - KisBaseNode::PropertyList eachPropertyList = eachItem.data(KisNodeModel::PropertiesRole).value(); - OptionalProperty prop = findProperty(eachPropertyList, clickedProperty); - if (!prop) continue; - } - } else { // Leave - /* Make every leaf of this node go State = stateInStasis */ - for (quint16 i = 0; i < numberOfLeaves; ++i) { - eachItem = model->index(i, 1, index.parent()); - // The entire property list has to be altered because model->setData cannot set individual properties - KisBaseNode::PropertyList eachPropertyList = eachItem.data(KisNodeModel::PropertiesRole).value(); - OptionalProperty prop = findProperty(eachPropertyList, clickedProperty); - if (!prop) continue; - - prop->state = prop->stateInStasis; - prop->isInStasis = false; - model->setData(eachItem, QVariant::fromValue(eachPropertyList), KisNodeModel::PropertiesRole); - } - } - } else { - clickedProperty->state = !clickedProperty->state.toBool(); - model->setData(index, QVariant::fromValue(props), KisNodeModel::PropertiesRole); - } -} - - bool NodeDelegate::editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index) { KisNodeViewColorScheme scm; @@ -773,14 +875,16 @@ bool NodeDelegate::editorEvent(QEvent *event, QAbstractItemModel *model, const Q OptionalProperty clickedProperty = realProps[clickedIcon]; if (!clickedProperty) return false; - d->toggleProperty(props, clickedProperty, mouseEvent->modifiers() == Qt::ControlModifier, index); + d->toggleProperty(props, clickedProperty, mouseEvent->modifiers(), index); return true; } } else if (leftButton && visibilityClicked) { KisBaseNode::PropertyList props = index.data(KisNodeModel::PropertiesRole).value(); OptionalProperty clickedProperty = d->findVisibilityProperty(props); if (!clickedProperty) return false; - d->toggleProperty(props, clickedProperty, mouseEvent->modifiers() == Qt::ControlModifier, index); + + d->toggleProperty(props, clickedProperty, mouseEvent->modifiers(), index); + return true; } else if (leftButton && decorationClicked) { bool isExpandable = model->hasChildren(index); -- GitLab From 66cdfabc7a684b1d9760f9a6528834e3511e36dd Mon Sep 17 00:00:00 2001 From: Ivan Yossi Date: Tue, 23 Apr 2019 18:36:48 -0500 Subject: [PATCH 2/4] Fix no isInState on creation and copy This allows shift + Click rely on node isInStasis property to have allow a saved previous state operation TODO: pick a suitable visual cur for "inStasis" mode --- libs/image/kis_base_node.h | 4 +-- plugins/dockers/layerdocker/NodeDelegate.cpp | 33 ++++++++++++++------ 2 files changed, 25 insertions(+), 12 deletions(-) diff --git a/libs/image/kis_base_node.h b/libs/image/kis_base_node.h index 9d1df1d164..02bf1bcb61 100644 --- a/libs/image/kis_base_node.h +++ b/libs/image/kis_base_node.h @@ -85,14 +85,14 @@ public: bool canHaveStasis; /** If the property isMutable and canHaveStasis, indicate whether it is in stasis or not */ - bool isInStasis; + bool isInStasis = false; /** If the property isMutable and canHaveStasis, provide this value to store the property's state while in stasis */ bool stateInStasis; bool operator==(const Property &rhs) const { - return rhs.name == name && rhs.state == state; + return rhs.name == name && rhs.state == state && rhs.isInStasis == false; } Property(): isMutable( false ) { } diff --git a/plugins/dockers/layerdocker/NodeDelegate.cpp b/plugins/dockers/layerdocker/NodeDelegate.cpp index d508020342..a9829a9207 100644 --- a/plugins/dockers/layerdocker/NodeDelegate.cpp +++ b/plugins/dockers/layerdocker/NodeDelegate.cpp @@ -36,6 +36,7 @@ #include #include #include +#include #include #include "kis_node_view_color_scheme.h" @@ -494,14 +495,14 @@ void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, Opt QModelIndex root(view->rootIndex()); if ((modifier & Qt::ShiftModifier) == Qt::ShiftModifier && clickedProperty->canHaveStasis) { - if(stasisIsDirty(root, clickedProperty)){ // clean inStasis if mixed! - resetPropertyStateRecursive(root, clickedProperty); - } +// if(stasisIsDirty(root, clickedProperty)){ // clean inStasis if mixed! +// resetPropertyStateRecursive(root, clickedProperty); +// } KisBaseNode::PropertyList props = index.data(KisNodeModel::PropertiesRole).value(); OptionalProperty prop = findProperty(props, clickedProperty); bool mode = true; - bool record = prop->isInStasis; + bool record = !prop->isInStasis; QList items; if(modifier == (Qt::ControlModifier | Qt::ShiftModifier)) { @@ -517,6 +518,7 @@ void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, Opt } else { resetPropertyStateRecursive(root, clickedProperty); clickedProperty->state = !clickedProperty->state.toBool(); + clickedProperty->isInStasis = false; view->model()->setData(index, QVariant::fromValue(props), KisNodeModel::PropertiesRole); } } @@ -535,7 +537,7 @@ void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, con if (!prop) continue; if (record){ // record prop->stateInStasis = prop->state.toBool(); - prop->isInStasis = false; + prop->isInStasis = true; if(mode) { //include mode prop->state = (items.contains(idx))? QVariant(true) : QVariant(false); } else { // exclude @@ -544,7 +546,7 @@ void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, con } } else { // recover prop->state = QVariant(prop->stateInStasis); - prop->isInStasis = true; + prop->isInStasis = false; } view->model()->setData(idx, QVariant::fromValue(props), KisNodeModel::PropertiesRole); @@ -593,8 +595,7 @@ void NodeDelegate::Private::resetPropertyStateRecursive(const QModelIndex &root, OptionalProperty prop = findProperty(props, clickedProperty); if (!prop) continue; - prop->stateInStasis = prop->state.toBool(); - prop->isInStasis = true; + prop->isInStasis = false; view->model()->setData(idx, QVariant::fromValue(props), KisNodeModel::PropertiesRole); resetPropertyStateRecursive(idx,clickedProperty); @@ -753,8 +754,20 @@ void NodeDelegate::drawVisibilityIconHijack(QPainter *p, const QStyleOptionViewI p->setOpacity(0.35); } - p->drawPixmap(fitRect.x(), fitRect.center().y() - scm.visibilitySize() / 2, - icon.pixmap(scm.visibilitySize(), QIcon::Normal)); + QPixmap pixmapIcon(icon.pixmap(scm.visibilitySize(), QIcon::Active)); + p->drawPixmap(fitRect.x(), fitRect.center().y() - scm.visibilitySize() / 2, pixmapIcon); + + if (prop->isInStasis) { + QPainter::CompositionMode prevComposition = p->compositionMode(); + p->setCompositionMode(QPainter::CompositionMode_HardLight); + pixmapIcon = icon.pixmap(scm.visibilitySize(), QIcon::Active); + QBitmap mask = pixmapIcon.mask(); + pixmapIcon.fill((QColor(142,160,27,255))); + pixmapIcon.setMask(mask); + p->drawPixmap(fitRect.x(), fitRect.center().y() - scm.visibilitySize() / 2, pixmapIcon); + p->setCompositionMode(prevComposition); + } + p->setOpacity(oldOpacity); //// For debugging purposes only -- GitLab From 8513086327de7119f6da28ba8abbfa43f77a0741 Mon Sep 17 00:00:00 2001 From: Ivan Yossi Date: Sun, 9 Jun 2019 19:34:11 -0500 Subject: [PATCH 3/4] Show feedback when hiding all layers with Shift+Click This also changes behaviour to be more strict. only layers present during stasis operation are marked as such. Almost all operations reset stasis except for add and delete layers. --- plugins/dockers/layerdocker/NodeDelegate.cpp | 33 ++++++++++++++------ plugins/dockers/layerdocker/NodeDelegate.h | 4 +++ plugins/dockers/layerdocker/NodeView.cpp | 1 + 3 files changed, 29 insertions(+), 9 deletions(-) diff --git a/plugins/dockers/layerdocker/NodeDelegate.cpp b/plugins/dockers/layerdocker/NodeDelegate.cpp index a9829a9207..eb4831499f 100644 --- a/plugins/dockers/layerdocker/NodeDelegate.cpp +++ b/plugins/dockers/layerdocker/NodeDelegate.cpp @@ -52,7 +52,7 @@ typedef KisBaseNode::Property* OptionalProperty; class NodeDelegate::Private { public: - Private() : view(0), edit(0) { } + Private() : view(0), edit(0), viewInStasis(false) { } NodeView *view; QPointer edit; @@ -61,6 +61,8 @@ public: QColor checkersColor1; QColor checkersColor2; + bool viewInStasis; + QList rightmostProperties(const KisBaseNode::PropertyList &props) const; int numProperties(const QModelIndex &index) const; OptionalProperty findProperty(KisBaseNode::PropertyList &props, const OptionalProperty &refProp) const; @@ -86,6 +88,7 @@ NodeDelegate::NodeDelegate(NodeView *view, QObject *parent) QApplication::instance()->installEventFilter(this); connect(KisConfigNotifier::instance(), SIGNAL(configChanged()), SLOT(slotConfigChanged())); + connect(this, SIGNAL(resetVisibilityStasis()), SLOT(slotResetState())); slotConfigChanged(); } @@ -495,16 +498,12 @@ void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, Opt QModelIndex root(view->rootIndex()); if ((modifier & Qt::ShiftModifier) == Qt::ShiftModifier && clickedProperty->canHaveStasis) { -// if(stasisIsDirty(root, clickedProperty)){ // clean inStasis if mixed! -// resetPropertyStateRecursive(root, clickedProperty); -// } - KisBaseNode::PropertyList props = index.data(KisNodeModel::PropertiesRole).value(); - OptionalProperty prop = findProperty(props, clickedProperty); - bool mode = true; + + OptionalProperty prop = findProperty(props, clickedProperty); bool record = !prop->isInStasis; - QList items; + QList items; if(modifier == (Qt::ControlModifier | Qt::ShiftModifier)) { mode = false; // inverted mode items.insert(0, index); // important! @@ -762,7 +761,7 @@ void NodeDelegate::drawVisibilityIconHijack(QPainter *p, const QStyleOptionViewI p->setCompositionMode(QPainter::CompositionMode_HardLight); pixmapIcon = icon.pixmap(scm.visibilitySize(), QIcon::Active); QBitmap mask = pixmapIcon.mask(); - pixmapIcon.fill((QColor(142,160,27,255))); + pixmapIcon.fill(d->view->palette().color(QPalette::Highlight)); pixmapIcon.setMask(mask); p->drawPixmap(fitRect.x(), fitRect.center().y() - scm.visibilitySize() / 2, pixmapIcon); p->setCompositionMode(prevComposition); @@ -1129,3 +1128,19 @@ void NodeDelegate::slotUpdateIcon() { KisLayerPropertiesIcons::instance()->updateIcons(); } + +void NodeDelegate::slotResetState(){ + + NodeView *view = d->view; + QModelIndex root = view->rootIndex(); + int childs = view->model()->rowCount(root); + if (childs > 0){ + QModelIndex firstChild = view->model()->index(0, 0, root); + KisBaseNode::PropertyList props = firstChild.data(KisNodeModel::PropertiesRole).value(); + + OptionalProperty visibilityProperty = d->findVisibilityProperty(props); + if(d->stasisIsDirty(root, visibilityProperty)){ // clean inStasis if mixed! + d->resetPropertyStateRecursive(root, visibilityProperty); + } + } +} diff --git a/plugins/dockers/layerdocker/NodeDelegate.h b/plugins/dockers/layerdocker/NodeDelegate.h index de819b8357..65771ad04a 100644 --- a/plugins/dockers/layerdocker/NodeDelegate.h +++ b/plugins/dockers/layerdocker/NodeDelegate.h @@ -50,6 +50,9 @@ public: void slotUpdateIcon(); +Q_SIGNALS: + void resetVisibilityStasis(); + protected: bool eventFilter(QObject *object, QEvent *event) override; @@ -83,6 +86,7 @@ private: private Q_SLOTS: void slotConfigChanged(); + void slotResetState(); }; #endif diff --git a/plugins/dockers/layerdocker/NodeView.cpp b/plugins/dockers/layerdocker/NodeView.cpp index 8c18321979..50a8eac46f 100644 --- a/plugins/dockers/layerdocker/NodeView.cpp +++ b/plugins/dockers/layerdocker/NodeView.cpp @@ -149,6 +149,7 @@ void NodeView::addPropertyActions(QMenu *menu, const QModelIndex &index) void NodeView::updateNode(const QModelIndex &index) { dataChanged(index, index); + d->delegate.resetVisibilityStasis(); } QItemSelectionModel::SelectionFlags NodeView::selectionCommand(const QModelIndex &index, -- GitLab From 990a861ff829e4aee99d6b007ec555820709f7b8 Mon Sep 17 00:00:00 2001 From: Ivan Yossi Date: Thu, 20 Jun 2019 00:13:06 -0500 Subject: [PATCH 4/4] Return to previous state only by shift-click last clicked layer --- libs/image/kis_base_node.h | 13 +++--- plugins/dockers/layerdocker/NodeDelegate.cpp | 42 ++++++++++++++------ 2 files changed, 37 insertions(+), 18 deletions(-) diff --git a/libs/image/kis_base_node.h b/libs/image/kis_base_node.h index 02bf1bcb61..ffd8fc7518 100644 --- a/libs/image/kis_base_node.h +++ b/libs/image/kis_base_node.h @@ -85,31 +85,32 @@ public: bool canHaveStasis; /** If the property isMutable and canHaveStasis, indicate whether it is in stasis or not */ - bool isInStasis = false; + bool isInStasis; /** If the property isMutable and canHaveStasis, provide this value to store the property's state while in stasis */ bool stateInStasis; bool operator==(const Property &rhs) const { - return rhs.name == name && rhs.state == state && rhs.isInStasis == false; + return rhs.name == name && rhs.state == state && isInStasis == rhs.isInStasis; } - Property(): isMutable( false ) { } + Property(): isMutable( false ), isInStasis(false) { } /// Constructor for a mutable property. Property( const KoID &n, const QIcon &on, const QIcon &off, bool isOn ) - : id(n.id()), name( n.name() ), isMutable( true ), onIcon( on ), offIcon( off ), state( isOn ), canHaveStasis( false ) { } + : id(n.id()), name( n.name() ), isMutable( true ), onIcon( on ), offIcon( off ), state( isOn ), + canHaveStasis( false ), isInStasis(false) { } /** Constructor for a mutable property accepting stasis */ Property( const KoID &n, const QIcon &on, const QIcon &off, bool isOn, - bool _isInStasis, bool _stateInStasis ) + bool _isInStasis, bool _stateInStasis = false ) : id(n.id()), name(n.name()), isMutable( true ), onIcon( on ), offIcon( off ), state( isOn ), canHaveStasis( true ), isInStasis( _isInStasis ), stateInStasis( _stateInStasis ) { } /// Constructor for a nonmutable property. Property( const KoID &n, const QString &s ) - : id(n.id()), name(n.name()), isMutable( false ), state( s ) { } + : id(n.id()), name(n.name()), isMutable( false ), state( s ), isInStasis(false) { } }; /** Return this type for PropertiesRole. */ diff --git a/plugins/dockers/layerdocker/NodeDelegate.cpp b/plugins/dockers/layerdocker/NodeDelegate.cpp index eb4831499f..ee7e333dd7 100644 --- a/plugins/dockers/layerdocker/NodeDelegate.cpp +++ b/plugins/dockers/layerdocker/NodeDelegate.cpp @@ -52,7 +52,7 @@ typedef KisBaseNode::Property* OptionalProperty; class NodeDelegate::Private { public: - Private() : view(0), edit(0), viewInStasis(false) { } + Private() : view(0), edit(0) { } NodeView *view; QPointer edit; @@ -61,7 +61,13 @@ public: QColor checkersColor1; QColor checkersColor2; - bool viewInStasis; + QList shiftClickedIndexes; + + enum StasisOperation { + Record, + Review, + Restore + }; QList rightmostProperties(const KisBaseNode::PropertyList &props) const; int numProperties(const QModelIndex &index) const; @@ -69,7 +75,7 @@ public: OptionalProperty findVisibilityProperty(KisBaseNode::PropertyList &props) const; void toggleProperty(KisBaseNode::PropertyList &props, OptionalProperty prop, const Qt::KeyboardModifiers modifier, const QModelIndex &index); - void togglePropertyRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty, const QList &items, bool record, bool mode); + void togglePropertyRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty, const QList &items, StasisOperation record, bool mode); bool stasisIsDirty(const QModelIndex &root, const OptionalProperty &clickedProperty, bool on = false, bool off = false); void resetPropertyStateRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty); @@ -77,7 +83,6 @@ public: void getParentsIndex(QList &items, const QModelIndex &index); void getChildrenIndex(QList &items, const QModelIndex &index); void getSiblingsIndex(QList &items, const QModelIndex &index); - }; NodeDelegate::NodeDelegate(NodeView *view, QObject *parent) @@ -501,10 +506,18 @@ void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, Opt bool mode = true; OptionalProperty prop = findProperty(props, clickedProperty); - bool record = !prop->isInStasis; + + // XXX: Change to use NodeProperty + int position = shiftClickedIndexes.indexOf(index); + + StasisOperation record = (!prop->isInStasis)? StasisOperation::Record : + (position < 0) ? StasisOperation::Review : StasisOperation::Restore; + + shiftClickedIndexes.clear(); + shiftClickedIndexes.push_back(index); QList items; - if(modifier == (Qt::ControlModifier | Qt::ShiftModifier)) { + if (modifier == (Qt::ControlModifier | Qt::ShiftModifier)) { mode = false; // inverted mode items.insert(0, index); // important! getSiblingsIndex(items, index); @@ -515,6 +528,7 @@ void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, Opt togglePropertyRecursive(root, clickedProperty, items, record, mode); } else { + shiftClickedIndexes.clear(); resetPropertyStateRecursive(root, clickedProperty); clickedProperty->state = !clickedProperty->state.toBool(); clickedProperty->isInStasis = false; @@ -522,7 +536,7 @@ void NodeDelegate::Private::toggleProperty(KisBaseNode::PropertyList &props, Opt } } -void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty, const QList &items, bool record, bool mode) +void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, const OptionalProperty &clickedProperty, const QList &items, StasisOperation record, bool mode) { int rowCount = view->model()->rowCount(root); @@ -534,8 +548,11 @@ void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, con OptionalProperty prop = findProperty(props, clickedProperty); if (!prop) continue; - if (record){ // record - prop->stateInStasis = prop->state.toBool(); + + if (record == StasisOperation::Record) { + prop->stateInStasis = prop->state.toBool(); + } + if (record == StasisOperation::Review || record == StasisOperation::Record) { prop->isInStasis = true; if(mode) { //include mode prop->state = (items.contains(idx))? QVariant(true) : QVariant(false); @@ -543,10 +560,11 @@ void NodeDelegate::Private::togglePropertyRecursive(const QModelIndex &root, con prop->state = (!items.contains(idx))? prop->state : (items.at(0) == idx)? QVariant(true) : QVariant(false); } - } else { // recover + } else { // restore prop->state = QVariant(prop->stateInStasis); prop->isInStasis = false; } + view->model()->setData(idx, QVariant::fromValue(props), KisNodeModel::PropertiesRole); togglePropertyRecursive(idx,clickedProperty, items, record, mode); @@ -567,7 +585,7 @@ bool NodeDelegate::Private::stasisIsDirty(const QModelIndex &root, const Optiona OptionalProperty prop = findProperty(props, clickedProperty); if (!prop) continue; - if(prop->isInStasis) { + if (prop->isInStasis) { on = true; } else { off = true; @@ -603,7 +621,7 @@ void NodeDelegate::Private::resetPropertyStateRecursive(const QModelIndex &root, void NodeDelegate::Private::getParentsIndex(QList &items, const QModelIndex &index) { - if(!index.isValid()) return; + if (!index.isValid()) return; items.append(index); getParentsIndex(items, index.parent()); } -- GitLab