Commit 5fbb275f authored by Dmitry Kazakov's avatar Dmitry Kazakov
Browse files

Fix sampling when Smudge Radius is set > 300% (possibel in legacy mode only)

parent c50411b3
......@@ -111,6 +111,7 @@ void sampleColor(const QRect &srcRect,
const KoColorSpace *cs = tempFixedDevice->colorSpace();
const int numPixels = sampleRect.width() * sampleRect.height();
sourceDevice->readRect(sampleRect);
sourceDevice->readBytes(tempFixedDevice->data(), sampleRect);
KisAlgebra2D::HaltonSequenceGenerator hGen(2);
......
......@@ -10,23 +10,30 @@
#include "kis_image.h"
#include "KisOverlayPaintDeviceWrapper.h"
void KisColorSmudgeSource::readRect(const QRect &rect) {
readRects({rect});
}
/**********************************************************************************/
/* KisColorSmudgeSourcePaintDevice */
/**********************************************************************************/
KisColorSmudgeSourcePaintDevice::KisColorSmudgeSourcePaintDevice(KisPaintDeviceSP sourceDevice)
: m_sourceDevice(sourceDevice)
KisColorSmudgeSourcePaintDevice::KisColorSmudgeSourcePaintDevice(KisOverlayPaintDeviceWrapper &overlayDevice)
: m_overlayDevice(overlayDevice)
{
}
void KisColorSmudgeSourcePaintDevice::readRects(const QVector<QRect> &rects) {
m_overlayDevice.readRects(rects);
}
void KisColorSmudgeSourcePaintDevice::readBytes(quint8 *dstPtr, const QRect &rect) {
m_sourceDevice->readBytes(dstPtr, rect);
m_overlayDevice.overlay()->readBytes(dstPtr, rect);
}
const KoColorSpace *KisColorSmudgeSourcePaintDevice::colorSpace() const {
return m_sourceDevice->colorSpace();
return m_overlayDevice.overlayColorSpace();
}
/**********************************************************************************/
/* KisColorSmudgeSourceImage */
/**********************************************************************************/
......@@ -38,10 +45,15 @@ KisColorSmudgeSourceImage::KisColorSmudgeSourceImage(KisImageSP image, KisOverla
KIS_ASSERT(m_image->projection() == m_overlayDevice.source());
}
void KisColorSmudgeSourceImage::readBytes(quint8 *dstPtr, const QRect &rect) {
void KisColorSmudgeSourceImage::readRects(const QVector<QRect> &rects)
{
m_image->blockUpdates();
m_overlayDevice.readRect(rect);
m_overlayDevice.readRects(rects);
m_image->unblockUpdates();
}
void KisColorSmudgeSourceImage::readBytes(quint8 *dstPtr, const QRect &rect)
{
m_overlayDevice.overlay()->readBytes(dstPtr, rect);
}
......
......@@ -17,6 +17,8 @@ class KisOverlayPaintDeviceWrapper;
class KisColorSmudgeSource {
public:
virtual ~KisColorSmudgeSource() = default;
void readRect(const QRect &rect);
virtual void readRects(const QVector<QRect> &rects) = 0;
virtual void readBytes(quint8 *dstPtr, const QRect &rect) = 0;
virtual const KoColorSpace* colorSpace() const = 0;
};
......@@ -25,18 +27,24 @@ using KisColorSmudgeSourceSP = QSharedPointer<KisColorSmudgeSource>;
struct KisColorSmudgeSourcePaintDevice : public KisColorSmudgeSource
{
KisColorSmudgeSourcePaintDevice(KisPaintDeviceSP sourceDevice);
KisColorSmudgeSourcePaintDevice(KisOverlayPaintDeviceWrapper &overlayDevice);
void readRects(const QVector<QRect> &rects) override;
void readBytes(quint8 *dstPtr, const QRect &rect) override;
const KoColorSpace* colorSpace() const override;
private:
KisPaintDeviceSP m_sourceDevice;
KisOverlayPaintDeviceWrapper &m_overlayDevice;
};
struct KisColorSmudgeSourceImage : public KisColorSmudgeSource
{
KisColorSmudgeSourceImage(KisImageSP image,
KisOverlayPaintDeviceWrapper &overlayDevice);
void readRects(const QVector<QRect> &rects) override;
void readBytes(quint8 *dstPtr, const QRect &rect) override;
const KoColorSpace* colorSpace() const override;
......
......@@ -23,7 +23,6 @@ KisColorSmudgeStrategyLightness::KisColorSmudgeStrategyLightness(KisPainter *pai
, m_smearAlpha(smearAlpha)
, m_initializationPainter(painter)
{
}
void KisColorSmudgeStrategyLightness::initializePainting()
......@@ -67,6 +66,8 @@ void KisColorSmudgeStrategyLightness::initializePainting()
m_heightmapPainter.setCompositeOp(COMPOSITE_ALPHA_DARKEN);
m_heightmapPainter.setSelection(m_initializationPainter->selection());
m_heightmapPainter.copyMirrorInformationFrom(m_initializationPainter);
m_sourceWrapperDevice = toQShared(new KisColorSmudgeSourcePaintDevice(*m_layerOverlayDevice));
}
KisColorSmudgeStrategyBase::DabColoringStrategy &KisColorSmudgeStrategyLightness::coloringStrategy()
......@@ -108,10 +109,10 @@ KisColorSmudgeStrategyLightness::paintDab(const QRect &srcRect, const QRect &dst
QVector<QRect> readRects;
readRects << mirroredRects;
readRects << srcRect;
m_layerOverlayDevice->readRects(readRects);
m_sourceWrapperDevice->readRects(readRects);
blendBrush({&m_finalPainter},
toQShared(new KisColorSmudgeSourcePaintDevice(m_colorOnlyDevice)),
m_sourceWrapperDevice,
m_maskDab, m_shouldPreserveOriginalDab,
srcRect, dstRect,
currentPaintColor,
......
......@@ -38,6 +38,7 @@ private:
KisPaintDeviceSP m_colorOnlyDevice;
KisPaintDeviceSP m_projectionDevice;
KisOverlayPaintDeviceWrapper *m_layerOverlayDevice;
KisColorSmudgeSourceSP m_sourceWrapperDevice;
KisPainter m_finalPainter;
KisPainter m_heightmapPainter;
bool m_shouldPreserveOriginalDab = true;
......
......@@ -28,7 +28,7 @@ KisColorSmudgeStrategyWithOverlay::KisColorSmudgeStrategyWithOverlay(KisPainter
m_imageOverlayDevice.reset(new KisOverlayPaintDeviceWrapper(image->projection(), 1, KisOverlayPaintDeviceWrapper::PreciseMode));
m_sourceWrapperDevice.reset(new KisColorSmudgeSourceImage(image, *m_imageOverlayDevice));
} else {
m_sourceWrapperDevice.reset(new KisColorSmudgeSourcePaintDevice(m_layerOverlayDevice->overlay()));
m_sourceWrapperDevice.reset(new KisColorSmudgeSourcePaintDevice(*m_layerOverlayDevice));
}
}
......@@ -81,10 +81,15 @@ QVector<QRect> KisColorSmudgeStrategyWithOverlay::paintDab(const QRect &srcRect,
QVector<QRect> readRects;
readRects << mirroredRects;
readRects << srcRect;
m_layerOverlayDevice->readRects(readRects);
m_sourceWrapperDevice->readRects(readRects);
if (m_imageOverlayDevice) {
m_imageOverlayDevice->readRects(readRects);
/**
* If we have m_imageOverlayDevice set, then m_sourceWrapperOverlay points to it, not
* to the layer's overlay. Therefore, we should read from it as well.
*/
m_layerOverlayDevice->readRects(readRects);
}
blendBrush(finalPainters(),
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment