File indexing completed on 2024-05-12 15:58:39

0001 /*
0002  *  This file is part of the KDE project
0003  *
0004  *  SPDX-FileCopyrightText: 2006 Cyrille Berger <cberger@cberger.net>
0005  *
0006  *  SPDX-License-Identifier: GPL-2.0-or-later
0007  */
0008 
0009 #include "kis_random_sub_accessor.h"
0010 #include <QtGlobal>
0011 
0012 #include <KoColorSpace.h>
0013 #include <KoMixColorsOp.h>
0014 #include <QtMath>
0015 
0016 #include "kis_paint_device.h"
0017 
0018 KisRandomSubAccessor::KisRandomSubAccessor(KisPaintDeviceSP device)
0019         : m_device(device)
0020         , m_currentPoint(0, 0)
0021         , m_randomAccessor(device->createRandomConstAccessorNG())
0022 {
0023 }
0024 
0025 
0026 KisRandomSubAccessor::~KisRandomSubAccessor()
0027 {
0028 }
0029 
0030 
0031 void KisRandomSubAccessor::sampledOldRawData(quint8* dst)
0032 {
0033     const quint8* pixels[4];
0034     qint16 weights[4];
0035     int x = qFloor(m_currentPoint.x());
0036     int y = qFloor(m_currentPoint.y());
0037 
0038     double hsub = m_currentPoint.x() - x;
0039     if (hsub < 0.0) {
0040         hsub = 1.0 + hsub;
0041     }
0042     double vsub = m_currentPoint.y() - y;
0043     if (vsub < 0.0) {
0044         vsub = 1.0 + vsub;
0045     }
0046     
0047     int sumOfWeights = 0;
0048 
0049     weights[0] = qRound((1.0 - hsub) * (1.0 - vsub) * 255);
0050     sumOfWeights += weights[0];
0051     m_randomAccessor->moveTo(x, y);
0052     pixels[0] = m_randomAccessor->oldRawData();
0053     weights[1] = qRound((1.0 - vsub) * hsub * 255);
0054     sumOfWeights += weights[1];
0055     m_randomAccessor->moveTo(x + 1, y);
0056     pixels[1] = m_randomAccessor->oldRawData();
0057     weights[2] = qRound(vsub * (1.0 - hsub) * 255);
0058     sumOfWeights += weights[2];
0059     m_randomAccessor->moveTo(x, y + 1);
0060     pixels[2] = m_randomAccessor->oldRawData();
0061     weights[3] = qRound(hsub * vsub * 255);
0062     sumOfWeights += weights[3];
0063     m_randomAccessor->moveTo(x + 1, y + 1);
0064     pixels[3] = m_randomAccessor->oldRawData();
0065 
0066     m_device->colorSpace()->mixColorsOp()->mixColors(pixels, weights, 4, dst, sumOfWeights);
0067 }
0068 
0069 
0070 void KisRandomSubAccessor::sampledRawData(quint8* dst)
0071 {
0072     const quint8* pixels[4];
0073     qint16 weights[4];
0074     int x = qFloor(m_currentPoint.x());
0075     int y = qFloor(m_currentPoint.y());
0076 
0077     double hsub = m_currentPoint.x() - x;
0078     if (hsub < 0.0) {
0079         hsub = 1.0 + hsub;
0080     }
0081     double vsub = m_currentPoint.y() - y;
0082     if (vsub < 0.0) {
0083         vsub = 1.0 + vsub;
0084     }
0085     
0086     int sumOfWeights = 0;
0087 
0088     weights[0] = qRound((1.0 - hsub) * (1.0 - vsub) * 255);
0089     sumOfWeights += weights[0];
0090     m_randomAccessor->moveTo(x, y);
0091     pixels[0] = m_randomAccessor->rawDataConst();
0092     weights[1] = qRound((1.0 - vsub) * hsub * 255);
0093     sumOfWeights += weights[1];
0094     m_randomAccessor->moveTo(x + 1, y);
0095     pixels[1] = m_randomAccessor->rawDataConst();
0096     weights[2] = qRound(vsub * (1.0 - hsub) * 255);
0097     sumOfWeights += weights[2];
0098     m_randomAccessor->moveTo(x, y + 1);
0099     pixels[2] = m_randomAccessor->rawDataConst();
0100     weights[3] = qRound(hsub * vsub * 255);
0101     sumOfWeights += weights[3];
0102     m_randomAccessor->moveTo(x + 1, y + 1);
0103     pixels[3] = m_randomAccessor->rawDataConst();
0104     m_device->colorSpace()->mixColorsOp()->mixColors(pixels, weights, 4, dst, sumOfWeights);
0105 }