Summary: | Calling setVisible() on a node's color channels does not behave as expected. | ||
---|---|---|---|
Product: | [Applications] krita | Reporter: | chris.venter |
Component: | Scripting | Assignee: | Krita Bugs <krita-bugs-null> |
Status: | RESOLVED FIXED | ||
Severity: | minor | ||
Priority: | NOR | ||
Version: | 4.4.2 | ||
Target Milestone: | --- | ||
Platform: | macOS (DMG) | ||
OS: | macOS | ||
Latest Commit: | https://invent.kde.org/graphics/krita/commit/1d22acfd3cacb3ee7717dc4958295aeba0cfe09c | Version Fixed In: | |
Sentry Crash Report: |
Description
chris.venter
2021-01-28 04:55:35 UTC
Proposed cause of bug: The code in the setVisible method in libs/libKis/Channel.cpp looks as follows: void Channel::setVisible(bool value) { if (!d->node || !d->channel) return; if (!d->node->inherits("KisLayer")) return; for (uint i = 0; i < d->node->colorSpace()->channelCount(); ++i) { if (d->node->colorSpace()->channels()[i] == d->channel) { QBitArray flags = d->node->colorSpace()->channelFlags(true, true); flags.setBit(i, value); KisLayerSP layer = qobject_cast<KisLayer*>(d->node.data()); layer->setChannelFlags(flags); break; } } } From a look into the call QBitArray flags = d->node->colorSpace()->channelFlags(true, true); it appears that this does not return the current status (active/inactive) of the layer's channels, rather it simply returns the "kind" of each channel in the colorspace, ie. whether it is a color channel or an alpha channel. Rather, the flags should be fetched using QBitArray flags = layer->channelFlags(); Modifying the code in setVisible() to read void Channel::setVisible(bool value) { if (!d->node || !d->channel) return; if (!d->node->inherits("KisLayer")) return; + KisLayerSP layer = qobject_cast<KisLayer*>(d->node.data()); + QBitArray flags = layer->channelFlags(); + if (flags.isEmpty()) { + flags.fill(1, d->node->colorSpace()->channelCount()); + } + for (uint i = 0; i < d->node->colorSpace()->channelCount(); ++i) { if (d->node->colorSpace()->channels()[i] == d->channel) { - QBitArray flags = d->node->colorSpace()->channelFlags(true, true); flags.setBit(i, value); - KisLayerSP layer = qobject_cast<KisLayer*>(d->node.data()); layer->setChannelFlags(flags); break; } } } has the desired outcome of *only* affecting the channel in question. The python code in the original bug post now works as intended. Git commit 74f77fc01cefed9261b59cc827927f11e36b2aae by Halla Rempt, on behalf of Chris Venter. Committed on 28/01/2021 at 13:22. Pushed by rempt into branch 'master'. Use layer->channelFlags in libkis Channel.cpp to correctly retrieve the current channel visibility M +6 -2 libs/libkis/Channel.cpp https://invent.kde.org/graphics/krita/commit/74f77fc01cefed9261b59cc827927f11e36b2aae Git commit 1d22acfd3cacb3ee7717dc4958295aeba0cfe09c by Halla Rempt, on behalf of Chris Venter. Committed on 28/01/2021 at 13:24. Pushed by rempt into branch 'krita/4.3'. Use layer->channelFlags in libkis Channel.cpp to correctly retrieve the current channel visibility (cherry picked from commit 74f77fc01cefed9261b59cc827927f11e36b2aae) M +6 -2 libs/libkis/Channel.cpp https://invent.kde.org/graphics/krita/commit/1d22acfd3cacb3ee7717dc4958295aeba0cfe09c |