Crop widget is now a designer plugin.
[cropwidget.git] / cropwidget.cpp
blob33c06f7e297d83778853cff37be744f7e88c509d
1 /*
2 cropwidget
3 Copyright (C) 2009 RafaƂ Rzepecki <divided.mind@gmail.com>
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
20 #include "cropwidget.h"
22 #include <QStackedLayout>
23 #include <QMouseEvent>
24 #include <QPainter>
25 #include <QPaintEvent>
26 #include <QResizeEvent>
28 CropWidget::CropWidget(QWidget *parent): QFrame(parent), _snapped(false)
32 void CropWidget::snap(bool snapped)
34 cropStart = QPoint();
35 cropRect = QRect();
36 const QList<QWidget *> widgets = findChildren<QWidget *>();
37 if (snapped) {
38 snapshot = QPixmap::grabWidget(this, contentsRect());
39 foreach(QWidget *w, widgets)
40 w->hide();
41 } else {
42 foreach(QWidget *w, widgets)
43 w->show();
44 QPainter painter(this);
45 painter.eraseRect(contentsRect());
46 update();
48 _snapped = snapped;
51 void CropWidget::paintEvent(QPaintEvent *event)
53 QFrame::paintEvent(event);
54 if (!_snapped)
55 return;
57 QPainter painter(this);
58 painter.setRenderHint(QPainter::SmoothPixmapTransform);
59 painter.drawPixmap(contentsRect(), snapshot);
61 if (cropRect.isValid()) {
62 QImage img(contentsRect().size(), QImage::Format_ARGB32);
63 QPainter ppm(&img);
64 ppm.fillRect(rect(), QColor(255, 255, 255, 200)); ppm.setCompositionMode(QPainter::CompositionMode_Clear);
65 ppm.eraseRect(cropRect);
66 painter.drawImage(contentsRect(), img);
69 event->accept();
72 void CropWidget::crop()
74 if ((!_snapped) || (!cropRect.isValid()))
75 return;
77 int x = cropRect.x() * snapshot.width() / width();
78 int y = cropRect.y() * snapshot.height() / height();
79 int w = cropRect.width() * snapshot.width() / width();
80 int h = cropRect.height() * snapshot.height() / height();
82 snapshot = snapshot.copy(QRect(x, y, w, h));
83 cropRect = QRect();
84 update();
87 void CropWidget::mousePressEvent(QMouseEvent *event)
89 if ((!_snapped) || (event->button() != Qt::LeftButton))
90 return QWidget::mousePressEvent(event);
92 const QPoint pos = toContents(event->pos());
94 cropStart = pos;
95 event->accept();
98 void CropWidget::mouseMoveEvent(QMouseEvent *event)
100 if ((!_snapped) || (cropStart.isNull()) || (!(event->buttons() & Qt::LeftButton)))
101 return QWidget::mouseMoveEvent(event);
103 const QPoint pos = toContents(event->pos());
105 cropRect = QRect(cropStart, pos).normalized();
106 update();
107 event->accept();
110 void CropWidget::mouseReleaseEvent(QMouseEvent *event)
112 if ((!_snapped) || (cropStart.isNull()) || (event->button() != Qt::LeftButton))
113 return QWidget::mouseReleaseEvent(event);
115 const QPoint pos = toContents(event->pos());
117 cropRect = QRect(cropStart, pos).normalized();
118 update();
119 cropStart = QPoint();
120 event->accept();
123 QSize CropWidget::sizeHint() const
125 if (_snapped)
126 return QSize(snapshot.size().width() + 2 * frameWidth(), snapshot.size().height() + 2 * frameWidth());
127 else
128 return QFrame::sizeHint();
131 QSizePolicy CropWidget::sizePolicy() const
133 if (_snapped)
134 return QSizePolicy(QSizePolicy::Fixed, QSizePolicy::Fixed);
135 else
136 return QFrame::sizePolicy();
139 QPoint CropWidget::toContents(QPoint point) const
141 QPoint p = point - contentsRect().topLeft();
142 if (p.x() < 0)
143 p.setX(0);
144 if (p.x() >= contentsRect().size().width())
145 p.setX(contentsRect().size().width() - 1);
146 if (p.y() < 0)
147 p.setY(0);
148 if (p.y() >= contentsRect().size().height())
149 p.setY(contentsRect().size().height() - 1);
150 return p;