summaryrefslogtreecommitdiff
path: root/libopie2/opiemm/oimagezoomer.cpp
blob: b7ef238b145ee554a65b2d43037b870c634b2116 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
#include "oimagezoomer.h"

#include <opie2/odebug.h>

#include <qimage.h>
#include <qpixmap.h>
#include <qpainter.h>
#include <qrect.h>
#include <qpoint.h>
#include <qsize.h>

namespace Opie {
namespace MM {

/**
 * \brief The most simple c'tor
 * The main c'tor. You still need to set a QPixmap/QIMage,
 *  setImageSize,setViewPortSize,setVisiblePoint
 *
 * @param parent The parent widget
 * @param name A name for this widget
 * @param fl The widget flags
 *
 */
OImageZoomer::OImageZoomer( QWidget* parent,  const char* name,  WFlags fl )
    :  QFrame( parent, name, fl ) {
    init();
}


/**
 * \brief This c'tor takes a QPixmap additional
 *
 * You initially set the QPixmap but you still need to provide
 * the additional data to make this widget useful
 *
 * @param pix A Pixmap it'll be converted to a QImage later!
 * @param par The parent widget
 * @param name The name of this widget
 * @param fl The widget flags
 */
OImageZoomer::OImageZoomer( const QPixmap& pix, QWidget* par, const char* name, WFlags fl )
    : QFrame( par, name, fl ) {
    init();
    setImage( pix );
}


/**
 * \brief This c'tor takes a QImage instead
 * You just provide a QImage which is saved. It behaves the same as the others.
 *
 * @param img A Image which will be used for the zoomer content
 * @param par The  parent of the widget
 * @param name The name of the widget
 * @param fl The widgets flags
 */
OImageZoomer::OImageZoomer( const QImage& img, QWidget* par, const char* name,  WFlags fl)
    : QFrame( par, name, fl ) {
    init();
    setImage( img );
}


/**
 * \brief overloaded c'tor
 *
 * This differs only in the arguments it takes
 *
 *
 * @param pSize The size of the Page you show
 * @param vSize The size of the viewport. The size of the visible part of the widget
 * @param par The parent of the widget
 * @param name The name
 * @param fl The window flags
 */
OImageZoomer::OImageZoomer( const QSize& pSize, const QSize& vSize, QWidget* par,
                            const char* name, WFlags fl )
    : QFrame( par, name, fl ), m_imgSize( pSize ),m_visSize( vSize ) {
    init();
}

/**
 * d'tor
 */
OImageZoomer::~OImageZoomer() {

}

void OImageZoomer::init() {
    m_mevent = false;
    setFrameStyle( Panel | Sunken );
}


/**
 * \brief set the page/image size
 * Tell us the QSize of the Data you show to the user. We need this
 * to do the calculations
 *
 * @param size The size of the stuff you want to zoom on
 */
void OImageZoomer::setImageSize( const QSize& size ) {
    m_imgSize = size;
    repaint();
}

/**
 * \brief Set the size of the viewport
 * Tell us the QSize of the viewport. The viewport is the part
 * of the widget which is exposed on the screen
 *
 * @param size Te size of the viewport
 *
 * @see QScrollView::viewport()
 */
void OImageZoomer::setViewPortSize( const QSize& size ) {
    m_visSize = size;
    repaint();
}

/**
 * \brief the point in the topleft corner which is currently visible
 * Set the visible point. This most of the times relate to QScrollView::contentsX()
 * and QScrollView::contentsY()
 *
 * @see setVisiblePoint(int,int)
 */
void OImageZoomer::setVisiblePoint( const QPoint& pt ) {
    m_visPt = pt;
    repaint();
}


/**
 * Set the Image. The image will be resized on resizeEvent
 * and it'll set the QPixmap background
 *
 * @param img The image will be stored internally and used as the background
 */
void OImageZoomer::setImage( const QImage& img) {
    m_img = img;
    resizeEvent( 0 );
    repaint();
}

/**
 * overloaded function it calls the QImage version
 */
void OImageZoomer::setImage( const QPixmap& pix) {
    setImage( pix.convertToImage() );
}

void OImageZoomer::resizeEvent( QResizeEvent* ev ) {
    QFrame::resizeEvent( ev );
    setBackgroundOrigin(  QWidget::WidgetOrigin );
    // TODO Qt3 use PalettePixmap and use size
    QPixmap pix; pix.convertFromImage( m_img.smoothScale( size().width(), size().height() ) );
    setBackgroundPixmap( pix);
}

void OImageZoomer::drawContents( QPainter* p ) {
    /*
     * if the page size
     */
    if ( m_imgSize.isEmpty() )
        return;

   /*
    * paint a red rect which represents the visible size
    *
    * We need to recalculate x,y and width and height of the
    * rect. So image size relates to contentRect
    *
    */
    QRect c( contentsRect() );
    p->setPen( Qt::red );

    /*
     * the contentRect is set equal to the size of the image
     * Rect/Original = NewRectORWidth/OriginalVisibleStuff and then simply we
     * need to add the c.y/x due usage of QFrame
     * For x and y we use the visiblePoint
     * For height and width we use the size of the viewport
     * if width/height would be bigger than our widget we use this width/height
     *
     */
    int len = m_imgSize.width();
    int x = (c.width()*m_visPt.x())/len        + c.x();
    int w = (c.width()*m_visSize.width() )/len + c.x();
    if ( w > c.width() ) w = c.width();

    len = m_imgSize.height();
    int y = (c.height()*m_visPt.y() )/len          + c.y();
    int h = (c.height()*m_visSize.height() )/len + c.y();
    if ( h > c.height() ) h = c.height();

    p->drawRect( x, y, w, h );
}

void OImageZoomer::mousePressEvent( QMouseEvent*) {
    m_mouseX = m_mouseY = -1;
    m_mevent = true;
}

void OImageZoomer::mouseReleaseEvent( QMouseEvent*ev) {
    if (!m_mevent) return;
    int mx, my;
    mx = ev->x();
    my = ev->y();
    int diffx = (mx) * m_imgSize.width() / width();
    int diffy = (my) * m_imgSize.height() / height();
    emit zoomArea(diffx,diffy);
}

void OImageZoomer::mouseMoveEvent( QMouseEvent* ev ) {
    int mx, my;
    mx = ev->x();
    my = ev->y();

    if ( m_mouseX != -1 && m_mouseY != -1 ) {
        m_mevent = false;
        int diffx = ( mx - m_mouseX ) * m_imgSize.width() / width();
        int diffy = ( my - m_mouseY ) * m_imgSize.height() / height();
        emit zoomAreaRel( diffx, diffy );
    }
    m_mouseX = mx;
    m_mouseY = my;
}


}
}