#include <mandelbrotwidget.h>
Inheritance diagram for MandelbrotWidget:


Definition at line 32 of file mandelbrotwidget.h.
Public Member Functions | |
| MandelbrotWidget (QWidget *parent=0) | |
Protected Member Functions | |
| void | paintEvent (QPaintEvent *event) |
| void | resizeEvent (QResizeEvent *event) |
| void | keyPressEvent (QKeyEvent *event) |
| void | wheelEvent (QWheelEvent *event) |
| void | mousePressEvent (QMouseEvent *event) |
| void | mouseMoveEvent (QMouseEvent *event) |
| void | mouseReleaseEvent (QMouseEvent *event) |
Private Slots | |
| void | updatePixmap (const QImage &image, double scaleFactor) |
Private Member Functions | |
| void | zoom (double zoomFactor) |
| void | scroll (int deltaX, int deltaY) |
Private Attributes | |
| RenderThread | thread |
| QPixmap | pixmap |
| QPoint | pixmapOffset |
| QPoint | lastDragPos |
| double | centerX |
| double | centerY |
| double | pixmapScale |
| double | curScale |
| MandelbrotWidget::MandelbrotWidget | ( | QWidget * | parent = 0 |
) |
Definition at line 38 of file mandelbrotwidget.cpp.
References centerX, centerY, QObject::connect(), Qt::CrossCursor, curScale, DefaultCenterX, DefaultCenterY, DefaultScale, pixmapScale, QWidget::resize(), QWidget::setCursor(), QWidget::setWindowTitle(), SIGNAL, SLOT, QObject::thread(), and updatePixmap().
00039 : QWidget(parent) 00040 { 00041 centerX = DefaultCenterX; 00042 centerY = DefaultCenterY; 00043 pixmapScale = DefaultScale; 00044 curScale = DefaultScale; 00045 00046 qRegisterMetaType<QImage>("QImage"); 00047 connect(&thread, SIGNAL(renderedImage(const QImage &, double)), 00048 this, SLOT(updatePixmap(const QImage &, double))); 00049 00050 setWindowTitle(tr("Mandelbrot")); 00051 setCursor(Qt::CrossCursor); 00052 resize(550, 400); 00053 }
Here is the call graph for this function:

| void MandelbrotWidget::paintEvent | ( | QPaintEvent * | event | ) | [protected, virtual] |
This event handler can be reimplemented in a subclass to receive paint events which are passed in the event parameter.
A paint event is a request to repaint all or part of the widget. It can happen as a result of repaint() or update(), or because the widget was obscured and has now been uncovered, or for many other reasons.
Many widgets can simply repaint their entire surface when asked to, but some slow widgets need to optimize by painting only the requested region: QPaintEvent::region(). This speed optimization does not change the result, as painting is clipped to that region during event processing. QListView and QTableView do this, for example.
Qt also tries to speed up painting by merging multiple paint events into one. When update() is called several times or the window system sends several paint events, Qt merges these events into one event with a larger region (see QRegion::united()). repaint() does not permit this optimization, so we suggest using update() whenever possible.
When the paint event occurs, the update region has normally been erased, so that you're painting on the widget's background.
The background can be set using setBackgroundRole() and setPalette().
From Qt 4.0, QWidget automatically double-buffers its painting, so there's no need to write double-buffering code in paintEvent() to avoid flicker.
Note: Under X11 it is possible to toggle the global double buffering by calling qt_x11_set_global_double_buffer(). Example usage:
...
extern void qt_x11_set_global_double_buffer(bool);
qt_x11_set_global_double_buffer(false);
...
Reimplemented from QWidget.
Definition at line 55 of file mandelbrotwidget.cpp.
References QRect::adjusted(), Qt::AlignCenter, Qt::black, curScale, QPainter::drawPixmap(), QPainter::drawRect(), QPainter::drawText(), QPainter::fillRect(), QPainter::fontMetrics(), QPixmap::height(), int, QMatrix::inverted(), QPixmap::isNull(), QMatrix::mapRect(), QPainter::matrix(), metrics(), Qt::NoPen, pixmap, pixmapOffset, pixmapScale, QWidget::rect(), QPainter::restore(), QPainter::save(), QPainter::scale(), QPainter::setBrush(), QPainter::setPen(), QPainter::translate(), Qt::white, QPixmap::width(), QWidget::width(), QPoint::x(), and QPoint::y().
00056 { 00057 QPainter painter(this); 00058 painter.fillRect(rect(), Qt::black); 00059 00060 if (pixmap.isNull()) { 00061 painter.setPen(Qt::white); 00062 painter.drawText(rect(), Qt::AlignCenter, 00063 tr("Rendering initial image, please wait...")); 00064 return; 00065 } 00066 00067 if (curScale == pixmapScale) { 00068 painter.drawPixmap(pixmapOffset, pixmap); 00069 } else { 00070 double scaleFactor = pixmapScale / curScale; 00071 int newWidth = int(pixmap.width() * scaleFactor); 00072 int newHeight = int(pixmap.height() * scaleFactor); 00073 int newX = pixmapOffset.x() + (pixmap.width() - newWidth) / 2; 00074 int newY = pixmapOffset.y() + (pixmap.height() - newHeight) / 2; 00075 00076 painter.save(); 00077 painter.translate(newX, newY); 00078 painter.scale(scaleFactor, scaleFactor); 00079 QRectF exposed = painter.matrix().inverted().mapRect(rect()).adjusted(-1, -1, 1, 1); 00080 painter.drawPixmap(exposed, pixmap, exposed); 00081 painter.restore(); 00082 } 00083 00084 QString text = tr("Use mouse wheel to zoom. " 00085 "Press and hold left mouse button to scroll."); 00086 QFontMetrics metrics = painter.fontMetrics(); 00087 int textWidth = metrics.width(text); 00088 00089 painter.setPen(Qt::NoPen); 00090 painter.setBrush(QColor(0, 0, 0, 127)); 00091 painter.drawRect((width() - textWidth) / 2 - 5, 0, textWidth + 10, 00092 metrics.lineSpacing() + 5); 00093 painter.setPen(Qt::white); 00094 painter.drawText((width() - textWidth) / 2, 00095 metrics.leading() + metrics.ascent(), text); 00096 }
Here is the call graph for this function:

| void MandelbrotWidget::resizeEvent | ( | QResizeEvent * | event | ) | [protected, virtual] |
This event handler can be reimplemented in a subclass to receive widget resize events which are passed in the event parameter. When resizeEvent() is called, the widget already has its new geometry. The old size is accessible through QResizeEvent::oldSize().
The widget will be erased and receive a paint event immediately after processing the resize event. No drawing need be (or should be) done inside this handler.
Reimplemented from QWidget.
Definition at line 98 of file mandelbrotwidget.cpp.
References centerX, centerY, curScale, QWidget::size(), and QObject::thread().
Here is the call graph for this function:

| void MandelbrotWidget::keyPressEvent | ( | QKeyEvent * | event | ) | [protected, virtual] |
This event handler, for event event, can be reimplemented in a subclass to receive key press events for the widget.
A widget must call setFocusPolicy() to accept focus initially and have focus in order to receive a key press event.
If you reimplement this handler, it is very important that you ignore() the event if you do not understand it, so that the widget's parent can interpret it.
The default implementation closes popup widgets if the user presses Esc. Otherwise the event is ignored.
Reimplemented from QWidget.
Definition at line 103 of file mandelbrotwidget.cpp.
References QWidget::event(), Qt::Key_Down, Qt::Key_Left, Qt::Key_Minus, Qt::Key_Plus, Qt::Key_Right, Qt::Key_Up, QWidget::keyPressEvent(), scroll(), ScrollStep, zoom(), ZoomInFactor, and ZoomOutFactor.
00104 { 00105 switch (event->key()) { 00106 case Qt::Key_Plus: 00107 zoom(ZoomInFactor); 00108 break; 00109 case Qt::Key_Minus: 00110 zoom(ZoomOutFactor); 00111 break; 00112 case Qt::Key_Left: 00113 scroll(-ScrollStep, 0); 00114 break; 00115 case Qt::Key_Right: 00116 scroll(+ScrollStep, 0); 00117 break; 00118 case Qt::Key_Down: 00119 scroll(0, -ScrollStep); 00120 break; 00121 case Qt::Key_Up: 00122 scroll(0, +ScrollStep); 00123 break; 00124 default: 00125 QWidget::keyPressEvent(event); 00126 } 00127 }
Here is the call graph for this function:

| void MandelbrotWidget::wheelEvent | ( | QWheelEvent * | event | ) | [protected, virtual] |
This event handler, for event event, can be reimplemented in a subclass to receive wheel events for the widget.
If you reimplement this handler, it is very important that you ignore() the event if you do not handle it, so that the widget's parent can interpret it.
The default implementation ignores the event.
Reimplemented from QWidget.
Definition at line 129 of file mandelbrotwidget.cpp.
References QWidget::event(), zoom(), and ZoomInFactor.
00130 { 00131 int numDegrees = event->delta() / 8; 00132 double numSteps = numDegrees / 15.0f; 00133 zoom(pow(ZoomInFactor, numSteps)); 00134 }
Here is the call graph for this function:

| void MandelbrotWidget::mousePressEvent | ( | QMouseEvent * | event | ) | [protected, virtual] |
This event handler, for event event, can be reimplemented in a subclass to receive mouse press events for the widget.
If you create new widgets in the mousePressEvent() the mouseReleaseEvent() may not end up where you expect, depending on the underlying window system (or X11 window manager), the widgets' location and maybe more.
The default implementation implements the closing of popup widgets when you click outside the window. For other widget types it does nothing.
Reimplemented from QWidget.
Definition at line 136 of file mandelbrotwidget.cpp.
References QWidget::event(), lastDragPos, and Qt::LeftButton.
00137 { 00138 if (event->button() == Qt::LeftButton) 00139 lastDragPos = event->pos(); 00140 }
Here is the call graph for this function:

| void MandelbrotWidget::mouseMoveEvent | ( | QMouseEvent * | event | ) | [protected, virtual] |
This event handler, for event event, can be reimplemented in a subclass to receive mouse move events for the widget.
If mouse tracking is switched off, mouse move events only occur if a mouse button is pressed while the mouse is being moved. If mouse tracking is switched on, mouse move events occur even if no mouse button is pressed.
QMouseEvent::pos() reports the position of the mouse cursor, relative to this widget. For press and release events, the position is usually the same as the position of the last mouse move event, but it might be different if the user's hand shakes. This is a feature of the underlying window system, not Qt.
Reimplemented from QWidget.
Definition at line 142 of file mandelbrotwidget.cpp.
References QWidget::event(), lastDragPos, Qt::LeftButton, pixmapOffset, and QWidget::update().
00143 { 00144 if (event->buttons() & Qt::LeftButton) { 00145 pixmapOffset += event->pos() - lastDragPos; 00146 lastDragPos = event->pos(); 00147 update(); 00148 } 00149 }
Here is the call graph for this function:

| void MandelbrotWidget::mouseReleaseEvent | ( | QMouseEvent * | event | ) | [protected, virtual] |
This event handler, for event event, can be reimplemented in a subclass to receive mouse release events for the widget.
Reimplemented from QWidget.
Definition at line 151 of file mandelbrotwidget.cpp.
References QWidget::event(), QPixmap::height(), QWidget::height(), lastDragPos, Qt::LeftButton, pixmap, pixmapOffset, scroll(), QPixmap::width(), QWidget::width(), QPoint::x(), and QPoint::y().
00152 { 00153 if (event->button() == Qt::LeftButton) { 00154 pixmapOffset += event->pos() - lastDragPos; 00155 lastDragPos = QPoint(); 00156 00157 int deltaX = (width() - pixmap.width()) / 2 - pixmapOffset.x(); 00158 int deltaY = (height() - pixmap.height()) / 2 - pixmapOffset.y(); 00159 scroll(deltaX, deltaY); 00160 } 00161 }
Here is the call graph for this function:

| void MandelbrotWidget::updatePixmap | ( | const QImage & | image, | |
| double | scaleFactor | |||
| ) | [private, slot] |
Definition at line 163 of file mandelbrotwidget.cpp.
References QPixmap::fromImage(), image, QPoint::isNull(), lastDragPos, pixmap, pixmapOffset, pixmapScale, and QWidget::update().
Referenced by MandelbrotWidget().
00164 { 00165 if (!lastDragPos.isNull()) 00166 return; 00167 00168 pixmap = QPixmap::fromImage(image); 00169 pixmapOffset = QPoint(); 00170 lastDragPos = QPoint(); 00171 pixmapScale = scaleFactor; 00172 update(); 00173 }
| void MandelbrotWidget::zoom | ( | double | zoomFactor | ) | [private] |
Definition at line 175 of file mandelbrotwidget.cpp.
References centerX, centerY, curScale, QWidget::size(), QObject::thread(), and QWidget::update().
Referenced by keyPressEvent(), and wheelEvent().
00176 { 00177 curScale *= zoomFactor; 00178 update(); 00179 thread.render(centerX, centerY, curScale, size()); 00180 }
Here is the call graph for this function:

| void MandelbrotWidget::scroll | ( | int | deltaX, | |
| int | deltaY | |||
| ) | [private] |
Scrolls the widget including its children dx pixels to the right and dy downward. Both dx and dy may be negative.
After scrolling, the widgets will receive paint events for the areas that need to be repainted. For widgets that Qt knows to be opaque, this is only the newly exposed parts. For example, if an opaque widget is scrolled 8 pixels to the left, only an 8-pixel wide stripe at the right edge needs updating.
Since widgets propagate the contents of their parents by default, you need to set the autoFillBackground property, or use setAttribute() to set the Qt::WA_OpaquePaintEvent attribute, to make a widget opaque.
For widgets that use contents propagation, a scroll will cause an update of the entire scroll area.
Reimplemented from QWidget.
Definition at line 182 of file mandelbrotwidget.cpp.
References centerX, centerY, curScale, QWidget::size(), QObject::thread(), and QWidget::update().
Referenced by keyPressEvent(), and mouseReleaseEvent().
00183 { 00184 centerX += deltaX * curScale; 00185 centerY += deltaY * curScale; 00186 update(); 00187 thread.render(centerX, centerY, curScale, size()); 00188 }
Here is the call graph for this function:

RenderThread MandelbrotWidget::thread [private] |
Definition at line 55 of file mandelbrotwidget.h.
QPixmap MandelbrotWidget::pixmap [private] |
Definition at line 56 of file mandelbrotwidget.h.
Referenced by mouseReleaseEvent(), paintEvent(), and updatePixmap().
QPoint MandelbrotWidget::pixmapOffset [private] |
Definition at line 57 of file mandelbrotwidget.h.
Referenced by mouseMoveEvent(), mouseReleaseEvent(), paintEvent(), and updatePixmap().
QPoint MandelbrotWidget::lastDragPos [private] |
Definition at line 58 of file mandelbrotwidget.h.
Referenced by mouseMoveEvent(), mousePressEvent(), mouseReleaseEvent(), and updatePixmap().
double MandelbrotWidget::centerX [private] |
Definition at line 59 of file mandelbrotwidget.h.
Referenced by MandelbrotWidget(), resizeEvent(), scroll(), and zoom().
double MandelbrotWidget::centerY [private] |
Definition at line 60 of file mandelbrotwidget.h.
Referenced by MandelbrotWidget(), resizeEvent(), scroll(), and zoom().
double MandelbrotWidget::pixmapScale [private] |
Definition at line 61 of file mandelbrotwidget.h.
Referenced by MandelbrotWidget(), paintEvent(), and updatePixmap().
double MandelbrotWidget::curScale [private] |
Definition at line 62 of file mandelbrotwidget.h.
Referenced by MandelbrotWidget(), paintEvent(), resizeEvent(), scroll(), and zoom().
1.5.1