Git commit 3f81a96dc7d5b95ba4cc3c9b1eb647fb630a92dd by Boudewijn Rempt, on = behalf of Wolthera van H=C3=B6vell tot Westerflier. Committed on 14/10/2017 at 08:39. Pushed by rempt into branch 'krita/3.3'. [Feature] ASC-CDL color balance filter(Slope, Offset, Power) This is a simple color balance filter as decided by the American Society of Cinematographers. It's purpose is to make communicating color balance easier over different applications. It is also interesting in that it is so simple it does not clip high-bit de= pth values. There's still some issues with the filter, but they are mostly GUI issues, so I am pushing this to prevent bitrot. I have noted the possible list of improvements in the header of the widget class. BUG:355747 Differential revision: https://phabricator.kde.org/D8184 CCMAIL:kimageshop@kde.org M +1 -0 plugins/filters/CMakeLists.txt A +11 -0 plugins/filters/asccdl/CMakeLists.txt A +127 -0 plugins/filters/asccdl/kis_asccdl_filter.cpp [License: G= PL (v2+)] A +61 -0 plugins/filters/asccdl/kis_asccdl_filter.h [License: GPL= (v2+)] A +103 -0 plugins/filters/asccdl/kis_wdg_asccdl.cpp [License: GPL = (v2+)] A +62 -0 plugins/filters/asccdl/kis_wdg_asccdl.h [License: GPL (v= 2+)] A +9 -0 plugins/filters/asccdl/kritaasccdl.json A +105 -0 plugins/filters/asccdl/wdg_asccdl.ui https://commits.kde.org/krita/3f81a96dc7d5b95ba4cc3c9b1eb647fb630a92dd diff --git a/plugins/filters/CMakeLists.txt b/plugins/filters/CMakeLists.txt index 8454461ca98..6faf7d54aba 100644 --- a/plugins/filters/CMakeLists.txt +++ b/plugins/filters/CMakeLists.txt @@ -26,3 +26,4 @@ add_subdirectory( normalize ) add_subdirectory( gradientmap ) add_subdirectory( threshold ) add_subdirectory( halftone ) +add_subdirectory( asccdl ) diff --git a/plugins/filters/asccdl/CMakeLists.txt b/plugins/filters/asccdl= /CMakeLists.txt new file mode 100644 index 00000000000..94a0aaeaa23 --- /dev/null +++ b/plugins/filters/asccdl/CMakeLists.txt @@ -0,0 +1,11 @@ +set(kritaasccdl_SOURCES + kis_asccdl_filter.cpp + kis_wdg_asccdl.cpp +) + +ki18n_wrap_ui(kritaasccdl_SOURCES + wdg_asccdl.ui + ) +add_library(kritaasccdl MODULE ${kritaasccdl_SOURCES}) +target_link_libraries(kritaasccdl kritaui) +install(TARGETS kritaasccdl DESTINATION ${KRITA_PLUGIN_INSTALL_DIR}) diff --git a/plugins/filters/asccdl/kis_asccdl_filter.cpp b/plugins/filters= /asccdl/kis_asccdl_filter.cpp new file mode 100644 index 00000000000..08df10514cc --- /dev/null +++ b/plugins/filters/asccdl/kis_asccdl_filter.cpp @@ -0,0 +1,127 @@ +/* + * Copyright (c) 2017 Wolthera van H=C3=B6vell tot Westerflier + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-13= 01, USA. + */ + +#include "kis_asccdl_filter.h" +#include "kis_wdg_asccdl.h" +#include +#include +#include +#include +#include + +K_PLUGIN_FACTORY_WITH_JSON(KritaASCCDLFactory, + "kritaasccdl.json", + registerPlugin();) + + +KritaASCCDL::KritaASCCDL(QObject *parent, const QVariantList &) : QObject(= parent) +{ + KisFilterRegistry::instance()->add(KisFilterSP(new KisFilterASCCDL())); +} + +KritaASCCDL::~KritaASCCDL() +{ + +} + +KisFilterASCCDL::KisFilterASCCDL(): KisColorTransformationFilter(id(), cat= egoryAdjust(), i18n("&Slope, Offset, Power..")) +{ + setSupportsPainting(true); + setSupportsAdjustmentLayers(true); + setSupportsLevelOfDetail(true); + setSupportsThreading(true); + setColorSpaceIndependence(FULLY_INDEPENDENT); + setShowConfigurationWidget(true); +} + +KoColorTransformation *KisFilterASCCDL::createTransformation(const KoColor= Space *cs, + const KisFilt= erConfigurationSP config) const +{ + KoColor black(Qt::black, cs); + return new KisASCCDLTransformation(cs, + config->getColor("slope", black), + config->getColor("offset", black), + config->getColor("power", black)); +} + +KisConfigWidget *KisFilterASCCDL::createConfigurationWidget(QWidget *paren= t, const KisPaintDeviceSP dev) const +{ + return new KisASCCDLConfigWidget(parent, dev->colorSpace()); +} + +bool KisFilterASCCDL::needsTransparentPixels(const KisFilterConfigurationS= P config, const KoColorSpace *cs) const +{ + KoColor black(Qt::black, cs); + KoColor offset =3D config->getColor("offset", black); + offset.convertTo(cs); + if (cs->difference(black.data(), offset.data())>0) { + return true; + } + return false; +} + +KisFilterConfigurationSP KisFilterASCCDL::factoryConfiguration() const +{ + KisColorTransformationConfigurationSP config =3D new KisColorTransform= ationConfiguration(id().id(), 0); + QVariant colorVariant("KoColor"); + KoColor black; + black.fromQColor(QColor(Qt::black)); + KoColor white; + white.fromQColor(QColor(Qt::white)); + colorVariant.setValue(white); + config->setProperty( "slope", colorVariant); + config->setProperty( "power", colorVariant); + colorVariant.setValue(black); + config->setProperty("offset", colorVariant); + return config; +} + +KisASCCDLTransformation::KisASCCDLTransformation(const KoColorSpace *cs, K= oColor slope, KoColor offset, KoColor power) +{ + QVector slopeN(cs->channelCount()); + slope.convertTo(cs); + slope.colorSpace()->normalisedChannelsValue(slope.data(), slopeN); + m_slope =3D slopeN; + offset.convertTo(cs); + QVector offsetN(cs->channelCount()); + offset.colorSpace()->normalisedChannelsValue(offset.data(), offsetN); + m_offset =3D offsetN; + power.convertTo(cs); + QVector powerN(cs->channelCount()); + power.colorSpace()->normalisedChannelsValue(power.data(), powerN); + m_power =3D powerN; + m_cs =3D cs; +} + +void KisASCCDLTransformation::transform(const quint8 *src, quint8 *dst, qi= nt32 nPixels) const +{ + QVector normalised(m_cs->channelCount()); + const int pixelSize =3D m_cs->pixelSize(); + while (nPixels--) { + m_cs->normalisedChannelsValue(src, normalised); + + for (int c=3D0; cchannelCount(); c++){ + normalised[c] =3D qPow( (normalised.at(c)*m_slope.at(c))+m_off= set.at(c), m_power.at(c)); + } + m_cs->fromNormalisedChannelsValue(dst, normalised); + src +=3D pixelSize; + dst +=3D pixelSize; + } +} + +#include "kis_asccdl_filter.moc" diff --git a/plugins/filters/asccdl/kis_asccdl_filter.h b/plugins/filters/a= sccdl/kis_asccdl_filter.h new file mode 100644 index 00000000000..50c38efecc0 --- /dev/null +++ b/plugins/filters/asccdl/kis_asccdl_filter.h @@ -0,0 +1,61 @@ +/* + * Copyright (c) 2017 Wolthera van H=C3=B6vell tot Westerflier + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-13= 01, USA. + */ + +#ifndef KIS_ASCCDL_FILTER_H +#define KIS_ASCCDL_FILTER_H + +#include +#include "filter/kis_color_transformation_filter.h" + +class KritaASCCDL : public QObject +{ + Q_OBJECT +public: + KritaASCCDL(QObject *parent, const QVariantList &); + ~KritaASCCDL() override; +}; + +class KisFilterASCCDL: public KisColorTransformationFilter +{ +public: + KisFilterASCCDL(); +public: + + static inline KoID id() { + return KoID("asc-cdl", i18n("Slope, Offset, Power(ASC-CDL)")); + } + KoColorTransformation *createTransformation(const KoColorSpace* cs, co= nst KisFilterConfigurationSP config) const override; + KisConfigWidget *createConfigurationWidget(QWidget* parent, const KisP= aintDeviceSP dev) const override; + bool needsTransparentPixels(const KisFilterConfigurationSP config, con= st KoColorSpace *cs) const; +protected: + KisFilterConfigurationSP factoryConfiguration() const override; +}; + +class KisASCCDLTransformation : public KoColorTransformation +{ +public: + KisASCCDLTransformation(const KoColorSpace *cs, KoColor slope, KoColor= offset, KoColor power); + void transform(const quint8* src, quint8* dst, qint32 nPixels) const o= verride; +private: + QVector m_slope; + QVector m_offset; + QVector m_power; + const KoColorSpace *m_cs; +}; + +#endif // KIS_ASCCDL_H diff --git a/plugins/filters/asccdl/kis_wdg_asccdl.cpp b/plugins/filters/as= ccdl/kis_wdg_asccdl.cpp new file mode 100644 index 00000000000..afce1f6b334 --- /dev/null +++ b/plugins/filters/asccdl/kis_wdg_asccdl.cpp @@ -0,0 +1,103 @@ +/* + * Copyright (c) 2017 Wolthera van H=C3=B6vell tot Westerflier + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-13= 01, USA. + */ + +#include "kis_wdg_asccdl.h" +#include +#include +#include +#include +#include +#include + +KisASCCDLConfigWidget::KisASCCDLConfigWidget(QWidget *parent, const KoColo= rSpace *cs) + :KisConfigWidget(parent), + m_page(new Ui_WdgASCCDL), + m_cs(cs) + +{ + KoColor black(Qt::black, cs); + m_page->setupUi(this); + m_page->btnSlope->setColor(black); + m_page->btnOffset->setColor(black); + m_page->btnPower->setColor(black); + + connect(m_page->btnSlope , SIGNAL(changed(const KoColor)), this, SLOT= (slopeColorChanged(const KoColor))); + connect(m_page->btnOffset, SIGNAL(changed(const KoColor)), this, SLOT= (offsetColorChanged(const KoColor))); + connect(m_page->btnPower , SIGNAL(changed(const KoColor)), this, SLOT= (powerColorChanged(const KoColor))); + connect(m_page->slopeSelector, SIGNAL(sigNewColor(const KoColor)), thi= s, SLOT(slopeColorChanged(const KoColor))); + connect(m_page->offsetSelector, SIGNAL(sigNewColor(const KoColor)), th= is, SLOT(offsetColorChanged(const KoColor))); + connect(m_page->powerSelector, SIGNAL(sigNewColor(const KoColor)), thi= s, SLOT(powerColorChanged(const KoColor))); +} + +KisASCCDLConfigWidget::~KisASCCDLConfigWidget() +{ + delete m_page; +} + +KisPropertiesConfigurationSP KisASCCDLConfigWidget::configuration() const +{ + KisFilterConfigurationSP config =3D new KisFilterConfiguration("asc-cd= l", 0); + QVariant colorVariant("KoColor"); + colorVariant.setValue(m_page->btnSlope->color()); + config->setProperty("slope", colorVariant); + colorVariant.setValue(m_page->btnOffset->color()); + config->setProperty("offset", colorVariant); + colorVariant.setValue(m_page->btnPower->color()); + config->setProperty("power", colorVariant); + return config; +} + +void KisASCCDLConfigWidget::setConfiguration(const KisPropertiesConfigurat= ionSP config) +{ + m_page->btnSlope->setColor (config->getColor( "slope", KoColor(Qt::whi= te, m_cs))); + m_page->slopeSelector->slotSetColor(config->getColor("slope", KoColor(= Qt::white, m_cs))); + m_page->btnOffset->setColor(config->getColor("offset", KoColor(Qt::bla= ck, m_cs))); + m_page->offsetSelector->slotSetColor(config->getColor("offset", KoColo= r(Qt::white, m_cs))); + m_page->btnPower->setColor (config->getColor( "power", KoColor(Qt::whi= te, m_cs))); + m_page->powerSelector->slotSetColor(config->getColor("power", KoColor(= Qt::white, m_cs))); +} + +void KisASCCDLConfigWidget::slopeColorChanged(const KoColor &c) +{ + if (QObject::sender() =3D=3D m_page->btnSlope) { + m_page->slopeSelector->slotSetColor(c); + } else { + m_page->btnSlope->setColor(c); + } + emit sigConfigurationItemChanged(); +} + +void KisASCCDLConfigWidget::offsetColorChanged(const KoColor &c) +{ + if (QObject::sender() =3D=3D m_page->btnOffset) { + m_page->offsetSelector->slotSetColor(c); + } else { + m_page->btnOffset->setColor(c); + } + emit sigConfigurationItemChanged(); +} + +void KisASCCDLConfigWidget::powerColorChanged(const KoColor &c) +{ + if (QObject::sender() =3D=3D m_page->btnPower) { + m_page->powerSelector->slotSetColor(c); + } else { + m_page->btnPower->setColor(c); + } + emit sigConfigurationItemChanged(); +} diff --git a/plugins/filters/asccdl/kis_wdg_asccdl.h b/plugins/filters/ascc= dl/kis_wdg_asccdl.h new file mode 100644 index 00000000000..bdca6461020 --- /dev/null +++ b/plugins/filters/asccdl/kis_wdg_asccdl.h @@ -0,0 +1,62 @@ +/* + * Copyright (c) 2017 Wolthera van H=C3=B6vell tot Westerflier + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-13= 01, USA. + */ +#ifndef KIS_WDG_ASCCDL_H +#define KIS_WDG_ASCCDL_H +#include +#include +#include "ui_wdg_asccdl.h" +#include +#include + +class Ui_WdgASCCDL; + +/** + * @brief The KisASCCDLConfigWidget class + * this handles the configuration widget for the slope offset power filter. + * + * Future improvements: + * 1. Have the cs that the widgets gets when being created be actually the= image cs. + * 2. Have the shape be force to a HSV wheel with a slider. + * 3. Make it easier to select power higher than 1.0 (it is possible, but = cumbersome) + * 4. make it easier to access ocio from filters. + * 5. Implement saturation whenever we can figure out what the formula is = for that. + * 6. Implement a way to retrieve and store xml data according to the asc-= cdl spec... + * + * The main problem for 5 and 6 is that I am unable to find the actual asc= -cdl spec. + */ + +class KisASCCDLConfigWidget : public KisConfigWidget +{ + + Q_OBJECT + +public: + KisASCCDLConfigWidget(QWidget * parent, const KoColorSpace *cs); + ~KisASCCDLConfigWidget() override; + + KisPropertiesConfigurationSP configuration() const override; + void setConfiguration(const KisPropertiesConfigurationSP config) overr= ide; + Ui_WdgASCCDL *m_page; + const KoColorSpace *m_cs; +public Q_SLOTS: + void slopeColorChanged(const KoColor &c); + void offsetColorChanged(const KoColor &c); + void powerColorChanged(const KoColor &c); +}; + +#endif //KIS_WDG_ASCCDL_H diff --git a/plugins/filters/asccdl/kritaasccdl.json b/plugins/filters/ascc= dl/kritaasccdl.json new file mode 100644 index 00000000000..5e09c37b7ee --- /dev/null +++ b/plugins/filters/asccdl/kritaasccdl.json @@ -0,0 +1,9 @@ +{ + "Id": "ASC CDL Color Balance", + "Type": "Service", + "X-KDE-Library": "kritaasccdl", + "X-KDE-ServiceTypes": [ + "Krita/Filter" + ], + "X-Krita-Version": "40" +} diff --git a/plugins/filters/asccdl/wdg_asccdl.ui b/plugins/filters/asccdl/= wdg_asccdl.ui new file mode 100644 index 00000000000..be3f17056dd --- /dev/null +++ b/plugins/filters/asccdl/wdg_asccdl.ui @@ -0,0 +1,105 @@ + + + WdgASCCDL + + + + 0 + 0 + 400 + 300 + + + + + + + + + + PushButton + + + + + + + PushButton + + + + + + + Offset: + + + + + + + ASC-CDL color balance + + + + + + + PushButton + + + + + + + Power: + + + + + + + Slope: + + + + + + + + + + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + + KisColorButton + QPushButton +
kis_color_button.h
+
+ + KisVisualColorSelector + QWidget +
KisVisualColorSelector.h
+ 1 +
+
+ + +