Krita Source Code Documentation
Loading...
Searching...
No Matches
KisPopupPalette Class Reference

#include <kis_popup_palette.h>

+ Inheritance diagram for KisPopupPalette:

Public Slots

void slotUpdateIcons ()
 

Signals

void finished () override
 
void sigChangeActivePaintop (int)
 
void sigChangefGColor (const KoColor &)
 
void sigUpdateCanvas ()
 
void sigUpdateRecentColor (int)
 
void zoomLevelChanged (int)
 
- Signals inherited from KisPopupWidgetInterface
virtual void finished ()=0
 Emitted when a popup widget believes that its job is finished.
 

Public Member Functions

void dismiss () override
 Called when you want to dismiss a popup widget.
 
void ensureWithinParent (const QPoint &globalPos, bool useUpperLeft)
 
 KisPopupPalette (KisViewManager *, KisCoordinatesConverter *, KisFavoriteResourceManager *, const KoColorDisplayRendererInterface *displayRenderer, QWidget *parent=0)
 
bool onScreen () override
 Returns whether the widget is active (on screen) or not.
 
void popup (const QPoint &position) override
 Called when and where you want a widget to popup.
 
int selectedColor () const
 
void setParent (QWidget *parent)
 
void setSelectedColor (int x)
 
QSize sizeHint () const override
 
 ~KisPopupPalette () override
 
- Public Member Functions inherited from KisPopupWidgetInterface
virtual ~KisPopupWidgetInterface ()
 

Protected Member Functions

int calculateColorIndex (QPointF position, int numColors) const
 Calculate index of recent color in array.
 
bool eventFilter (QObject *, QEvent *) override
 
int findPresetSlot (QPointF position) const
 / find the index of the brush preset slot containing @position.
 
int hoveredColor () const
 
int hoveredPreset () const
 
void mouseMoveEvent (QMouseEvent *) override
 
void mousePressEvent (QMouseEvent *) override
 
void mouseReleaseEvent (QMouseEvent *) override
 
void paintEvent (QPaintEvent *) override
 
void resizeEvent (QResizeEvent *) override
 
void setHoveredColor (int x)
 
void setHoveredPreset (int x)
 
void showEvent (QShowEvent *event) override
 
void tabletEvent (QTabletEvent *event) override
 

Properties

int hoveredColor
 
int hoveredPreset
 
int selectedColor
 

Private Slots

void showBottomBarWidget (bool visible)
 
void showHudWidget (bool visible)
 
void slotConfigurationChanged ()
 
void slotDisplayConfigurationChanged ()
 
void slotEmitColorChanged ()
 
void slotExternalFgColorChanged (const KoColor &color)
 
void slotFitToViewClicked ()
 
void slotRemoveMirrorPos ()
 
void slotSetMirrorPos ()
 
void slotSetSelectedColor (int x)
 
void slotShowTagsPopup ()
 
void slotUpdate ()
 
void slotZoomSliderChanged (int zoom)
 
void slotZoomSliderPressed ()
 
void slotZoomSliderReleased ()
 
void slotZoomToOneHundredPercentClicked ()
 

Private Member Functions

void calculatePresetLayout ()
 Determine the number of rings to distribute the presets and calculate the radius of the brush preset slots and saves the "layout" to m_cachedPresetLayout.
 
void calculateRotationSnapAreas ()
 
QPainterPath createPathFromPresetIndex (int index) const
 
QPainterPath drawDonutPathAngle (int, int, int)
 
QPainterPath drawDonutPathFull (int, int, int, int)
 
QPainterPath drawFgBgColorIndicator (int type) const
 
QPointF drawPointOnAngle (qreal angle, qreal radius) const
 
bool isPointInPixmap (QPointF &, int pos)
 
void reconfigure ()
 
QRectF rotationIndicatorRect (qreal rotationAngle) const
 

Private Attributes

KisHighlightedToolButtoncanvasOnlyButton {0}
 
QPushButton * fitToViewButton {0}
 
KisKActionCollectionm_actionCollection
 
KisActionManagerm_actionManager
 
KisAcyclicSignalConnectorm_acyclicConnector = 0
 
KisRoundHudButtonm_bottomBarButton {0}
 
QWidget * m_bottomBarWidget {0}
 
CachedPresetLayout m_cachedPresetLayout
 
QRectF m_canvasRotationIndicatorRect
 
KisRoundHudButtonm_clearColorHistoryButton {0}
 
KisMouseClickEaterm_clicksEater
 
QScopedPointer< KisSignalCompressorm_colorChangeCompressor
 
qreal m_colorHistoryInnerRadius {72.0}
 
qreal m_colorHistoryOuterRadius {92.0}
 
KisColorSelectorInterfacem_colorSelector {0}
 
KisCoordinatesConverterm_coordinatesConverter
 
const KoColorDisplayRendererInterfacem_displayRenderer
 
KisDockerHudm_dockerHud {0}
 
KisRoundHudButtonm_dockerHudButton {0}
 
int m_hoveredColor {0}
 
int m_hoveredPreset {0}
 
bool m_isOverCanvasRotationIndicator {false}
 
bool m_isOverFgBgColors {false}
 
bool m_isOverResetCanvasRotationIndicator {false}
 
bool m_isRotatingCanvasIndicator {false}
 
bool m_isZoomingCanvas {false}
 
QSpacerItem * m_mainArea {0}
 
int m_maxPresetSlotCount {10}
 
QPoint m_mirrorPos {}
 
qreal m_popupPaletteSize {385.0}
 
qreal m_presetRingMargin {3.0}
 
int m_presetSlotCount {10}
 
QRectF m_resetCanvasRotationIndicatorRect
 
KisFavoriteResourceManagerm_resourceManager
 
qreal m_rotationSnapAngle {0}
 
qreal m_rotationTrackSize {18.0}
 
int m_selectedColor {0}
 
bool m_showColorHistory {true}
 
bool m_showRotationTrack {true}
 
std::array< QLineF, 24 > m_snapLines {}
 
qreal m_snapRadius {15}
 
std::array< QRect, 24 > m_snapRects {}
 
bool m_snapRotation {false}
 
bool m_tabletRightClickPressed {false}
 
KisRoundHudButtonm_tagsButton {0}
 
bool m_touchBeginReceived {false}
 
bool m_useDynamicSlotCount {true}
 
KisViewManagerm_viewManager
 
KisHighlightedToolButtonmirrorMode {0}
 
QGraphicsOpacityEffect * opacityChange {0}
 
QSlider * zoomCanvasSlider {0}
 
int zoomSliderMaxValue {200}
 
int zoomSliderMinValue {10}
 
QPushButton * zoomToOneHundredPercentButton {0}
 

Detailed Description

Definition at line 45 of file kis_popup_palette.h.

Constructor & Destructor Documentation

◆ KisPopupPalette()

KisPopupPalette::KisPopupPalette ( KisViewManager * viewManager,
KisCoordinatesConverter * coordinatesConverter,
KisFavoriteResourceManager * manager,
const KoColorDisplayRendererInterface * displayRenderer,
QWidget * parent = 0 )

Tablet support code generates a spurious right-click right after opening the window, so we should ignore it. Next right-click will be used for closing the popup palette

Definition at line 92 of file kis_popup_palette.cpp.

94 : QWidget(parent,
95
111 KisPlatformPluginInterfaceFactory::instance()->surfaceColorManagedByOS() ?
112 Qt::Popup :
113 Qt::FramelessWindowHint)
114 , m_coordinatesConverter(coordinatesConverter)
115 , m_viewManager(viewManager)
116 , m_actionManager(viewManager->actionManager())
117 , m_resourceManager(manager)
118 , m_displayRenderer(displayRenderer)
120 , m_actionCollection(viewManager->actionCollection())
122 , m_clicksEater(new KisMouseClickEater(Qt::RightButton, 1, this))
123{
124 setAttribute(Qt::WA_TranslucentBackground);
125
126 connect(m_colorChangeCompressor.data(), SIGNAL(timeout()),
127 SLOT(slotEmitColorChanged()));
128
129 connect(KisConfigNotifier::instance(), SIGNAL(configChanged()), this, SLOT(slotConfigurationChanged()));
130 connect(m_displayRenderer, SIGNAL(displayConfigurationChanged()), this, SLOT(slotDisplayConfigurationChanged()));
131
132 m_acyclicConnector->connectForwardKoColor(m_resourceManager, SIGNAL(sigChangeFGColorSelector(KoColor)),
134
136 m_resourceManager, SIGNAL(sigSetFGColor(KoColor)));
137 // just update() to repaint color labels on external background color change
138 connect(viewManager->canvasResourceProvider(), SIGNAL(sigBGColorChanged(KoColor)), SLOT(update()));
139
140 connect(this, SIGNAL(sigChangeActivePaintop(int)), m_resourceManager, SLOT(slotChangeActivePaintop(int)));
141 connect(this, SIGNAL(sigUpdateRecentColor(int)), m_resourceManager, SLOT(slotUpdateRecentColor(int)));
142
143 connect(m_resourceManager, SIGNAL(setSelectedColor(int)), this, SLOT(slotSetSelectedColor(int)));
144 connect(m_resourceManager, SIGNAL(updatePalettes()), this, SLOT(slotUpdate()));
145 connect(m_resourceManager, SIGNAL(hidePalettes()), this, SIGNAL(finished()));
146
147 // Instances of `this` rely on finished() to be detached and its lifetime is associated with `parent`
148 connect(parent, SIGNAL(destroyed(QObject *)), this, SIGNAL(finished()), Qt::DirectConnection);
149
150 setCursor(Qt::ArrowCursor);
151 setMouseTracking(true);
153 setHoveredColor(-1);
155
156 m_dockerHud = new KisDockerHud(i18n("Popup Palette"), "popuppalette");
157
159
160 connect(m_tagsButton, SIGNAL(clicked()), SLOT(slotShowTagsPopup()));
161
163 m_dockerHudButton->setCheckable(true);
164
165 connect(m_dockerHudButton, SIGNAL(toggled(bool)), SLOT(showHudWidget(bool)));
166
167 m_bottomBarWidget = new QWidget(this);
168
170 m_bottomBarButton->setCheckable(true);
171
172 connect( m_bottomBarButton, SIGNAL(toggled(bool)), SLOT(showBottomBarWidget(bool)));
173
175 m_clearColorHistoryButton->setToolTip(i18n("Clear color history"));
176
177 connect(m_clearColorHistoryButton, SIGNAL(clicked(bool)), m_resourceManager, SLOT(slotClearHistory()));
178 //Otherwise the colors won't disappear until the cursor moves away from the button:
179 connect(m_clearColorHistoryButton, SIGNAL(released()), this, SLOT(slotUpdate()));
180
181 // add some stuff below the pop-up palette that will make it easier to use for tablet people
182 QGridLayout* gLayout = new QGridLayout(this);
183 gLayout->setSizeConstraint(QLayout::SetFixedSize);
184 gLayout->setSpacing(0);
185 gLayout->setContentsMargins(QMargins());
187 gLayout->addItem(m_mainArea, 0, 0); // this should push the box to the bottom
188 gLayout->setColumnMinimumWidth(1, WIDGET_MARGIN);
189 gLayout->addWidget(m_dockerHud, 0, 2);
190 gLayout->setRowMinimumHeight(1, WIDGET_MARGIN);
191 gLayout->addWidget(m_bottomBarWidget, 2, 0);
192
193 QHBoxLayout* hLayout = new QHBoxLayout(m_bottomBarWidget);
194
196 mirrorMode->setFixedSize(35, 35);
197
198 mirrorMode->setToolTip(i18n("Mirror Canvas"));
199 mirrorMode->setDefaultAction(m_actionCollection->action("mirror_canvas_around_cursor"));
200 connect(mirrorMode, SIGNAL(clicked(bool)), this, SLOT(slotUpdate()));
201 connect(mirrorMode, SIGNAL(pressed()), this, SLOT(slotSetMirrorPos()));
202 connect(mirrorMode, SIGNAL(clicked()), this, SLOT(slotRemoveMirrorPos()));
203
205 canvasOnlyButton->setFixedSize(35, 35);
206
207 canvasOnlyButton->setToolTip(i18n("Canvas Only"));
208 canvasOnlyButton->setDefaultAction(m_actionCollection->action("view_show_canvas_only"));
209
210 zoomToOneHundredPercentButton = new QPushButton(this);
211 zoomToOneHundredPercentButton->setText(i18n("100%"));
212 zoomToOneHundredPercentButton->setFixedHeight(35);
213
214 zoomToOneHundredPercentButton->setToolTip(i18n("Zoom to 100%"));
215 connect(zoomToOneHundredPercentButton, SIGNAL(clicked(bool)), this, SLOT(slotZoomToOneHundredPercentClicked()));
216
217 fitToViewButton = new QPushButton(this);
218 fitToViewButton->setFixedHeight(35);
219
220 fitToViewButton->setToolTip(i18n("Fit Canvas to View"));
221 connect(fitToViewButton, SIGNAL(clicked(bool)), this, SLOT(slotFitToViewClicked()));
222
223 zoomCanvasSlider = new QSlider(Qt::Horizontal, this);
224 zoomSliderMinValue = 10; // set in %
225 zoomSliderMaxValue = 200; // set in %
226
228 zoomCanvasSlider->setFixedHeight(35);
230
231 zoomCanvasSlider->setSingleStep(1);
232 zoomCanvasSlider->setPageStep(1);
233
234 connect(zoomCanvasSlider, SIGNAL(valueChanged(int)), this, SLOT(slotZoomSliderChanged(int)));
235 connect(zoomCanvasSlider, SIGNAL(sliderPressed()), this, SLOT(slotZoomSliderPressed()));
236 connect(zoomCanvasSlider, SIGNAL(sliderReleased()), this, SLOT(slotZoomSliderReleased()));
237
239
240 hLayout->setSpacing(2);
241 hLayout->setContentsMargins(0, 6, 0, 0);
242 hLayout->addWidget(mirrorMode);
243 hLayout->addWidget(canvasOnlyButton);
244 hLayout->addWidget(zoomCanvasSlider);
246 hLayout->addWidget(fitToViewButton);
247
248 setVisible(false);
249 reconfigure();
250
251 opacityChange = new QGraphicsOpacityEffect(this);
252 opacityChange->setOpacity(1);
253 setGraphicsEffect(opacityChange);
254
260 installEventFilter(m_clicksEater);
261
262 // Prevent tablet events from being captured by the canvas
263 setAttribute(Qt::WA_NoMousePropagation, true);
264
265 // Because we can create a popup in canvas widget, synthetic events sometimes arrive here (see mousePressEvent()).
266 setAttribute(Qt::WA_AcceptTouchEvents, true);
267 installEventFilter(this);
268 const QList<QWidget *> childrenWidgets = findChildren<QWidget *>();
269 for (const auto &child: childrenWidgets) {
270 child->setAttribute(Qt::WA_AcceptTouchEvents, true);
271 child->installEventFilter(this);
272 }
273
274 // Load configuration..
275 KisConfig cfg(true);
276 m_dockerHudButton->setChecked(cfg.showBrushHud());
277 m_bottomBarButton->setChecked(cfg.showPaletteBottomBar());
278
279 m_dockerHud->setVisible(m_dockerHudButton->isChecked());
280 m_bottomBarWidget->setVisible(m_bottomBarButton->isChecked());
281}
connect(this, SIGNAL(optionsChanged()), this, SLOT(saveOptions()))
void connectBackwardKoColor(QObject *sender, const char *signal, QObject *receiver, const char *method)
void connectForwardKoColor(QObject *sender, const char *signal, QObject *receiver, const char *method)
static KisConfigNotifier * instance()
QAction * action(int index) const
static KisPlatformPluginInterfaceFactory * instance()
KisHighlightedToolButton * canvasOnlyButton
KisActionManager * m_actionManager
KisRoundHudButton * m_dockerHudButton
KisViewManager * m_viewManager
void finished() override
KisKActionCollection * m_actionCollection
KisRoundHudButton * m_tagsButton
QPushButton * zoomToOneHundredPercentButton
void slotExternalFgColorChanged(const KoColor &color)
void slotSetSelectedColor(int x)
KisRoundHudButton * m_bottomBarButton
void slotZoomSliderChanged(int zoom)
void sigChangefGColor(const KoColor &)
KisHighlightedToolButton * mirrorMode
KisCoordinatesConverter * m_coordinatesConverter
void slotDisplayConfigurationChanged()
void sigChangeActivePaintop(int)
void showBottomBarWidget(bool visible)
QSpacerItem * m_mainArea
KisMouseClickEater * m_clicksEater
void showHudWidget(bool visible)
QWidget * m_bottomBarWidget
QScopedPointer< KisSignalCompressor > m_colorChangeCompressor
KisFavoriteResourceManager * m_resourceManager
KisRoundHudButton * m_clearColorHistoryButton
KisDockerHud * m_dockerHud
void setHoveredPreset(int x)
KisAcyclicSignalConnector * m_acyclicConnector
QGraphicsOpacityEffect * opacityChange
void setSelectedColor(int x)
void slotZoomToOneHundredPercentClicked()
const KoColorDisplayRendererInterface * m_displayRenderer
void setHoveredColor(int x)
void sigUpdateRecentColor(int)
QPushButton * fitToViewButton
KisCanvasResourceProvider * canvasResourceProvider()
int zoomInPercent() const
static const int WIDGET_MARGIN
bool update(QSpinBox *spinBox)

References KisKActionCollection::action(), canvasOnlyButton, KisViewManager::canvasResourceProvider(), connect(), KisAcyclicSignalConnector::connectBackwardKoColor(), KisAcyclicSignalConnector::connectForwardKoColor(), finished(), fitToViewButton, KisConfigNotifier::instance(), m_actionCollection, m_acyclicConnector, m_bottomBarButton, m_bottomBarWidget, m_clearColorHistoryButton, m_clicksEater, m_colorChangeCompressor, m_coordinatesConverter, m_displayRenderer, m_dockerHud, m_dockerHudButton, m_mainArea, m_popupPaletteSize, m_resourceManager, m_tagsButton, mirrorMode, opacityChange, reconfigure(), setHoveredColor(), setHoveredPreset(), setSelectedColor(), showBottomBarWidget(), KisConfig::showBrushHud(), showHudWidget(), KisConfig::showPaletteBottomBar(), sigChangeActivePaintop(), sigChangefGColor(), sigUpdateRecentColor(), slotConfigurationChanged(), slotDisplayConfigurationChanged(), slotEmitColorChanged(), slotExternalFgColorChanged(), slotFitToViewClicked(), slotRemoveMirrorPos(), slotSetMirrorPos(), slotSetSelectedColor(), slotShowTagsPopup(), slotUpdate(), slotUpdateIcons(), slotZoomSliderChanged(), slotZoomSliderPressed(), slotZoomSliderReleased(), slotZoomToOneHundredPercentClicked(), WIDGET_MARGIN, zoomCanvasSlider, KoZoomHandler::zoomInPercent(), zoomSliderMaxValue, zoomSliderMinValue, and zoomToOneHundredPercentButton.

◆ ~KisPopupPalette()

KisPopupPalette::~KisPopupPalette ( )
override

Definition at line 283 of file kis_popup_palette.cpp.

284{
285}

Member Function Documentation

◆ calculateColorIndex()

int KisPopupPalette::calculateColorIndex ( QPointF position,
int numColors ) const
protected

Calculate index of recent color in array.

Parameters
numColorsthe total number of recent colors
Returns
-1 if numColors < 1

Definition at line 1198 of file kis_popup_palette.cpp.

1199{
1200 if (numColors < 1) {
1201 return -1;
1202 }
1203 // relative to palette center
1204 QPointF relPosition = position - QPointF(0.5 * m_popupPaletteSize, 0.5 * m_popupPaletteSize);
1205
1206 qreal angle = M_PI - qAtan2(relPosition.x(), relPosition.y()) + M_PI / numColors;
1207 angle = normalizeAngle(angle);
1208
1209 int index = floor(angle * numColors / (2 * M_PI));
1210 return qBound(0, index, numColors - 1);
1211}
std::enable_if< std::is_floating_point< T >::value, T >::type normalizeAngle(T a)
Definition kis_global.h:121
#define M_PI
Definition kis_global.h:111

References M_PI, m_popupPaletteSize, and normalizeAngle().

◆ calculatePresetLayout()

void KisPopupPalette::calculatePresetLayout ( )
private

Determine the number of rings to distribute the presets and calculate the radius of the brush preset slots and saves the "layout" to m_cachedPresetLayout.

Definition at line 1231 of file kis_popup_palette.cpp.

1232{
1233 if (m_presetSlotCount == 0) {
1235 return;
1236 }
1237 // how many degrees each slice will get
1238 // if the slot count is 1, we must divide by 2 to get 180 for the algorithm to work
1239 qreal angleSlice = 360.0 / qMax(m_presetSlotCount, 2);
1240 qreal outerRadius = m_popupPaletteSize/2 - m_presetRingMargin - (m_showRotationTrack ? m_rotationTrackSize + 1 /* half of stroke */ : BORDER_WIDTH);
1241 qreal innerRadius = m_colorHistoryOuterRadius +
1243 ? 1 /* half of stroke */ + m_presetRingMargin
1244 : 0 /* preset margin is already included in either color history radius when it's not showing */
1245 );
1246
1247 qreal ringWidth = outerRadius - innerRadius;
1248 qreal halfRingWidth = 0.5 * ringWidth;
1249 qreal ringMidRadius = innerRadius + halfRingWidth;
1250
1251 // reset the cached layout
1254
1255 // note: adding the margin the way it's done
1256 // (calculating the radiuses without taking it into account then subtracting it after)
1257 // is not particularly accurate, but it looks fine since it's so small
1258 int margin = 2;
1259
1260 // assume one row and get the max radius until the circles would touch
1261 qreal oneRowAngleSlice = angleSlice / 2;
1262 qreal oneRowMaxRadius = ringMidRadius * qSin(qDegreesToRadians(oneRowAngleSlice));
1263
1264 // if the circles are bigger than the ring we're limited by the
1265 // ring's width instead and only one row would fit
1266
1267 // oneRowMaxRadius * 0.2 is to make sure that we still do one row if
1268 // there isn't that much of a difference and two would just look weirder
1269 if (oneRowMaxRadius - margin > halfRingWidth - oneRowMaxRadius * 0.2) {
1270 c.ringCount = 1;
1271 c.firstRowRadius = qMin(halfRingWidth, oneRowMaxRadius - margin);
1272 c.firstRowPos = ringMidRadius;
1273 return;
1274 }
1275
1276 // otherwise 2 or 3 rows always fit
1277 qreal tempRadius = halfRingWidth;
1278 {
1279 // for two rows, the first row is tangent to the inner radius
1280 // and the second row to the outer one
1281 qreal twoRowInnerCount = ceil(qMax(m_presetSlotCount, 2) / 2.0);
1282 qreal twoRowAngleSlice = 360.0 / twoRowInnerCount;
1283
1284 // we can start at half the ring width and shrink the radius until nothing is overlapping
1285 while (tempRadius >= 0) {
1286 tempRadius -= 0.2;
1287 QPointF r1p1(drawPointOnAngle(twoRowAngleSlice / 2, innerRadius + tempRadius));
1288 QPointF r1p2(drawPointOnAngle(twoRowAngleSlice / 2 * 3, innerRadius + tempRadius));
1289 QPointF r2p(drawPointOnAngle(twoRowAngleSlice, outerRadius - tempRadius));
1290 qreal row1SiblingDistance = kisDistance(r1p1, r1p2);
1291 qreal row1To2Distance = kisDistance(r1p1, r2p);
1292 if (row1To2Distance >= (tempRadius + margin) * 2) {
1293 // the previous radius is the one that's guaranteed not to be overlapping
1294 if (row1SiblingDistance < (tempRadius + margin) * 2) {
1295 // the inner row still overlaps, attempt 3 rows instead
1296 break;
1297 }
1298 c.ringCount = 2;
1299 c.secondRowRadius = tempRadius;
1300 c.secondRowPos = outerRadius - tempRadius;
1301 c.firstRowRadius = tempRadius;
1302 c.firstRowPos = innerRadius + tempRadius;
1303 return;
1304 }
1305 }
1306 }
1307
1308 // for three rows, we initially arrange them like so:
1309 // the first row tangent to the inner radius
1310 // the second row in the middle
1311 // the third row tangent to the outer radius
1312
1313 qreal threeRowInnerCount = ceil(qMax(m_presetSlotCount, 2) / 3.0);
1314 qreal threeRowAngleSlice = 360.0 / threeRowInnerCount;
1315
1316 // then we decrease the radius until no row is overlapping each other or itself
1317 while (tempRadius >= 0) {
1318 QPointF r1p1(drawPointOnAngle(threeRowAngleSlice / 2, innerRadius + tempRadius));
1319 QPointF r1p2(drawPointOnAngle(threeRowAngleSlice / 2 * 3, innerRadius + tempRadius));
1320 QPointF r2p1(drawPointOnAngle(threeRowAngleSlice, ringMidRadius));
1321 QPointF r2p2(drawPointOnAngle(threeRowAngleSlice * 2, ringMidRadius));
1322 QPointF r3p(drawPointOnAngle(threeRowAngleSlice / 2, outerRadius - tempRadius));
1323
1324 qreal row1SiblingDistance = kisDistance(r1p1, r1p2);
1325 qreal row1to2Distance = kisDistance(r1p1, r2p1);
1326 qreal row2to3Distance = kisDistance(r2p1, r3p);
1327 qreal row1to3Distance = kisDistance(r1p1, r3p);
1328
1329 if (
1330 row1to2Distance >= tempRadius * 2 &&
1331 row2to3Distance >= tempRadius * 2 &&
1332 row1to3Distance >= tempRadius * 2 &&
1333 row1SiblingDistance >= tempRadius * 2
1334 ) {
1335
1336 qreal row2SiblingDistance = kisDistance(r2p1, r2p2);
1337
1338 qreal firstRowRadius = tempRadius;
1339 qreal thirdRowRadius = tempRadius;
1340 qreal secondRowRadius = tempRadius;
1341
1342 bool firstRowTouching = row1SiblingDistance - firstRowRadius * 2 < 1;
1343 if (firstRowTouching) {
1344 // attempt to expand the second row
1345 // and expand + move the third row inwards
1346 QPointF tempR3p = r3p;
1347 qreal tempSecondThirdRowRadius = secondRowRadius;
1348 qreal tempRow2to3Distance = row2to3Distance;
1349 qreal tempRow1to3Distance = row1to3Distance;
1350 while (
1351 tempSecondThirdRowRadius * 2 < tempRow2to3Distance &&
1352 tempSecondThirdRowRadius * 2 < row2SiblingDistance &&
1353 tempSecondThirdRowRadius * 2 < tempRow1to3Distance &&
1354 tempSecondThirdRowRadius + firstRowRadius < row1to2Distance
1355 ) {
1356 // the previous temp variables are within limits
1357 r3p = tempR3p;
1358 row2to3Distance = tempRow2to3Distance;
1359 row1to3Distance = tempRow1to3Distance;
1360 secondRowRadius = tempSecondThirdRowRadius;
1361
1362 tempSecondThirdRowRadius += 1;
1363
1364 tempR3p = drawPointOnAngle(threeRowAngleSlice / 2, outerRadius - tempSecondThirdRowRadius);
1365
1366 tempRow2to3Distance = kisDistance(r2p1, tempR3p);
1367 tempRow1to3Distance = kisDistance(r1p1, tempR3p);
1368 }
1369 thirdRowRadius = secondRowRadius;
1370 }
1371
1372 {
1373 // the third row can sometimes be expanded + moved a bit more
1374 qreal tempThirdRowRadius = thirdRowRadius;
1375 QPointF tempR3p = r3p;
1376 qreal tempRow2to3Distance = row2to3Distance;
1377 qreal tempRow1to3Distance = row1to3Distance;
1378 while (
1379 tempThirdRowRadius < halfRingWidth &&
1380 secondRowRadius + tempThirdRowRadius < tempRow2to3Distance &&
1381 firstRowRadius + tempThirdRowRadius < tempRow1to3Distance
1382 ) {
1383 r3p = tempR3p;
1384 row2to3Distance = tempRow2to3Distance;
1385 row1to3Distance = tempRow1to3Distance;
1386 thirdRowRadius = tempThirdRowRadius;
1387
1388 tempThirdRowRadius += 1;
1389
1390 tempR3p = drawPointOnAngle(threeRowAngleSlice / 2, outerRadius - tempThirdRowRadius);
1391 tempRow2to3Distance = kisDistance(r2p1, tempR3p);
1392 tempRow1to3Distance = kisDistance(r1p1, tempR3p);
1393 }
1394 }
1395 // the third row is no longer moved
1396 qreal thirdRowPos = outerRadius - thirdRowRadius;
1397
1398 // many times, e.g. when the second row is touching
1399 // the first row can be moved outwards and expanded
1400 // sometimes it will even detach from the inner radius if the ringwidth is large enough
1401 // and there's a lot of presets
1402 qreal firstRowPos = innerRadius + tempRadius;
1403 {
1404 qreal tempFirstRowPos = firstRowPos;
1405 qreal tempFirstRowRadius = firstRowRadius;
1406 qreal tempRow1SiblingDistance = row1SiblingDistance;
1407 qreal tempRow1to3Distance = row1to3Distance;
1408 qreal tempRow1to2Distance = row1to2Distance;
1409 QPointF tempR1p1 = r1p1;
1410 QPointF tempR1p2 = r1p2;
1411
1412 while (
1413 tempFirstRowPos < ringMidRadius &&
1414 tempFirstRowRadius + secondRowRadius < tempRow1to2Distance &&
1415 tempFirstRowRadius + thirdRowRadius < tempRow1to3Distance
1416 ) {
1417 firstRowPos = tempFirstRowPos;
1418 firstRowRadius = tempFirstRowRadius;
1419 row1to2Distance = tempRow1to2Distance;
1420 r1p1 = tempR1p1;
1421 // these are unused after so it's not necessary to update them
1422 // row1to3Distance = tempRow1to3Distance;
1423 // row1SiblingDistance = tempRow1SiblingDistance;
1424 // r1p2 = tempR1p2;
1425
1426 tempFirstRowPos += 1;
1427
1428 tempR1p1 = drawPointOnAngle(threeRowAngleSlice / 2, tempFirstRowPos);
1429 tempR1p2 = drawPointOnAngle(threeRowAngleSlice / 2 * 3, tempFirstRowPos);
1430 tempRow1SiblingDistance = kisDistance(tempR1p1, tempR1p2);
1431 // expand it to the max size
1432 tempFirstRowRadius = tempRow1SiblingDistance / 2;
1433 tempRow1to2Distance = kisDistance(tempR1p2, r2p1);
1434 tempRow1to3Distance = kisDistance(tempR1p1, r3p);
1435 }
1436 }
1437
1438 // finally it's rare, but sometimes possible to also move + expand the second row
1439 qreal secondRowPos = ringMidRadius;
1440 bool row2touching1 = row1to2Distance - (firstRowRadius + secondRowRadius) < 1;
1441 bool row2touching3 = row2to3Distance - (thirdRowRadius + secondRowRadius) < 1;
1442 if (!row2touching1 && !row2touching3) {
1443 // move the second row in until it's touching the first row
1444 qreal knownAngleRatio = qSin(qDegreesToRadians(threeRowAngleSlice / 2)) /
1445 (firstRowRadius + secondRowRadius);
1446 qreal angleRow1Row2Center = qAsin(knownAngleRatio * firstRowPos);
1447 qreal angleCenterRow2Row1 = 180 - threeRowAngleSlice / 2 - qRadiansToDegrees(angleRow1Row2Center);
1448 secondRowPos = qSin(qDegreesToRadians(angleCenterRow2Row1)) / knownAngleRatio;
1449 }
1450 if (!row2touching3) {
1451 QPointF tempR2p1 = r2p1;
1452 qreal tempRadius = secondRowRadius;
1453 qreal tempRow1to2Distance = row1to2Distance;
1454 qreal tempRow2to3Distance = row2to3Distance;
1455 qreal tempSecondRowPos = secondRowPos;
1456 while (
1457 tempSecondRowPos < thirdRowPos &&
1458 tempRadius + thirdRowRadius < tempRow2to3Distance &&
1459 // this is an artificial limit, it could get bigger but looks weird
1460 tempRadius < thirdRowRadius
1461 ) {
1462 secondRowRadius = tempRadius;
1463 secondRowPos = tempSecondRowPos;
1464 // these are unused after so it's not necessary to update them
1465 // r2p1 = tempR2p1;
1466 // row1to2Distance = tempRow1to2Distance;
1467 // row2to3Distance = tempRow2to3Distance;
1468
1469 tempSecondRowPos += 1;
1470
1471 tempR2p1 = drawPointOnAngle(threeRowAngleSlice, secondRowPos + 1);
1472 tempRow1to2Distance = kisDistance(tempR2p1, r1p1);
1473 tempRow2to3Distance = kisDistance(tempR2p1, r3p);
1474 tempRadius = tempRow1to2Distance - firstRowRadius;
1475 }
1476 }
1477 c = {
1478 3, //ringCount
1479 firstRowRadius - margin,
1480 secondRowRadius - margin,
1481 thirdRowRadius - margin,
1482 firstRowPos,
1483 secondRowPos,
1484 thirdRowPos
1485 };
1486 return;
1487 }
1488 tempRadius -= 0.2;
1489 }
1490}
QPointF drawPointOnAngle(qreal angle, qreal radius) const
CachedPresetLayout m_cachedPresetLayout
qreal kisDistance(const QPointF &pt1, const QPointF &pt2)
Definition kis_global.h:190
static const qreal BORDER_WIDTH

References BORDER_WIDTH, drawPointOnAngle(), CachedPresetLayout::firstRowPos, CachedPresetLayout::firstRowRadius, kisDistance(), m_cachedPresetLayout, m_colorHistoryOuterRadius, m_popupPaletteSize, m_presetRingMargin, m_presetSlotCount, m_rotationTrackSize, m_showColorHistory, m_showRotationTrack, CachedPresetLayout::ringCount, CachedPresetLayout::secondRowPos, and CachedPresetLayout::secondRowRadius.

◆ calculateRotationSnapAreas()

void KisPopupPalette::calculateRotationSnapAreas ( )
private

Definition at line 1549 of file kis_popup_palette.cpp.

1549 {
1550 int i = 0;
1551 for (QRect &rect: m_snapRects) {
1552 QPointF point(drawPointOnAngle(i * 15, m_popupPaletteSize / 2 - BORDER_WIDTH - m_snapRadius/2));
1553 point += QPointF(m_popupPaletteSize / 2 - m_snapRadius, m_popupPaletteSize / 2 - m_snapRadius);
1554 rect = QRect(point.x(), point.y(), m_snapRadius*2, m_snapRadius*2);
1555 i++;
1556 }
1557 i = 0;
1558 for (QLineF &line: m_snapLines) {
1559 qreal penWidth = BORDER_WIDTH / 2;
1560 QPointF point1 = drawPointOnAngle(i * 15, m_popupPaletteSize / 2 - m_rotationTrackSize + penWidth);
1561 point1 += QPointF(m_popupPaletteSize / 2, m_popupPaletteSize / 2);
1562 QPointF point2 = drawPointOnAngle(i * 15, m_popupPaletteSize / 2 - BORDER_WIDTH - penWidth);
1563 point2 += QPointF(m_popupPaletteSize / 2, m_popupPaletteSize / 2);
1564 line = QLineF(point1, point2);
1565 i++;
1566 }
1567}
std::array< QRect, 24 > m_snapRects
std::array< QLineF, 24 > m_snapLines

References BORDER_WIDTH, drawPointOnAngle(), m_popupPaletteSize, m_rotationTrackSize, m_snapLines, m_snapRadius, and m_snapRects.

◆ createPathFromPresetIndex()

QPainterPath KisPopupPalette::createPathFromPresetIndex ( int index) const
private

Definition at line 1492 of file kis_popup_palette.cpp.

1493{
1494 // how many degrees each slice will get
1495 // if the slot count is 1, we must divide by 2 to get 180 for the algorithm to work
1496 qreal angleSlice = 360.0 / qMax(m_presetSlotCount, 2);
1497 // the starting angle of the slice we need to draw. the negative sign makes us go clockwise.
1498 // adding 90 degrees makes us start at the top. otherwise we would start at the right
1499 qreal startingAngle = -(index * angleSlice) + 90;
1501 qreal radius = m_cachedPresetLayout.firstRowRadius;
1503 case 1: break;
1504 case 2: {
1505 angleSlice = 180.0/((m_presetSlotCount+1) / 2);
1506 startingAngle = -(index * angleSlice) + 90;
1507
1508 if (index % 2) {
1511 }
1512 break;
1513 }
1514 case 3: {
1515 int triplet = index / 3;
1516 angleSlice = 180.0 / ((m_presetSlotCount + 2) / 3);
1517 switch (index % 3) {
1518 case 0:
1519 startingAngle = -(triplet * 2 * angleSlice) + 90;
1522 break;
1523 case 1:
1524 startingAngle = -(triplet * 2 * angleSlice) + 90;
1527 break;
1528 case 2:
1529 startingAngle = -((triplet * 2 + 1) * angleSlice) + 90;
1532 break;
1533 default:
1534 KIS_ASSERT(false);
1535 }
1536 break;
1537 }
1538 default:
1540 }
1541 QPainterPath path;
1542 qreal pathX = length * qCos(qDegreesToRadians(startingAngle)) - radius;
1543 qreal pathY = -(length) * qSin(qDegreesToRadians(startingAngle)) - radius;
1544 qreal pathDiameter = 2 * radius; // distance is used to calculate the X/Y in addition to the preset circle size
1545 path.addEllipse(pathX, pathY, pathDiameter, pathDiameter);
1546 return path;
1547}
qreal length(const QPointF &vec)
Definition Ellipse.cc:82
#define KIS_ASSERT_RECOVER_NOOP(cond)
Definition kis_assert.h:97
#define KIS_ASSERT(cond)
Definition kis_assert.h:33

References CachedPresetLayout::firstRowPos, CachedPresetLayout::firstRowRadius, KIS_ASSERT, KIS_ASSERT_RECOVER_NOOP, length(), m_cachedPresetLayout, m_presetSlotCount, CachedPresetLayout::ringCount, CachedPresetLayout::secondRowPos, CachedPresetLayout::secondRowRadius, CachedPresetLayout::thirdRowPos, and CachedPresetLayout::thirdRowRadius.

◆ dismiss()

void KisPopupPalette::dismiss ( )
overridevirtual

Called when you want to dismiss a popup widget.

Implements KisPopupWidgetInterface.

Definition at line 1085 of file kis_popup_palette.cpp.

1086{
1087 setVisible(false);
1088}

◆ drawDonutPathAngle()

QPainterPath KisPopupPalette::drawDonutPathAngle ( int inner_radius,
int outer_radius,
int limit )
private

Definition at line 786 of file kis_popup_palette.cpp.

787{
788 QPainterPath path;
789 path.moveTo(-0.999 * outer_radius * sin(M_PI / limit), 0.999 * outer_radius * cos(M_PI / limit));
790 path.arcTo(-1 * outer_radius, -1 * outer_radius, 2 * outer_radius, 2 * outer_radius, -90.0 - 180.0 / limit,
791 360.0 / limit);
792 path.arcTo(-1 * inner_radius, -1 * inner_radius, 2 * inner_radius, 2 * inner_radius, -90.0 + 180.0 / limit,
793 - 360.0 / limit);
794 path.closeSubpath();
795
796 return path;
797}

References M_PI.

◆ drawDonutPathFull()

QPainterPath KisPopupPalette::drawDonutPathFull ( int x,
int y,
int inner_radius,
int outer_radius )
private

Definition at line 776 of file kis_popup_palette.cpp.

777{
778 QPainterPath path;
779 path.addEllipse(QPointF(x, y), outer_radius, outer_radius);
780 path.addEllipse(QPointF(x, y), inner_radius, inner_radius);
781 path.setFillRule(Qt::OddEvenFill);
782
783 return path;
784}

◆ drawFgBgColorIndicator()

QPainterPath KisPopupPalette::drawFgBgColorIndicator ( int type) const
private

Definition at line 799 of file kis_popup_palette.cpp.

800{
801 QPointF edgePoint = QPointF(0.14645, 0.14645) * (m_popupPaletteSize);
802
803 // the points are really (-5, 15) and (5, 15) shifted right 1px
804 // this is so that where the circles meet the circle of the palette, the space occupied is exactly half to either side of the -45deg line
805 QPainterPath indicator;
806 switch (type) {
807 case 0: { // background
808 indicator.addEllipse(edgePoint + QPointF(-4, 15), 30, 30);
809 break;
810 }
811 case 1: { //foreground
812 indicator.addEllipse(edgePoint + QPointF(6, -15), 30, 30);
813 break;
814 }
815 }
816 return indicator;
817}

References m_popupPaletteSize.

◆ drawPointOnAngle()

QPointF KisPopupPalette::drawPointOnAngle ( qreal angle,
qreal radius ) const
private

Definition at line 1221 of file kis_popup_palette.cpp.

1222{
1223 QPointF p(
1224 // -90 so it starts at the top since this is mainly used by calculatePresetLayout
1225 radius * qCos(qDegreesToRadians(angle - 90)),
1226 radius * qSin(qDegreesToRadians(angle - 90))
1227 );
1228 return p;
1229}
const Params2D p

References p.

◆ ensureWithinParent()

void KisPopupPalette::ensureWithinParent ( const QPoint & globalPos,
bool useUpperLeft )

Definition at line 1095 of file kis_popup_palette.cpp.

1095 {
1096 if (isVisible()) {
1097 const QSize paletteSize = geometry().size();
1098 const QPoint paletteCenterOffset(paletteSize.width() / 2, paletteSize.height() / 2);
1099
1100 QPoint paletteGlobalPos = globalPos;
1101 if (!useUpperLeft) {
1102 paletteGlobalPos -= paletteCenterOffset;
1103 }
1104
1105 if (parentWidget()) {
1106 const qreal widgetMargin = -20.0;
1107
1108 const QPoint paletteParentPos = parentWidget()->mapFromGlobal(paletteGlobalPos);
1109 QRect paletteParentRect(paletteParentPos, paletteSize);
1110
1111 const QRect fitRect = kisGrowRect(parentWidget()->rect(), widgetMargin);
1112 paletteParentRect = kisEnsureInRect(paletteParentRect, fitRect);
1113 paletteGlobalPos = parentWidget()->mapToGlobal(paletteParentRect.topLeft());
1114 }
1115
1116
1117 const QPoint moveToPoint = this->windowHandle() ? paletteGlobalPos : parentWidget()->mapFromGlobal(paletteGlobalPos);
1118
1119 move(moveToPoint);
1120 }
1121}
T kisGrowRect(const T &rect, U offset)
Definition kis_global.h:186
QRect kisEnsureInRect(QRect rc, const QRect &bounds)
Definition kis_global.h:267
unsigned paletteSize
Definition palette.c:34

References kisEnsureInRect(), kisGrowRect(), and paletteSize.

◆ eventFilter()

bool KisPopupPalette::eventFilter ( QObject * ,
QEvent * event )
overrideprotected

Definition at line 980 of file kis_popup_palette.cpp.

981{
982 switch (event->type()) {
983 case QEvent::TouchBegin:
985 break;
986 case QEvent::MouseButtonPress:
987 case QEvent::MouseMove:
988 // HACK(sh_zam): Let's say the tap gesture is used by the canvas to launch the popup. Following that, a
989 // synthesized mousePress is sent and this arrives in our event filter here. But, this event was meant for the
990 // canvas (even though it blocks it), so we only act on the event if we got a TouchBegin on it first.
991 if (static_cast<QMouseEvent *>(event)->source() == Qt::MouseEventSynthesizedBySystem && !m_touchBeginReceived) {
992 event->accept();
993 return true;
994 }
995 break;
996 case QEvent::MouseButtonRelease:
997 if (static_cast<QMouseEvent *>(event)->source() == Qt::MouseEventSynthesizedBySystem && !m_touchBeginReceived) {
998 event->accept();
999 return true;
1000 }
1001 // fallthrough
1002 case QEvent::Show:
1003 case QEvent::FocusOut:
1004 m_touchBeginReceived = false;
1005 break;
1006 default:
1007 break;
1008 }
1009 return false;
1010}
KisMagneticGraph::vertex_descriptor source(typename KisMagneticGraph::edge_descriptor e, KisMagneticGraph g)

References m_touchBeginReceived, and source().

◆ findPresetSlot()

int KisPopupPalette::findPresetSlot ( QPointF position) const
protected

/ find the index of the brush preset slot containing @position.

Returns
-1 if none is found

Definition at line 1569 of file kis_popup_palette.cpp.

1570{
1571 QPointF adjustedPoint = position - QPointF(m_popupPaletteSize/2, m_popupPaletteSize/2);
1572 for (int i = 0; i < m_presetSlotCount; i++) {
1573 if (createPathFromPresetIndex(i).contains(adjustedPoint)) {
1574 return i;
1575 }
1576 }
1577 return -1;
1578}
QPainterPath createPathFromPresetIndex(int index) const

References createPathFromPresetIndex(), m_popupPaletteSize, and m_presetSlotCount.

◆ finished

void KisPopupPalette::finished ( )
overridesignal

◆ hoveredColor()

int KisPopupPalette::hoveredColor ( ) const
protected

Definition at line 475 of file kis_popup_palette.cpp.

476{
477 return m_hoveredColor;
478}

References m_hoveredColor.

◆ hoveredPreset()

int KisPopupPalette::hoveredPreset ( ) const
protected

Definition at line 465 of file kis_popup_palette.cpp.

466{
467 return m_hoveredPreset;
468}

References m_hoveredPreset.

◆ isPointInPixmap()

bool KisPopupPalette::isPointInPixmap ( QPointF & point,
int pos )
private

Definition at line 1213 of file kis_popup_palette.cpp.

1214{
1215 if (createPathFromPresetIndex(pos).contains(point + QPointF(-m_popupPaletteSize / 2, -m_popupPaletteSize / 2))) {
1216 return true;
1217 }
1218 return false;
1219}

References createPathFromPresetIndex(), and m_popupPaletteSize.

◆ mouseMoveEvent()

void KisPopupPalette::mouseMoveEvent ( QMouseEvent * event)
overrideprotected

Definition at line 829 of file kis_popup_palette.cpp.

830{
831 QPointF point = event->localPos();
832 event->accept();
833
835 // check if mouse is over the canvas rotation knob
836 bool wasOverRotationIndicator = m_isOverCanvasRotationIndicator;
838 bool wasOverResetRotationIndicator = m_isOverResetCanvasRotationIndicator;
840
841 if (
842 wasOverRotationIndicator != m_isOverCanvasRotationIndicator ||
843 wasOverResetRotationIndicator != m_isOverResetCanvasRotationIndicator
844 ) {
845 update();
846 }
847
849 m_snapRotation = false;
850 int i = 0;
851 for (QRect &rect: m_snapRects) {
852 QPainterPath circle;
853 circle.addEllipse(rect);
854 if (circle.contains(point)) {
855 m_snapRotation = true;
856 m_rotationSnapAngle = i * 15;
857 break;
858 }
859 i++;
860 }
861 qreal finalAngle = 0.0;
862 if (m_snapRotation) {
863 finalAngle = m_rotationSnapAngle;
864 // to match the numbers displayed when rotating without snapping
865 if (finalAngle >= 270) {
866 finalAngle = finalAngle - 360;
867 }
868 } else {
869 // we are rotating the canvas, so calculate the rotation angle based off the center
870 // calculate the angle we are at first
871 QPoint widgetCenterPoint = QPoint(m_popupPaletteSize/2, m_popupPaletteSize/2);
872
873 qreal dX = point.x() - widgetCenterPoint.x();
874 qreal dY = point.y() - widgetCenterPoint.y();
875
876
877 finalAngle = qAtan2(dY,dX) * 180 / M_PI; // what we need if we have two points, but don't know the angle
878 finalAngle = finalAngle + 90; // add 90 degrees so 0 degree position points up
879 }
880 qreal angleDifference = finalAngle - m_coordinatesConverter->rotationAngle(); // the rotation function accepts diffs, so find it out
881
882 KisCanvasController *canvasController =
884 KIS_ASSERT_RECOVER_RETURN(canvasController);
885 canvasController->rotateCanvas(angleDifference);
887
888 update();
889 Q_EMIT sigUpdateCanvas();
890 }
891 }
892
893 if (m_isRotatingCanvasIndicator == false) {
894 QPainterPath bgColor(drawFgBgColorIndicator(0));
895 QPainterPath fgColor(drawFgBgColorIndicator(1));
896 QPainterPath backgroundContainer;
898 backgroundContainer.addEllipse(circleRect);
899
900 QPainterPath fgBgColors = (fgColor + bgColor) - backgroundContainer;
901
902 if (fgBgColors.contains(point)) {
903 if (!m_isOverFgBgColors) {
904 m_isOverFgBgColors = true;
905 setToolTip(i18n("Click to swap foreground and background colors.\nRight click to set to black and white."));
906 update();
907 }
908 } else {
909 if (m_isOverFgBgColors) {
910 m_isOverFgBgColors = false;
911 setToolTip(QString());
912 update();
913 }
914 }
915
917 if (colorHistoryPath.contains(point)) {
918 if (hoveredPreset() >= 0) {
919 setToolTip(QString());
921 }
922
924
925 if (pos != hoveredColor()) {
926 setHoveredColor(pos);
927 update();
928 }
929 }
930 else {
931 if (hoveredColor() >= 0) {
932 setHoveredColor(-1);
933 update();
934 }
935
936 int pos = findPresetSlot(point);
937
938 if (pos != hoveredPreset()) {
939
940 if (pos >= 0 && pos < m_resourceManager->numFavoritePresets()) {
941 setToolTip(m_resourceManager->favoritePresetNamesList().at(pos));
942 setHoveredPreset(pos);
943 }
944 else {
945 setToolTip(QString());
947 }
948
949 update();
950 }
951 }
952 }
953}
void rotateCanvas(qreal angle, const std::optional< KoViewTransformStillPoint > &stillPoint, bool isNativeGesture=false)
QPainterPath drawFgBgColorIndicator(int type) const
void sigUpdateCanvas()
int findPresetSlot(QPointF position) const
/ find the index of the brush preset slot containing @position.
QRectF m_resetCanvasRotationIndicatorRect
QPainterPath drawDonutPathFull(int, int, int, int)
int calculateColorIndex(QPointF position, int numColors) const
Calculate index of recent color in array.
QRectF rotationIndicatorRect(qreal rotationAngle) const
bool m_isOverResetCanvasRotationIndicator
QRectF m_canvasRotationIndicatorRect
KisCanvas2 * canvasBase() const
Return the canvas base class.
KoCanvasController * canvasController() const
#define KIS_ASSERT_RECOVER_RETURN(cond)
Definition kis_assert.h:75

References BORDER_WIDTH, calculateColorIndex(), KisViewManager::canvasBase(), KoCanvasBase::canvasController(), drawDonutPathFull(), drawFgBgColorIndicator(), KisFavoriteResourceManager::favoritePresetNamesList(), findPresetSlot(), hoveredColor, hoveredPreset, KIS_ASSERT_RECOVER_RETURN, m_canvasRotationIndicatorRect, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius, m_coordinatesConverter, m_isOverCanvasRotationIndicator, m_isOverFgBgColors, m_isOverResetCanvasRotationIndicator, m_isRotatingCanvasIndicator, M_PI, m_popupPaletteSize, m_resetCanvasRotationIndicatorRect, m_resourceManager, m_rotationSnapAngle, m_showRotationTrack, m_snapRects, m_snapRotation, m_viewManager, KisFavoriteResourceManager::recentColorsTotal(), KisCanvasController::rotateCanvas(), KisCoordinatesConverter::rotationAngle(), rotationIndicatorRect(), setHoveredColor(), setHoveredPreset(), and sigUpdateCanvas().

◆ mousePressEvent()

void KisPopupPalette::mousePressEvent ( QMouseEvent * event)
overrideprotected

◆ mouseReleaseEvent()

void KisPopupPalette::mouseReleaseEvent ( QMouseEvent * event)
overrideprotected

We are in native and modal mode, so handle our closure ourselves

Definition at line 1147 of file kis_popup_palette.cpp.

1148{
1149 QPointF point = event->localPos();
1150 event->accept();
1151
1155#if QT_VERSION < QT_VERSION_CHECK(6, 0, 0)
1156 const QPointF localPos = event->localPos();
1157#else
1158 const QPointF localPos = event->position();
1159#endif
1160
1161 if (this->windowHandle() && !QRectF(rect()).contains(localPos)) {
1162 Q_EMIT finished();
1163 return;
1164 }
1165
1167 update();
1168 }
1169
1171
1172 if (event->button() == Qt::LeftButton) {
1173 if (m_isOverFgBgColors) {
1175 }
1176
1177 //in favorite brushes area
1178 if (hoveredPreset() > -1) {
1179 //setSelectedBrush(hoveredBrush());
1181 }
1182
1183 if (m_showColorHistory) {
1185 if (pathColor.contains(point)) {
1187
1188 if (pos >= 0 && pos < m_resourceManager->recentColorsTotal()) {
1189 Q_EMIT sigUpdateRecentColor(pos);
1190 }
1191 }
1192 }
1193 } else if (event->button() == Qt::RightButton) {
1194 Q_EMIT finished();
1195 }
1196}

References calculateColorIndex(), drawDonutPathFull(), finished(), hoveredPreset, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius, m_isOverFgBgColors, m_isRotatingCanvasIndicator, m_popupPaletteSize, m_resourceManager, m_showColorHistory, m_viewManager, KisFavoriteResourceManager::recentColorsTotal(), sigChangeActivePaintop(), sigUpdateRecentColor(), and KisViewManager::slotToggleFgBg().

◆ onScreen()

bool KisPopupPalette::onScreen ( )
overridevirtual

Returns whether the widget is active (on screen) or not.

Implements KisPopupWidgetInterface.

Definition at line 1090 of file kis_popup_palette.cpp.

1091{
1092 return isVisible();
1093}

◆ paintEvent()

void KisPopupPalette::paintEvent ( QPaintEvent * e)
overrideprotected

Definition at line 560 of file kis_popup_palette.cpp.

561{
562 Q_UNUSED(e);
563
564 QPainter painter(this);
565
566 QPen pen(palette().color(QPalette::Text), BORDER_WIDTH);
567 painter.setPen(pen);
568
569 painter.setRenderHint(QPainter::Antialiasing);
570 painter.setRenderHint(QPainter::SmoothPixmapTransform);
571
572 if (m_isOverFgBgColors) {
573 painter.save();
574 painter.setPen(QPen(palette().color(QPalette::Highlight), BORDER_WIDTH));
575 }
576
577 // painting background color indicator
578 QPainterPath bgColor(drawFgBgColorIndicator(0));
579 painter.fillPath(bgColor, m_displayRenderer->toQColor(m_resourceManager->bgColor()));
580 painter.drawPath(bgColor);
581
582 // painting foreground color indicator
583 QPainterPath fgColor(drawFgBgColorIndicator(1));
584 painter.fillPath(fgColor, m_displayRenderer->toQColor(m_colorSelector->getCurrentColor()));
585 painter.drawPath(fgColor);
586
587 if (m_isOverFgBgColors) painter.restore();
588
589
590 // create a circle background that everything else will go into
591 QPainterPath backgroundContainer;
592
593 // draws the circle halfway into the border so that the border never goes past the bounds of the popup
595 backgroundContainer.addEllipse(circleRect);
596 painter.fillPath(backgroundContainer, palette().brush(QPalette::Window));
597 painter.drawPath(backgroundContainer);
598
600 painter.save();
601 QPen pen(palette().color(QPalette::Window).lighter(150), 2);
602 painter.setPen(pen);
603
604 // draw rotation snap lines
606 for (QLineF &line: m_snapLines) {
607 painter.drawLine(line);
608 }
609 }
610 // create a path slightly inside the container circle. this will create a 'track' to indicate that we can rotate the canvas
611 // with the indicator
612 QPainterPath rotationTrackPath;
613 QRectF circleRect2(m_rotationTrackSize, m_rotationTrackSize,
615
616 rotationTrackPath.addEllipse(circleRect2);
617 painter.drawPath(rotationTrackPath);
618
619 // create a reset canvas rotation indicator to bring the canvas back to 0 degrees
620 QRectF resetRotationIndicator = m_resetCanvasRotationIndicatorRect;
621
623 ? palette().color(QPalette::Highlight)
624 : palette().color(QPalette::Text));
625 // cover the first snap line
626 painter.setBrush(palette().brush(QPalette::Window));
627 painter.setPen(pen);
628 painter.drawEllipse(resetRotationIndicator);
629
630 // create the canvas rotation handle
631 // highlight if either just hovering or currently rotating
633 ? palette().color(QPalette::Highlight)
634 : palette().color(QPalette::Text));
635 painter.setPen(pen);
636
637 // fill with highlight if snapping
639 ? palette().brush(QPalette::Highlight)
640 : palette().brush(QPalette::Text));
641
642 // gotta update the rect, see bug 459801
643 // (note: it can't just update when it shows up because then rotating when popup palette is on the screen wouldn't make an effect)
645 painter.drawEllipse(m_canvasRotationIndicatorRect);
646
647 painter.restore();
648 }
649
650 // the following things needs to be based off the center, so let's translate the painter
651 painter.translate(m_popupPaletteSize / 2, m_popupPaletteSize / 2);
652
653 // painting favorite brushes
655
656 // painting favorite brushes pixmap/icon
657 QPainterPath presetPath;
658 int presetCount = images.size();
659 bool isTagEmpty = presetCount == 0;
660 for (int pos = 0; pos < m_presetSlotCount; pos++) {
661 painter.save();
662 presetPath = createPathFromPresetIndex(pos);
663
664 if (pos < presetCount) {
665 painter.setClipPath(presetPath);
666
667 QRect bounds = presetPath.boundingRect().toAlignedRect();
668 if (!images.at(pos).isNull()) {
669 QImage previewHighDPI = images.at(pos).scaled(bounds.size()*devicePixelRatioF() , Qt::KeepAspectRatioByExpanding, Qt::SmoothTransformation);
670 previewHighDPI.setDevicePixelRatio(devicePixelRatioF());
671 painter.drawImage(bounds.topLeft(), previewHighDPI);
672 }
673 } else {
674 painter.fillPath(presetPath, palette().brush(QPalette::Window)); // brush slot that has no brush in it
675 }
676 // needs to be called here so that the clipping is removed
677 painter.restore();
678 // if the slot is empty, stroke it slightly darker
679 QColor color = isTagEmpty || pos >= presetCount
680 ? palette().color(QPalette::Window).lighter(150)
681 : palette().color(QPalette::Text);
682 painter.setPen(QPen(color, 1));
683 painter.drawPath(presetPath);
684 }
685 if (hoveredPreset() > -1) {
687 painter.setPen(QPen(palette().color(QPalette::Highlight), BORDER_WIDTH));
688 painter.drawPath(presetPath);
689 }
690
691 if (m_showColorHistory) {
692 // paint recent colors area.
693 painter.setPen(Qt::NoPen);
694 const qreal rotationAngle = 360.0 / m_resourceManager->recentColorsTotal();
695 const qreal rotationOffset = 180.0;
696
697 painter.rotate(rotationOffset);
698
699 // there might be no recent colors at the start, so paint a placeholder
701 painter.setBrush(Qt::transparent);
702
703 QPainterPath emptyRecentColorsPath(drawDonutPathFull(0, 0, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius));
704 painter.setPen(QPen(palette().color(QPalette::Window).lighter(150), 2, Qt::SolidLine, Qt::FlatCap, Qt::MiterJoin));
705 painter.drawPath(emptyRecentColorsPath);
706 } else {
707 for (int pos = 0; pos < m_resourceManager->recentColorsTotal(); pos++) {
709
710 //accessing recent color of index pos
711 painter.fillPath(recentColorsPath, m_displayRenderer->toQColor( m_resourceManager->recentColorAt(pos) ));
712 painter.drawPath(recentColorsPath);
713 painter.rotate(rotationAngle);
714 }
715 }
716
717 // painting hovered color
718 if (hoveredColor() > -1) {
719 painter.setPen(QPen(palette().color(QPalette::Highlight), 2, Qt::SolidLine, Qt::FlatCap, Qt::MiterJoin));
720
722 QPainterPath path_ColorDonut(drawDonutPathFull(0, 0, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius));
723 painter.drawPath(path_ColorDonut);
724 } else {
725 painter.rotate((m_resourceManager->recentColorsTotal() + hoveredColor()) * rotationAngle);
727 painter.drawPath(path);
728 painter.rotate(hoveredColor() * -1 * rotationAngle);
729 }
730 }
731
732 // painting selected color
733 if (selectedColor() > -1) {
734 painter.setPen(QPen(palette().color(QPalette::Highlight).darker(130), 2, Qt::SolidLine, Qt::FlatCap, Qt::MiterJoin));
735
737 QPainterPath path_ColorDonut(drawDonutPathFull(0, 0, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius));
738 painter.drawPath(path_ColorDonut);
739 } else {
740 painter.rotate((m_resourceManager->recentColorsTotal() + selectedColor()) * rotationAngle);
742 painter.drawPath(path);
743 painter.rotate(selectedColor() * -1 * rotationAngle);
744 }
745 }
746 }
747
748
749 // if we are actively rotating the canvas or zooming, make the panel slightly transparent to see the canvas better
751 opacityChange->setOpacity(0.4);
752 } else {
753 opacityChange->setOpacity(1.0);
754 }
755
756}
virtual KoColor getCurrentColor() const =0
QPainterPath drawDonutPathAngle(int, int, int)
KisColorSelectorInterface * m_colorSelector
virtual QColor toQColor(const KoColor &c, bool proofToPaintColors=false) const =0
#define bounds(x, a, b)
rgba palette[MAX_PALETTE]
Definition palette.c:35

References KisFavoriteResourceManager::bgColor(), BORDER_WIDTH, bounds, createPathFromPresetIndex(), drawDonutPathAngle(), drawDonutPathFull(), drawFgBgColorIndicator(), KisFavoriteResourceManager::favoritePresetImages(), KisColorSelectorInterface::getCurrentColor(), hoveredColor, hoveredPreset, m_canvasRotationIndicatorRect, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius, m_colorSelector, m_coordinatesConverter, m_displayRenderer, m_isOverCanvasRotationIndicator, m_isOverFgBgColors, m_isOverResetCanvasRotationIndicator, m_isRotatingCanvasIndicator, m_isZoomingCanvas, m_popupPaletteSize, m_presetSlotCount, m_resetCanvasRotationIndicatorRect, m_resourceManager, m_rotationTrackSize, m_showColorHistory, m_showRotationTrack, m_snapLines, m_snapRotation, opacityChange, palette, KisFavoriteResourceManager::recentColorAt(), KisFavoriteResourceManager::recentColorsTotal(), KisCoordinatesConverter::rotationAngle(), rotationIndicatorRect(), selectedColor, and KoColorDisplayRendererInterface::toQColor().

◆ popup()

void KisPopupPalette::popup ( const QPoint & position)
overridevirtual

Called when and where you want a widget to popup.

Implements KisPopupWidgetInterface.

Definition at line 1077 of file kis_popup_palette.cpp.

1077 {
1078 setVisible(true);
1079 KIS_SAFE_ASSERT_RECOVER_RETURN(parentWidget());
1080 const QPoint globalPos = parentWidget()->mapToGlobal(position);
1081 ensureWithinParent(globalPos, false);
1082 m_mirrorPos = QCursor::pos();
1083}
void ensureWithinParent(const QPoint &globalPos, bool useUpperLeft)
#define KIS_SAFE_ASSERT_RECOVER_RETURN(cond)
Definition kis_assert.h:128

References ensureWithinParent(), KIS_SAFE_ASSERT_RECOVER_RETURN, and m_mirrorPos.

◆ reconfigure()

void KisPopupPalette::reconfigure ( )
private

Definition at line 293 of file kis_popup_palette.cpp.

294{
295 KisConfig config(true);
296 m_useDynamicSlotCount = config.readEntry("popuppalette/useDynamicSlotCount", true);
297 m_maxPresetSlotCount = config.favoritePresets();
299 int presetCount = m_resourceManager->numFavoritePresets();
300 // if there are no presets because the tag is empty
301 // show the maximum number allowed (they will be painted as empty slots)
302 m_presetSlotCount = presetCount == 0
305 } else {
307 }
308 m_popupPaletteSize = config.readEntry("popuppalette/size", 385);
309 qreal selectorRadius = config.readEntry("popuppalette/selectorSize", 140) / 2.0;
310
311 m_showColorHistory = config.readEntry("popuppalette/showColorHistory", true);
312 m_showRotationTrack = config.readEntry("popuppalette/showRotationTrack", true);
313
316 if (m_showColorHistory) {
318 m_clearColorHistoryButton->setVisible(true);
319 } else {
320 m_clearColorHistoryButton->setVisible(false);
321 }
322
324
325 bool useVisualSelector = config.readEntry<bool>("popuppalette/usevisualcolorselector", false);
326 if (m_colorSelector) {
327 // if the selector type changed, delete it
328 bool haveVisualSelector = qobject_cast<KisVisualColorSelector*>(m_colorSelector) != 0;
329 if (useVisualSelector != haveVisualSelector) {
330 delete m_colorSelector;
331 m_colorSelector = 0;
332 }
333 }
334 if (!m_colorSelector) {
335 if (useVisualSelector) {
337 selector->setAcceptTabletEvents(true);
338 connect(KisConfigNotifier::instance(), SIGNAL(configChanged()),
339 selector, SLOT(slotConfigurationChanged()));
340 m_colorSelector = selector;
341 }
342 else {
344 connect(m_colorSelector, SIGNAL(requestCloseContainer()), this, SIGNAL(finished()));
345 connect(KisConfigNotifier::instance(), SIGNAL(configChanged()),
346 m_colorSelector, SLOT(configurationChanged()));
347 }
349 m_colorSelector->setConfig(true,false);
350 m_colorSelector->setVisible(true);
352 connect(m_colorSelector, SIGNAL(sigNewColor(KoColor)),
353 m_colorChangeCompressor.data(), SLOT(start()));
354
355 }
356
357
358 const int auxButtonSize = 35;
359 m_colorSelector->move(m_popupPaletteSize/2 - selectorRadius, m_popupPaletteSize/2 - selectorRadius);
361
362 // ellipse - to make sure the widget doesn't eat events meant for recent colors or brushes
363 // - needs to be +2 pixels on every side for anti-aliasing to look nice on high dpi displays
364 // rectangle - to make sure the area doesn't extend outside of the widget
365 QRegion maskedEllipse(-2, -2, m_colorSelector->width() + 4, m_colorSelector->height() + 4, QRegion::Ellipse );
366 QRegion maskedRectangle(0, 0, m_colorSelector->width(), m_colorSelector->height(), QRegion::Rectangle);
367 QRegion maskedRegion = maskedEllipse.intersected(maskedRectangle);
368
369 m_colorSelector->setMask(maskedRegion);
370
371 m_dockerHud->setFixedHeight(int(m_popupPaletteSize));
372
373 // arranges the buttons around the popup palette
374 // buttons are spread out from the center of the set arc length
375
376 // the margin in degrees between buttons
377 qreal margin = 10.0;
378 // visual center
379 qreal center = m_popupPaletteSize/2 - auxButtonSize/2.0;
380 qreal length = m_popupPaletteSize/2 + auxButtonSize/2.0 + 5;
381 {
382 int buttonCount = 2;
383 int arcLength = 90;
384 // note the int buttonCount/2 is on purpose
385 qreal start = arcLength/2 - (buttonCount/2) * margin;
386 if (buttonCount % 2 == 0) start += margin / 2;
387 int place = 0;
388 m_dockerHudButton->setGeometry(
389 center + qCos(qDegreesToRadians(start + place*margin))*length,
390 center + qSin(qDegreesToRadians(start + place*margin))*length,
391 auxButtonSize, auxButtonSize
392 );
393 place++;
394 m_bottomBarButton->setGeometry (
395 center + qCos(qDegreesToRadians(start + place*margin))*length,
396 center + qSin(qDegreesToRadians(start + place*margin))*length,
397 auxButtonSize, auxButtonSize
398 );
399 }
400 {
401 int buttonCount = m_showColorHistory ? 2 : 1 ;
402 int arcLength = 90;
403 int shiftArc = 90;
404 // note the int buttonCount/2 is on purpose
405 qreal start = shiftArc + arcLength / 2 - (buttonCount/2) * margin;
406 if (buttonCount % 2 == 0) start += margin / 2;
407 int place = 0;
408 if (m_showColorHistory) {
409 m_clearColorHistoryButton->setGeometry(
410 center + qCos(qDegreesToRadians(start + place * margin)) * length,
411 center + qSin(qDegreesToRadians(start + place * margin)) * length,
412 auxButtonSize, auxButtonSize);
413 place++;
414 }
415 m_tagsButton->setGeometry(
416 center + qCos(qDegreesToRadians(start + place*margin))*length,
417 center + qSin(qDegreesToRadians(start + place*margin))*length,
418 auxButtonSize, auxButtonSize
419 );
420 }
422}
virtual void setDisplayRenderer(const KoColorDisplayRendererInterface *displayRenderer)
virtual void setConfig(bool forceCircular, bool forceSelfUpdate)
void calculatePresetLayout()
Determine the number of rings to distribute the presets and calculate the radius of the brush preset ...
The KisVisualColorSelector class.

References calculatePresetLayout(), connect(), KisConfig::favoritePresets(), finished(), KisConfigNotifier::instance(), length(), m_bottomBarButton, m_clearColorHistoryButton, m_colorChangeCompressor, m_colorHistoryInnerRadius, m_colorHistoryOuterRadius, m_colorSelector, m_displayRenderer, m_dockerHud, m_dockerHudButton, m_mainArea, m_maxPresetSlotCount, m_popupPaletteSize, m_presetRingMargin, m_presetSlotCount, m_resourceManager, m_showColorHistory, m_showRotationTrack, m_tagsButton, m_useDynamicSlotCount, KisFavoriteResourceManager::numFavoritePresets(), KisConfig::readEntry(), KisVisualColorSelector::setAcceptTabletEvents(), KisColorSelectorInterface::setConfig(), KisColorSelectorInterface::setDisplayRenderer(), slotConfigurationChanged(), and slotDisplayConfigurationChanged().

◆ resizeEvent()

void KisPopupPalette::resizeEvent ( QResizeEvent * resizeEvent)
overrideprotected

When popup is native, its geometry report the global position; then the popup is non-native, its geometry is in its parent's coordinate system.

Definition at line 758 of file kis_popup_palette.cpp.

758 {
759 Q_UNUSED(resizeEvent);
763 // Ensure that the resized geometry fits within the desired rect...
764
770 const QPoint globalTopLeft = windowHandle() ?
771 geometry().topLeft() :
772 parentWidget()->mapToGlobal(geometry().topLeft());
773 ensureWithinParent(globalTopLeft, true);
774}
void resizeEvent(QResizeEvent *) override

References calculateRotationSnapAreas(), ensureWithinParent(), m_canvasRotationIndicatorRect, m_coordinatesConverter, m_resetCanvasRotationIndicatorRect, resizeEvent(), KisCoordinatesConverter::rotationAngle(), and rotationIndicatorRect().

◆ rotationIndicatorRect()

QRectF KisPopupPalette::rotationIndicatorRect ( qreal rotationAngle) const
private

Definition at line 819 of file kis_popup_palette.cpp.

820{
821 qreal paletteRadius = 0.5 * m_popupPaletteSize;
822 QPointF rotationDialPosition(drawPointOnAngle(rotationAngle, paletteRadius - 10));
823 rotationDialPosition += QPointF(paletteRadius, paletteRadius);
824
825 QPointF indicatorDiagonal(7.5, 7.5);
826 return QRectF(rotationDialPosition - indicatorDiagonal, rotationDialPosition + indicatorDiagonal);
827}

References drawPointOnAngle(), and m_popupPaletteSize.

◆ selectedColor()

int KisPopupPalette::selectedColor ( ) const

Definition at line 485 of file kis_popup_palette.cpp.

486{
487 return m_selectedColor;
488}

References m_selectedColor.

◆ setHoveredColor()

void KisPopupPalette::setHoveredColor ( int x)
protected

Definition at line 480 of file kis_popup_palette.cpp.

References m_hoveredColor.

◆ setHoveredPreset()

void KisPopupPalette::setHoveredPreset ( int x)
protected

Definition at line 470 of file kis_popup_palette.cpp.

471{
473}

References m_hoveredPreset.

◆ setParent()

void KisPopupPalette::setParent ( QWidget * parent)

Definition at line 548 of file kis_popup_palette.cpp.

548 {
549 QWidget::setParent(parent);
550}

◆ setSelectedColor()

void KisPopupPalette::setSelectedColor ( int x)

Definition at line 490 of file kis_popup_palette.cpp.

491{
493}

References m_selectedColor.

◆ showBottomBarWidget

void KisPopupPalette::showBottomBarWidget ( bool visible)
privateslot

Definition at line 538 of file kis_popup_palette.cpp.

539{
540 const bool reallyVisible = visible && m_bottomBarButton->isChecked();
541
542 m_bottomBarWidget->setVisible(reallyVisible);
543
544 KisConfig cfg(false);
545 cfg.setShowPaletteBottomBar(visible);
546}

References m_bottomBarButton, m_bottomBarWidget, and KisConfig::setShowPaletteBottomBar().

◆ showEvent()

void KisPopupPalette::showEvent ( QShowEvent * event)
overrideprotected

Definition at line 1123 of file kis_popup_palette.cpp.

1124{
1126
1127 // don't set the zoom slider if we are outside of the zoom slider bounds. It will change the zoom level to within
1128 // the bounds and cause the canvas to jump between the slider's min and max
1132 zoomCanvasSlider->setValue(m_coordinatesConverter->zoomInPercent()); // sync the zoom slider
1133 }
1134
1135 QWidget::showEvent(event);
1136}

References m_clicksEater, m_coordinatesConverter, KisMouseClickEater::reset(), zoomCanvasSlider, KoZoomHandler::zoomInPercent(), zoomSliderMaxValue, and zoomSliderMinValue.

◆ showHudWidget

void KisPopupPalette::showHudWidget ( bool visible)
privateslot

Definition at line 528 of file kis_popup_palette.cpp.

529{
531 const bool reallyVisible = visible && m_dockerHudButton->isChecked();
532 m_dockerHud->setVisible(reallyVisible);
533
534 KisConfig cfg(false);
535 cfg.setShowBrushHud(visible);
536}
void setIsShown(bool isShown)

References m_dockerHud, m_dockerHudButton, KisDockerHud::setIsShown(), and KisConfig::setShowBrushHud().

◆ sigChangeActivePaintop

void KisPopupPalette::sigChangeActivePaintop ( int )
signal

◆ sigChangefGColor

void KisPopupPalette::sigChangefGColor ( const KoColor & )
signal

◆ sigUpdateCanvas

void KisPopupPalette::sigUpdateCanvas ( )
signal

◆ sigUpdateRecentColor

void KisPopupPalette::sigUpdateRecentColor ( int )
signal

◆ sizeHint()

QSize KisPopupPalette::sizeHint ( ) const
override

Definition at line 553 of file kis_popup_palette.cpp.

554{
555 // Note: the canvas popup widget system "abuses" the sizeHint to determine
556 // the position to show the widget; this does not reflect the true size.
558}

References m_popupPaletteSize.

◆ slotConfigurationChanged

void KisPopupPalette::slotConfigurationChanged ( )
privateslot

Definition at line 287 of file kis_popup_palette.cpp.

288{
289 reconfigure();
290 layout()->invalidate();
291}

References reconfigure().

◆ slotDisplayConfigurationChanged

void KisPopupPalette::slotDisplayConfigurationChanged ( )
privateslot

Definition at line 424 of file kis_popup_palette.cpp.

425{
426 // Visual Color Selector picks up color space from input
429 //hack to get around cmyk for now.
430 if (paintingCS->colorChannelCount()>3) {
431 paintingCS = KoColorSpaceRegistry::instance()->rgb8();
432 }
435}
virtual void slotSetColor(const KoColor &c)=0
virtual void slotSetColorSpace(const KoColorSpace *cs)
slotSetColorSpace Set the color space the selector should cover
virtual const KoColorSpace * getPaintingColorSpace() const =0
getColorSpace
virtual quint32 colorChannelCount() const =0
static KoColorSpaceRegistry * instance()
const KoColorSpace * rgb8(const QString &profileName=QString())

References KisViewManager::canvasResourceProvider(), KoColorSpace::colorChannelCount(), KisCanvasResourceProvider::fgColor(), KoColorDisplayRendererInterface::getPaintingColorSpace(), KoColorSpaceRegistry::instance(), m_colorSelector, m_displayRenderer, m_viewManager, KoColorSpaceRegistry::rgb8(), KisColorSelectorInterface::slotSetColor(), and KisColorSelectorInterface::slotSetColorSpace().

◆ slotEmitColorChanged

void KisPopupPalette::slotEmitColorChanged ( )
privateslot

Definition at line 444 of file kis_popup_palette.cpp.

445{
446 if (isVisible()) {
447 update();
449 }
450}

References KisColorSelectorInterface::getCurrentColor(), m_colorSelector, and sigChangefGColor().

◆ slotExternalFgColorChanged

void KisPopupPalette::slotExternalFgColorChanged ( const KoColor & color)
privateslot

◆ slotFitToViewClicked

void KisPopupPalette::slotFitToViewClicked ( )
privateslot

Definition at line 1059 of file kis_popup_palette.cpp.

1059 {
1060 QAction *action = m_actionCollection->action("zoom_to_fit");
1061
1062 if (action) {
1063 action->trigger();
1064 }
1065
1066 // sync zoom slider
1068}

References KisKActionCollection::action(), m_actionCollection, m_coordinatesConverter, zoomCanvasSlider, and KoZoomHandler::zoomInPercent().

◆ slotRemoveMirrorPos

void KisPopupPalette::slotRemoveMirrorPos ( )
privateslot

Definition at line 1073 of file kis_popup_palette.cpp.

1073 {
1074 m_actionCollection->action("mirror_canvas_around_cursor")->setProperty("customPosition", QVariant());
1075}

References KisKActionCollection::action(), and m_actionCollection.

◆ slotSetMirrorPos

void KisPopupPalette::slotSetMirrorPos ( )
privateslot

Definition at line 1070 of file kis_popup_palette.cpp.

1070 {
1071 m_actionCollection->action("mirror_canvas_around_cursor")->setProperty("customPosition", QVariant(m_mirrorPos));
1072}

References KisKActionCollection::action(), m_actionCollection, and m_mirrorPos.

◆ slotSetSelectedColor

void KisPopupPalette::slotSetSelectedColor ( int x)
inlineprivateslot

Definition at line 202 of file kis_popup_palette.h.

202{ setSelectedColor(x); update(); }

References setSelectedColor().

◆ slotShowTagsPopup

void KisPopupPalette::slotShowTagsPopup ( )
privateslot

Definition at line 1012 of file kis_popup_palette.cpp.

1013{
1015 QVector<QString> tags;
1016 for (int i = 0; i < model.rowCount(); ++i) {
1017 QModelIndex idx = model.index(i, 0);
1018 tags << model.data(idx, Qt::DisplayRole).toString();
1019 }
1020
1021 //std::sort(tags.begin(), tags.end());
1022
1023 if (!tags.isEmpty()) {
1024 QMenu menu;
1025 Q_FOREACH (const QString& tag, tags) {
1026 menu.addAction(tag)->setData(tag);
1027 }
1028
1029 QAction *action = menu.exec(QCursor::pos());
1030 if (action) {
1031
1032 for (int i = 0; i < model.rowCount(); ++i) {
1033 QModelIndex idx = model.index(i, 0);
1034 if (model.data(idx, Qt::DisplayRole).toString() == action->data()) {
1035 m_resourceManager->setCurrentTag(model.tagForIndex(idx));
1036 reconfigure();
1037 break;
1038 }
1039 }
1040 }
1041 } else {
1042 QWhatsThis::showText(QCursor::pos(),
1043 i18n("There are no tags available to show in this popup. To add presets, you need to tag them and then select the tag here."));
1044 }
1045
1046}
const QString PaintOpPresets

References m_resourceManager, ResourceType::PaintOpPresets, reconfigure(), KisFavoriteResourceManager::setCurrentTag(), and KisTagModel::tagForIndex().

◆ slotUpdate

◆ slotUpdateIcons

void KisPopupPalette::slotUpdateIcons ( )
slot

Definition at line 509 of file kis_popup_palette.cpp.

510{
511 this->setPalette(qApp->palette());
512
513 for(int i=0; i<this->children().size(); i++) {
514 QWidget *w = qobject_cast<QWidget*>(this->children().at(i));
515 if (w) {
516 w->setPalette(qApp->palette());
517 }
518 }
519 zoomToOneHundredPercentButton->setIcon(m_actionCollection->action("zoom_to_100pct")->icon());
520 fitToViewButton->setIcon(m_actionCollection->action("zoom_to_fit")->icon());
522 m_tagsButton->setIcon(KisIconUtils::loadIcon("tag"));
523 m_clearColorHistoryButton->setIcon(KisIconUtils::loadIcon("reload-preset-16"));
526}
void slotUpdateIcons()
void setOnOffIcons(const QIcon &on, const QIcon &off)
QIcon loadIcon(const QString &name)

References KisKActionCollection::action(), fitToViewButton, KisIconUtils::loadIcon(), m_actionCollection, m_bottomBarButton, m_clearColorHistoryButton, m_dockerHud, m_dockerHudButton, m_tagsButton, KisRoundHudButton::setOnOffIcons(), KisDockerHud::slotUpdateIcons(), and zoomToOneHundredPercentButton.

◆ slotZoomSliderChanged

void KisPopupPalette::slotZoomSliderChanged ( int zoom)
privateslot

Definition at line 495 of file kis_popup_palette.cpp.

495 {
496 Q_EMIT zoomLevelChanged(zoom);
497}
void zoomLevelChanged(int)

References zoomLevelChanged().

◆ slotZoomSliderPressed

void KisPopupPalette::slotZoomSliderPressed ( )
privateslot

Definition at line 499 of file kis_popup_palette.cpp.

500{
501 m_isZoomingCanvas = true;
502}

References m_isZoomingCanvas.

◆ slotZoomSliderReleased

void KisPopupPalette::slotZoomSliderReleased ( )
privateslot

Definition at line 504 of file kis_popup_palette.cpp.

505{
506 m_isZoomingCanvas = false;
507}

References m_isZoomingCanvas.

◆ slotZoomToOneHundredPercentClicked

void KisPopupPalette::slotZoomToOneHundredPercentClicked ( )
privateslot

Definition at line 1048 of file kis_popup_palette.cpp.

1048 {
1049 QAction *action = m_actionCollection->action("zoom_to_100pct");
1050
1051 if (action) {
1052 action->trigger();
1053 }
1054
1055 // also move the zoom slider to 100% position so they are in sync
1056 zoomCanvasSlider->setValue(100);
1057}

References KisKActionCollection::action(), m_actionCollection, and zoomCanvasSlider.

◆ tabletEvent()

void KisPopupPalette::tabletEvent ( QTabletEvent * event)
overrideprotected

Definition at line 1138 of file kis_popup_palette.cpp.

1139{
1140 if (event->button() == Qt::RightButton && event->type() == QEvent::TabletPress) {
1142 }
1143
1144 event->ignore();
1145}

References m_tabletRightClickPressed.

◆ zoomLevelChanged

void KisPopupPalette::zoomLevelChanged ( int )
signal

Member Data Documentation

◆ canvasOnlyButton

KisHighlightedToolButton* KisPopupPalette::canvasOnlyButton {0}
private

Definition at line 170 of file kis_popup_palette.h.

170{0};

◆ fitToViewButton

QPushButton* KisPopupPalette::fitToViewButton {0}
private

Definition at line 172 of file kis_popup_palette.h.

172{0};

◆ m_actionCollection

KisKActionCollection* KisPopupPalette::m_actionCollection
private

Definition at line 145 of file kis_popup_palette.h.

◆ m_actionManager

KisActionManager* KisPopupPalette::m_actionManager
private

Definition at line 140 of file kis_popup_palette.h.

◆ m_acyclicConnector

KisAcyclicSignalConnector* KisPopupPalette::m_acyclicConnector = 0
private

Definition at line 176 of file kis_popup_palette.h.

◆ m_bottomBarButton

KisRoundHudButton* KisPopupPalette::m_bottomBarButton {0}
private

Definition at line 160 of file kis_popup_palette.h.

160{0};

◆ m_bottomBarWidget

QWidget* KisPopupPalette::m_bottomBarWidget {0}
private

Definition at line 149 of file kis_popup_palette.h.

149{0};

◆ m_cachedPresetLayout

CachedPresetLayout KisPopupPalette::m_cachedPresetLayout
private

Definition at line 178 of file kis_popup_palette.h.

◆ m_canvasRotationIndicatorRect

QRectF KisPopupPalette::m_canvasRotationIndicatorRect
private

Definition at line 162 of file kis_popup_palette.h.

◆ m_clearColorHistoryButton

KisRoundHudButton* KisPopupPalette::m_clearColorHistoryButton {0}
private

Definition at line 158 of file kis_popup_palette.h.

158{0};

◆ m_clicksEater

KisMouseClickEater* KisPopupPalette::m_clicksEater
private

Definition at line 182 of file kis_popup_palette.h.

◆ m_colorChangeCompressor

QScopedPointer<KisSignalCompressor> KisPopupPalette::m_colorChangeCompressor
private

Definition at line 144 of file kis_popup_palette.h.

◆ m_colorHistoryInnerRadius

qreal KisPopupPalette::m_colorHistoryInnerRadius {72.0}
private

Definition at line 151 of file kis_popup_palette.h.

151{72.0};

◆ m_colorHistoryOuterRadius

qreal KisPopupPalette::m_colorHistoryOuterRadius {92.0}
private

Definition at line 152 of file kis_popup_palette.h.

152{92.0};

◆ m_colorSelector

KisColorSelectorInterface* KisPopupPalette::m_colorSelector {0}
private

Definition at line 142 of file kis_popup_palette.h.

142{0};

◆ m_coordinatesConverter

KisCoordinatesConverter* KisPopupPalette::m_coordinatesConverter
private

Definition at line 137 of file kis_popup_palette.h.

◆ m_displayRenderer

const KoColorDisplayRendererInterface* KisPopupPalette::m_displayRenderer
private

Definition at line 143 of file kis_popup_palette.h.

◆ m_dockerHud

KisDockerHud* KisPopupPalette::m_dockerHud {0}
private

Definition at line 148 of file kis_popup_palette.h.

148{0};

◆ m_dockerHudButton

KisRoundHudButton* KisPopupPalette::m_dockerHudButton {0}
private

Definition at line 161 of file kis_popup_palette.h.

161{0};

◆ m_hoveredColor

int KisPopupPalette::m_hoveredColor {0}
private

Definition at line 126 of file kis_popup_palette.h.

126{0};

◆ m_hoveredPreset

int KisPopupPalette::m_hoveredPreset {0}
private

Definition at line 124 of file kis_popup_palette.h.

124{0};

◆ m_isOverCanvasRotationIndicator

bool KisPopupPalette::m_isOverCanvasRotationIndicator {false}
private

Definition at line 164 of file kis_popup_palette.h.

164{false};

◆ m_isOverFgBgColors

bool KisPopupPalette::m_isOverFgBgColors {false}
private

Definition at line 130 of file kis_popup_palette.h.

130{false};

◆ m_isOverResetCanvasRotationIndicator

bool KisPopupPalette::m_isOverResetCanvasRotationIndicator {false}
private

Definition at line 165 of file kis_popup_palette.h.

165{false};

◆ m_isRotatingCanvasIndicator

bool KisPopupPalette::m_isRotatingCanvasIndicator {false}
private

Definition at line 166 of file kis_popup_palette.h.

166{false};

◆ m_isZoomingCanvas

bool KisPopupPalette::m_isZoomingCanvas {false}
private

Definition at line 167 of file kis_popup_palette.h.

167{false};

◆ m_mainArea

QSpacerItem* KisPopupPalette::m_mainArea {0}
private

Definition at line 147 of file kis_popup_palette.h.

147{0};

◆ m_maxPresetSlotCount

int KisPopupPalette::m_maxPresetSlotCount {10}
private

Definition at line 122 of file kis_popup_palette.h.

122{10};

◆ m_mirrorPos

QPoint KisPopupPalette::m_mirrorPos {}
private

Definition at line 121 of file kis_popup_palette.h.

121{};

◆ m_popupPaletteSize

qreal KisPopupPalette::m_popupPaletteSize {385.0}
private

Definition at line 150 of file kis_popup_palette.h.

150{385.0};

◆ m_presetRingMargin

qreal KisPopupPalette::m_presetRingMargin {3.0}
private

Definition at line 156 of file kis_popup_palette.h.

156{3.0};

◆ m_presetSlotCount

int KisPopupPalette::m_presetSlotCount {10}
private

Definition at line 123 of file kis_popup_palette.h.

123{10};

◆ m_resetCanvasRotationIndicatorRect

QRectF KisPopupPalette::m_resetCanvasRotationIndicatorRect
private

Definition at line 163 of file kis_popup_palette.h.

◆ m_resourceManager

KisFavoriteResourceManager* KisPopupPalette::m_resourceManager
private

Definition at line 141 of file kis_popup_palette.h.

◆ m_rotationSnapAngle

qreal KisPopupPalette::m_rotationSnapAngle {0}
private

Definition at line 132 of file kis_popup_palette.h.

132{0};

◆ m_rotationTrackSize

qreal KisPopupPalette::m_rotationTrackSize {18.0}
private

Definition at line 154 of file kis_popup_palette.h.

154{18.0};

◆ m_selectedColor

int KisPopupPalette::m_selectedColor {0}
private

Definition at line 127 of file kis_popup_palette.h.

127{0};

◆ m_showColorHistory

bool KisPopupPalette::m_showColorHistory {true}
private

Definition at line 153 of file kis_popup_palette.h.

153{true};

◆ m_showRotationTrack

bool KisPopupPalette::m_showRotationTrack {true}
private

Definition at line 155 of file kis_popup_palette.h.

155{true};

◆ m_snapLines

std::array<QLineF, 24> KisPopupPalette::m_snapLines {}
private

Definition at line 135 of file kis_popup_palette.h.

135{};

◆ m_snapRadius

qreal KisPopupPalette::m_snapRadius {15}
private

Definition at line 133 of file kis_popup_palette.h.

133{15};

◆ m_snapRects

std::array<QRect, 24> KisPopupPalette::m_snapRects {}
private

Definition at line 134 of file kis_popup_palette.h.

134{};

◆ m_snapRotation

bool KisPopupPalette::m_snapRotation {false}
private

Definition at line 131 of file kis_popup_palette.h.

131{false};

◆ m_tabletRightClickPressed

bool KisPopupPalette::m_tabletRightClickPressed {false}
private

Definition at line 128 of file kis_popup_palette.h.

128{false};

◆ m_tagsButton

KisRoundHudButton* KisPopupPalette::m_tagsButton {0}
private

Definition at line 159 of file kis_popup_palette.h.

159{0};

◆ m_touchBeginReceived

bool KisPopupPalette::m_touchBeginReceived {false}
private

Definition at line 129 of file kis_popup_palette.h.

129{false};

◆ m_useDynamicSlotCount

bool KisPopupPalette::m_useDynamicSlotCount {true}
private

Definition at line 125 of file kis_popup_palette.h.

125{true};

◆ m_viewManager

KisViewManager* KisPopupPalette::m_viewManager
private

Definition at line 139 of file kis_popup_palette.h.

◆ mirrorMode

KisHighlightedToolButton* KisPopupPalette::mirrorMode {0}
private

Definition at line 169 of file kis_popup_palette.h.

169{0};

◆ opacityChange

QGraphicsOpacityEffect* KisPopupPalette::opacityChange {0}
private

Definition at line 181 of file kis_popup_palette.h.

181{0};

◆ zoomCanvasSlider

QSlider* KisPopupPalette::zoomCanvasSlider {0}
private

Definition at line 173 of file kis_popup_palette.h.

173{0};

◆ zoomSliderMaxValue

int KisPopupPalette::zoomSliderMaxValue {200}
private

Definition at line 175 of file kis_popup_palette.h.

175{200};

◆ zoomSliderMinValue

int KisPopupPalette::zoomSliderMinValue {10}
private

Definition at line 174 of file kis_popup_palette.h.

174{10};

◆ zoomToOneHundredPercentButton

QPushButton* KisPopupPalette::zoomToOneHundredPercentButton {0}
private

Definition at line 171 of file kis_popup_palette.h.

171{0};

Property Documentation

◆ hoveredColor

int KisPopupPalette::hoveredColor
readwrite

Definition at line 51 of file kis_popup_palette.h.

◆ hoveredPreset

int KisPopupPalette::hoveredPreset
readwrite

Definition at line 50 of file kis_popup_palette.h.

◆ selectedColor

int KisPopupPalette::selectedColor
readwrite

Definition at line 52 of file kis_popup_palette.h.


The documentation for this class was generated from the following files: