diff --git a/plugins/filters/guassianhighpass/guassianhighpass_filter.cpp b/plugins/filters/guassianhighpass/guassianhighpass_filter.cpp index 5b2c992d81..c36f1e9b96 100644 --- a/plugins/filters/guassianhighpass/guassianhighpass_filter.cpp +++ b/plugins/filters/guassianhighpass/guassianhighpass_filter.cpp @@ -1,119 +1,126 @@ /* * This file is part of Krita * * Copyright (c) 2019 Miguel Lopez * * 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-1301, USA. */ #include //MSVC requires that Vc come first #include "guassianhighpass_filter.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "kis_lod_transform.h" #include "wdg_guassianhighpass.h" #include "ui_wdgguassianhighpass.h" #include "KoColorSpaceTraits.h" #include KisGuassianHighPassFilter::KisGuassianHighPassFilter() : KisFilter(id(), FiltersCategoryEdgeDetectionId, i18n("&Guassian High Pass...")) { setSupportsPainting(true); - setSupportsAdjustmentLayers(false); - setSupportsThreading(false); - setSupportsLevelOfDetail(false); + setSupportsAdjustmentLayers(true); + setSupportsThreading(true); + setSupportsLevelOfDetail(true); setColorSpaceIndependence(FULLY_INDEPENDENT); } KisConfigWidget * KisGuassianHighPassFilter::createConfigurationWidget(QWidget* parent, const KisPaintDeviceSP, bool /* useForMasks */) const { return new KisWdgGuassianHighPass(parent); } KisFilterConfigurationSP KisGuassianHighPassFilter::factoryConfiguration() const { KisFilterConfigurationSP config = new KisFilterConfiguration(id().id(), 1); config->setProperty("blurAmount", 1); return config; } void KisGuassianHighPassFilter::processImpl(KisPaintDeviceSP device, const QRect& applyRect, const KisFilterConfigurationSP _config, KoUpdater * ) const { - QPointer filterUpdater = 0; QPointer convolutionUpdater = 0; - const QRect deviceBounds = device->defaultBounds()->bounds(); KisFilterConfigurationSP config = _config ? _config : new KisFilterConfiguration(id().id(), 1); QVariant value; KisLodTransformScalar t(device); const qreal blurAmount = t.scale(config->getProperty("blurAmount", value) ? value.toDouble() : 1.0); QBitArray channelFlags = config->channelFlags(); - KisPaintDeviceSP blur = new KisPaintDevice(*device); + + const QRect gaussNeedRect = this->neededRect(applyRect, config, device->defaultBounds()->currentLevelOfDetail()); + + KisPaintDeviceSP blur = m_cachedPaintDevice.getDevice(device); + KisPainter::copyAreaOptimizedOldData(gaussNeedRect.topLeft(), device, blur, gaussNeedRect); KisGaussianKernel::applyGaussian(blur, applyRect, blurAmount, blurAmount, channelFlags, - convolutionUpdater); + convolutionUpdater, + true); // make sure we cerate an internal transaction on temp device KisPainter painter(device); painter.setCompositeOp(blur->colorSpace()->compositeOp(COMPOSITE_GRAIN_EXTRACT)); - painter.bitBlt(0, 0, blur, 0, 0, deviceBounds.width(), deviceBounds.height()); + painter.bitBlt(applyRect.topLeft(), blur, applyRect); painter.end(); + + m_cachedPaintDevice.putDevice(blur); } QRect KisGuassianHighPassFilter::neededRect(const QRect & rect, const KisFilterConfigurationSP config, int lod) const { KisLodTransformScalar t(lod); QVariant value; - const qreal blurAmount = t.scale(config->getProperty("blurAmount", value) ? value.toDouble() : 1.0); - return rect.adjusted(-blurAmount * 2, -blurAmount * 2, blurAmount * 2, blurAmount * 2); + const int halfSize = config->getProperty("blurAmount", value) ? KisGaussianKernel::kernelSizeFromRadius(t.scale(value.toFloat())) / 2 : 5; + + return rect.adjusted( -halfSize * 2, -halfSize * 2, halfSize * 2, halfSize * 2); } QRect KisGuassianHighPassFilter::changedRect(const QRect & rect, const KisFilterConfigurationSP config, int lod) const { KisLodTransformScalar t(lod); QVariant value; - const qreal blurAmount = t.scale(config->getProperty("blurAmount", value) ? value.toDouble() : 1.0); - return rect.adjusted( -blurAmount, -blurAmount, blurAmount, blurAmount); + const int halfSize = config->getProperty("blurAmount", value) ? KisGaussianKernel::kernelSizeFromRadius(t.scale(value.toFloat())) / 2 : 5; + + return rect.adjusted( -halfSize, -halfSize, halfSize, halfSize); } diff --git a/plugins/filters/guassianhighpass/guassianhighpass_filter.h b/plugins/filters/guassianhighpass/guassianhighpass_filter.h index 88907b81b3..8b31c1408c 100644 --- a/plugins/filters/guassianhighpass/guassianhighpass_filter.h +++ b/plugins/filters/guassianhighpass/guassianhighpass_filter.h @@ -1,52 +1,54 @@ /* * This file is part of Krita * * Copyright (c) 2019 Miguel Lopez * * 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-1301, USA. */ #ifndef KIS_GUASSIANHIGHPASS_FILTER_H #define KIS_GUASSIANHIGHPASS_FILTER_H #include "filter/kis_filter.h" +#include "kis_cached_paint_device.h" + class KisGuassianHighPassFilter : public KisFilter { public: KisGuassianHighPassFilter(); void processImpl(KisPaintDeviceSP device, const QRect& applyRect, const KisFilterConfigurationSP config, KoUpdater * ) const override; static inline KoID id() { return KoID("guassianhighpass", i18n("Guassian High Pass")); } KisConfigWidget * createConfigurationWidget(QWidget* parent, const KisPaintDeviceSP dev, bool useForMasks) const override; KisFilterConfigurationSP factoryConfiguration() const override; QRect changedRect(const QRect & rect, const KisFilterConfigurationSP _config, int lod) const override; QRect neededRect(const QRect & rect, const KisFilterConfigurationSP _config, int lod) const override; private: - + mutable KisCachedPaintDevice m_cachedPaintDevice; }; #endif