File indexing completed on 2024-06-16 04:17:32
0001 /* 0002 * SPDX-FileCopyrightText: 2020 Ashwin Dhakaita <ashwingpdhakaita@gmail.com> 0003 * 0004 * SPDX-License-Identifier: LGPL-2.0-or-later 0005 */ 0006 0007 #include "MyPaintPaintOp.h" 0008 0009 #include <KoColorConversions.h> 0010 #include <KoCompositeOpRegistry.h> 0011 #include <KoToolManager.h> 0012 #include <QDebug> 0013 #include <QtMath> 0014 #include <kis_brush_based_paintop_settings.h> 0015 #include <kis_image.h> 0016 #include <kis_node.h> 0017 #include <kis_paint_information.h> 0018 #include <kis_painter.h> 0019 #include <kis_paintop.h> 0020 #include <kis_paintop_plugin_utils.h> 0021 #include <kis_paintop_settings.h> 0022 #include <kis_spacing_information.h> 0023 #include <libmypaint/mypaint-brush.h> 0024 0025 KisMyPaintPaintOp::KisMyPaintPaintOp(const KisPaintOpSettingsSP settings, KisPainter *painter, KisNodeSP /*node*/, KisImageSP image) 0026 : KisPaintOp (painter) { 0027 0028 m_image = image; 0029 0030 m_brush.reset(new KisMyPaintPaintOpPreset()); 0031 m_surface.reset(new KisMyPaintSurface(this->painter(), nullptr, m_image)); 0032 0033 m_brush->apply(settings); 0034 0035 if (settings->getBool("EraserMode")) { 0036 0037 painter->setCompositeOpId(COMPOSITE_ERASE); 0038 mypaint_brush_set_base_value(m_brush->brush(), MYPAINT_BRUSH_SETTING_ERASER, false); 0039 } 0040 0041 m_brush->setColor(this->painter()->paintColor(), painter->device()->colorSpace()); 0042 0043 if (KoToolManager::instance()->activeToolId() != "KritaShape/KisToolBrush") { 0044 mypaint_brush_set_base_value(m_brush->brush(), MYPAINT_BRUSH_SETTING_SLOW_TRACKING, 0.0); 0045 } 0046 0047 m_settings = settings; 0048 m_airBrushData.read(m_settings.data()); 0049 0050 m_dtime = -1; 0051 m_isStrokeStarted = false; 0052 m_radius = exp(mypaint_brush_get_base_value(m_brush->brush(), MYPAINT_BRUSH_SETTING_RADIUS_LOGARITHMIC)); 0053 } 0054 0055 KisMyPaintPaintOp::~KisMyPaintPaintOp() { 0056 } 0057 0058 KisSpacingInformation KisMyPaintPaintOp::paintAt(const KisPaintInformation& info) { 0059 0060 if (!painter()) { 0061 return KisSpacingInformation(1.0); 0062 } 0063 0064 const qreal lodScale = KisLodTransform::lodToScale(painter()->device()); 0065 0066 qreal radius = m_radius; 0067 radius *= lodScale; 0068 mypaint_brush_set_base_value(m_brush->brush(), MYPAINT_BRUSH_SETTING_RADIUS_LOGARITHMIC, log(radius)); 0069 0070 m_isStrokeStarted = mypaint_brush_get_state(m_brush->brush(), MYPAINT_BRUSH_STATE_STROKE_STARTED); 0071 if (!m_isStrokeStarted) { 0072 0073 mypaint_brush_stroke_to(m_brush->brush(), m_surface->surface(), info.pos().x(), info.pos().y(), info.pressure(), 0074 info.xTilt(), info.yTilt(), 1.0f); 0075 0076 m_dtime = 0.015; 0077 } 0078 else { 0079 m_dtime = abs(info.currentTime() - m_previousTime)*0.001; 0080 } 0081 0082 mypaint_brush_stroke_to(m_brush->brush(), m_surface->surface(), info.pos().x(), info.pos().y(), info.pressure(), 0083 info.xTilt(), info.yTilt(), m_dtime); 0084 0085 m_previousTime = info.currentTime(); 0086 0087 return computeSpacing(info, lodScale); 0088 } 0089 0090 KisSpacingInformation KisMyPaintPaintOp::updateSpacingImpl(const KisPaintInformation &info) const 0091 { 0092 KisSpacingInformation spacingInfo = computeSpacing(info, KisLodTransform::lodToScale(painter()->device())); 0093 return spacingInfo; 0094 } 0095 0096 KisTimingInformation KisMyPaintPaintOp::updateTimingImpl(const KisPaintInformation &info) const { 0097 0098 return KisPaintOpPluginUtils::effectiveTiming(&m_airBrushData, nullptr, info); 0099 } 0100 0101 KisSpacingInformation KisMyPaintPaintOp::computeSpacing(const KisPaintInformation &info, qreal lodScale) const { 0102 0103 return KisPaintOpPluginUtils::effectiveSpacing(m_radius*2, m_radius*2, 0104 false, 0.0, false, m_radius*2, 0105 true, 1, lodScale, &m_airBrushData, nullptr, info); 0106 }