File indexing completed on 2025-01-05 03:59:44
0001 /* ============================================================ 0002 * 0003 * This file is a part of digiKam project 0004 * https://www.digikam.org 0005 * 0006 * Date : 2013-07-15 0007 * Description : a widget to draw an image clip region. 0008 * 0009 * SPDX-FileCopyrightText: 2013-2014 by Yiou Wang <geow812 at gmail dot com> 0010 * SPDX-FileCopyrightText: 2010-2012 by Marcel Wiesweg <marcel dot wiesweg at gmx dot de> 0011 * SPDX-FileCopyrightText: 2011-2024 by Gilles Caulier <caulier dot gilles at gmail dot com> 0012 * 0013 * SPDX-License-Identifier: GPL-2.0-or-later 0014 * 0015 * ============================================================ */ 0016 0017 #include "imageregionwidget.h" 0018 0019 // C++ includes 0020 0021 #include <cmath> 0022 0023 // Qt includes 0024 0025 #include <QTimer> 0026 #include <QIcon> 0027 0028 // KDE includes 0029 0030 #include <klocalizedstring.h> 0031 0032 // Local includes 0033 0034 #include "digikam_debug.h" 0035 #include "imageregionitem.h" 0036 #include "previewtoolbar.h" 0037 #include "previewlayout.h" 0038 #include "dimgitems_p.h" 0039 0040 namespace Digikam 0041 { 0042 0043 class Q_DECL_HIDDEN ImageRegionWidget::Private 0044 { 0045 0046 public: 0047 0048 explicit Private() 0049 : capturePtMode(false), 0050 renderingPreviewMode(PreviewToolBar::PreviewBothImagesVertCont), 0051 oldRenderingPreviewMode(PreviewToolBar::PreviewBothImagesVertCont), 0052 delay(nullptr), 0053 item(nullptr) 0054 { 0055 } 0056 0057 DImg targetImage; 0058 0059 bool capturePtMode; 0060 0061 int renderingPreviewMode; 0062 int oldRenderingPreviewMode; 0063 0064 QPolygon hightlightPoints; 0065 0066 QTimer* delay; 0067 0068 ImageRegionItem* item; 0069 }; 0070 0071 ImageRegionWidget::ImageRegionWidget(QWidget* const parent, bool paintExtras) 0072 : GraphicsDImgView(parent), 0073 d_ptr(new Private) 0074 { 0075 d_ptr->item = new ImageRegionItem(this, paintExtras); 0076 setItem(d_ptr->item); 0077 0078 setAttribute(Qt::WA_DeleteOnClose); 0079 setFrameStyle(QFrame::NoFrame); 0080 setMinimumSize(480, 320); 0081 setWhatsThis(i18n("<p>Here you can see the original clip image " 0082 "which will be used for the preview computation.</p>" 0083 "<p>Click and drag the mouse cursor in the " 0084 "image to change the clip focus.</p>")); 0085 0086 d_ptr->delay = new QTimer(this); 0087 d_ptr->delay->setInterval(500); 0088 d_ptr->delay->setSingleShot(true); 0089 0090 connect(d_ptr->delay, SIGNAL(timeout()), 0091 this, SLOT(slotOriginalImageRegionChanged())); 0092 0093 connect(this, SIGNAL(viewportRectChanged(QRectF)), 0094 this, SLOT(slotOriginalImageRegionChangedDelayed())); 0095 0096 layout()->fitToWindow(); 0097 installPanIcon(); 0098 } 0099 0100 ImageRegionWidget::~ImageRegionWidget() 0101 { 0102 delete d_ptr->item; 0103 delete d_ptr; 0104 } 0105 0106 void ImageRegionWidget::setHighLightPoints(const QPolygon& pointsList) 0107 { 0108 d_ptr->item->setHighLightPoints(pointsList); 0109 viewport()->update(); 0110 } 0111 0112 void ImageRegionWidget::setCapturePointMode(bool b) 0113 { 0114 if (d_ptr->capturePtMode && b) 0115 { 0116 return; 0117 } 0118 0119 d_ptr->capturePtMode = b; 0120 viewport()->setMouseTracking(!b); 0121 0122 if (b) 0123 { 0124 d_ptr->oldRenderingPreviewMode = d_ptr->renderingPreviewMode; 0125 slotPreviewModeChanged(PreviewToolBar::PreviewOriginalImage); 0126 viewport()->setCursor(QCursor(QIcon::fromTheme(QLatin1String("color-picker")).pixmap(32), 4, 27)); 0127 } 0128 else 0129 { 0130 slotPreviewModeChanged(d_ptr->oldRenderingPreviewMode); 0131 viewport()->unsetCursor(); 0132 } 0133 } 0134 0135 void ImageRegionWidget::slotPreviewModeChanged(int mode) 0136 { 0137 d_ptr->renderingPreviewMode = mode; 0138 d_ptr->item->setRenderingPreviewMode(mode); 0139 slotOriginalImageRegionChanged(); 0140 viewport()->update(); 0141 } 0142 0143 QRect ImageRegionWidget::getOriginalImageRegionToRender() const 0144 { 0145 QRect r = d_ptr->item->getImageRegion(); 0146 double z = layout()->realZoomFactor(); 0147 0148 int x = qRound((double)r.x() / z); 0149 int y = qRound((double)r.y() / z); 0150 int w = qRound((double)r.width() / z); 0151 int h = qRound((double)r.height() / z); 0152 0153 QRect rect(x, y, w, h); 0154 return (rect); 0155 } 0156 0157 void ImageRegionWidget::setPreviewImage(const DImg& img) 0158 { 0159 d_ptr->targetImage = img; 0160 QRect r = d_ptr->item->getImageRegion(); 0161 d_ptr->targetImage.resize(r.width(), r.height()); 0162 0163 // Because tool which only work on image data, the DImg container 0164 // do not contain metadata from original image. About Color Managed View, we need to 0165 // restore the embedded ICC color profile. 0166 // However, some tools may set a profile on the preview image, which we accept of course. 0167 0168 if (d_ptr->targetImage.getIccProfile().isNull()) 0169 { 0170 d_ptr->targetImage.setIccProfile(d_ptr->item->image().getIccProfile()); 0171 } 0172 0173 d_ptr->item->setTargetImage(d_ptr->targetImage); 0174 } 0175 0176 DImg ImageRegionWidget::getOriginalImage() const 0177 { 0178 return (d_ptr->item->image().copy()); 0179 } 0180 0181 DImg ImageRegionWidget::getOriginalRegionImage(bool useDownscaledImage) const 0182 { 0183 DImg image = d_ptr->item->image().copy(getOriginalImageRegionToRender()); 0184 0185 if (useDownscaledImage) 0186 { 0187 QRect r = d_ptr->item->getImageRegion(); 0188 image.resize(r.width(), r.height()); 0189 } 0190 0191 return (image); 0192 } 0193 0194 void ImageRegionWidget::slotOriginalImageRegionChangedDelayed() 0195 { 0196 viewport()->update(); 0197 d_ptr->delay->start(); 0198 } 0199 0200 void ImageRegionWidget::slotOriginalImageRegionChanged(bool targetDone) 0201 { 0202 if (targetDone) 0203 { 0204 Q_EMIT signalOriginalClipFocusChanged(); // For Image Edit Tools 0205 } 0206 } 0207 0208 void ImageRegionWidget::exposureSettingsChanged() 0209 { 0210 d_ptr->item->clearCache(); 0211 d_ptr->item->setTargetImage(d_ptr->targetImage); 0212 } 0213 0214 void ImageRegionWidget::ICCSettingsChanged() 0215 { 0216 d_ptr->item->clearCache(); 0217 d_ptr->item->setTargetImage(d_ptr->targetImage); 0218 } 0219 0220 void ImageRegionWidget::mousePressEvent(QMouseEvent* e) 0221 { 0222 if (d_ptr->capturePtMode) 0223 { 0224 emitCapturedPointFromOriginal(mapToScene(e->pos())); 0225 QGraphicsView::mousePressEvent(e); 0226 return; 0227 } 0228 0229 GraphicsDImgView::mousePressEvent(e); 0230 } 0231 0232 void ImageRegionWidget::mouseReleaseEvent(QMouseEvent* e) 0233 { 0234 if (d_ptr->capturePtMode) 0235 { 0236 setCapturePointMode(false); 0237 QGraphicsView::mouseReleaseEvent(e); 0238 return; 0239 } 0240 0241 GraphicsDImgView::mouseReleaseEvent(e); 0242 } 0243 0244 void ImageRegionWidget::emitCapturedPointFromOriginal(const QPointF& pt) 0245 { 0246 int x = (int)(pt.x() / layout()->realZoomFactor()); 0247 int y = (int)(pt.y() / layout()->realZoomFactor()); 0248 QPoint imgPt(x, y); 0249 DColor color = d_ptr->item->image().getPixelColor(x, y); 0250 qCDebug(DIGIKAM_GENERAL_LOG) << "Captured point from image : " << imgPt; 0251 Q_EMIT signalCapturedPointFromOriginal(color, imgPt); 0252 } 0253 0254 void ImageRegionWidget::updateImage(const DImg& img) 0255 { 0256 d_ptr->item->setImage(img); 0257 } 0258 0259 } // namespace Digikam 0260 0261 #include "moc_imageregionwidget.cpp"