1 /*
2  * fancylabel.cpp - the FancyLabel widget
3  * Copyright (C) 2003  Michail Pishchagin
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Lesser General Public
7  * License as published by the Free Software Foundation; either
8  * version 2.1 of the License, or (at your option) any later version.
9  *
10  * This library 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 GNU
13  * Lesser General Public License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with this library; if not, write to the Free Software
17  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18  *
19  */
20 
21 #include "fancylabel.h"
22 
23 #include <QPixmap>
24 #include <QColor>
25 #include <QLayout>
26 #include <QLabel>
27 #include <QFrame>
28 #include <QPainter>
29 #include <QResizeEvent>
30 
31 #ifndef WIDGET_PLUGIN
32 #include "iconset.h"
33 #endif
34 
35 #include "iconlabel.h"
36 
37 //----------------------------------------------------------------------------
38 // IconLabel
39 //----------------------------------------------------------------------------
40 
41 class IconLabel::Private : public QObject
42 {
43 	Q_OBJECT
44 
45 public:
46 
47 	IconLabel *label;
48 	PsiIcon *icon;
49 	bool copyIcon;
50 #ifdef WIDGET_PLUGIN
51 	QString iconName;
52 #endif
53 
Private(IconLabel * l)54 	Private(IconLabel *l)
55 	{
56 		label = l;
57 		icon = 0;
58 		copyIcon = false;
59 	}
60 
~Private()61 	~Private()
62 	{
63 		stopIcon();
64 #ifndef WIDGET_PLUGIN
65 		if ( icon && copyIcon )
66 			delete icon;
67 #endif
68 	}
69 
setIcon(const PsiIcon * i,bool _copyIcon)70 	void setIcon(const PsiIcon *i, bool _copyIcon)
71 	{
72 		stopIcon();
73 
74 		if (copyIcon && icon) {
75 			delete icon;
76 			icon = 0;
77 		}
78 
79 		copyIcon = _copyIcon;
80 
81 #ifndef WIDGET_PLUGIN
82 		if ( i ) {
83 			if (copyIcon)
84 				icon = new PsiIcon(*i);
85 			else
86 				icon = (PsiIcon *)i;
87 		}
88 		else {
89 			icon = 0;
90 		}
91 
92 #else
93     Q_UNUSED(i);
94 #endif
95 		startIcon();
96 	}
97 
98 protected:
stopIcon()99 	void stopIcon()
100 	{
101 #ifndef WIDGET_PLUGIN
102 		if ( icon ) {
103 			disconnect(icon, 0, this, 0);
104 			icon->stop();
105 		}
106 #endif
107 	}
108 
startIcon()109 	void startIcon()
110 	{
111 #ifndef WIDGET_PLUGIN
112 		if ( icon ) {
113 			connect(icon, SIGNAL(pixmapChanged()), SLOT(iconUpdated()));
114 			icon->activated(false); // TODO: should icon play sound when it's activated on icon?
115 		}
116 		iconUpdated();
117 #endif
118 	}
119 
120 private slots:
iconUpdated()121 	void iconUpdated()
122 	{
123 #ifndef WIDGET_PLUGIN
124 		label->setPixmap(icon ? icon->pixmap() : QPixmap());
125 #endif
126 	}
127 };
128 
IconLabel(QWidget * parent)129 IconLabel::IconLabel(QWidget *parent)
130 : QLabel(parent)
131 {
132 	d = new Private(this);
133 }
134 
~IconLabel()135 IconLabel::~IconLabel()
136 {
137 	delete d;
138 }
139 
psiIcon() const140 const PsiIcon *IconLabel::psiIcon () const
141 {
142 	return d->icon;
143 }
144 
psiIconName() const145 QString IconLabel::psiIconName () const
146 {
147 #ifndef WIDGET_PLUGIN
148 	if ( d->icon )
149 		return d->icon->name();
150 	return QString();
151 #else
152 	return d->iconName;
153 #endif
154 }
155 
setPsiIcon(const PsiIcon * i,bool copyIcon)156 void IconLabel::setPsiIcon(const PsiIcon *i, bool copyIcon)
157 {
158 	d->setIcon(i, copyIcon);
159 }
160 
setPsiIcon(const QString & name)161 void IconLabel::setPsiIcon(const QString &name)
162 {
163 #ifndef WIDGET_PLUGIN
164 	setPsiIcon( IconsetFactory::iconPtr(name) );
165 #else
166 	d->iconName = name;
167 	setText("<qt>icon:<br><small>" + name + "</small></qt>");
168 #endif
169 }
170 
setScaledContents(int width,int height)171 void IconLabel::setScaledContents(int width, int height)
172 {
173 	QLabel::setScaledContents(true);
174 	setMinimumSize(width, height);
175 	setMaximumSize(width, height);
176 }
177 
178 //----------------------------------------------------------------------------
179 // MyFancyFrame -- internal
180 //----------------------------------------------------------------------------
181 
182 class MyFancyFrame : public QFrame
183 {
184 	Q_OBJECT
185 protected:
paintEvent(QPaintEvent * event)186 	void paintEvent(QPaintEvent *event)
187 	{
188 		QPainter *p = new QPainter(this);
189 		p->drawPixmap(0, 0, background);
190 		delete p;
191 		QFrame::paintEvent(event);
192 	}
193 
resizeEvent(QResizeEvent * e)194 	void resizeEvent (QResizeEvent *e)
195 	{
196 		QFrame::resizeEvent (e);
197 
198 		QRect rect = geometry();
199 		int w = rect.width();
200 
201 		if ( rect.height() <= 0 || w <= 0 )
202 			return; // avoid crash
203 
204 		int r1, g1, b1;
205 		from->getRgb (&r1, &g1, &b1);
206 		int r2, g2, b2;
207 		to->getRgb (&r2, &g2, &b2);
208 
209 		float stepR = (float)(r2 - r1) / w;
210 		float stepG = (float)(g2 - g1) / w;
211 		float stepB = (float)(b2 - b1) / w;
212 
213 		QPixmap pix (rect.width(), rect.height());
214 		QPainter p;
215 		p.begin (&pix);
216 		for (int i = 0; i < w; i++) {
217 			int r = (int)((float)r1 + stepR*i);
218 			int g = (int)((float)g1 + stepG*i);
219 			int b = (int)((float)b1 + stepB*i);
220 
221 			p.setPen ( QColor( r, g, b ) );
222 			p.drawLine ( i, 0, i, rect.height() );
223 		}
224 		p.end ();
225 
226 		background = pix;
227 		update();
228 	}
229 
230 private:
231 	QColor *from, *to;
232 	QPixmap background;
233 
234 public:
MyFancyFrame(QWidget * parent,QColor * _from,QColor * _to)235 	MyFancyFrame (QWidget *parent, QColor *_from, QColor *_to)
236 	: QFrame (parent)
237 	{
238 		from = _from;
239 		to = _to;
240 	}
241 
repaintBackground()242 	void repaintBackground()
243 	{
244 		QResizeEvent e(size(), size());
245 		resizeEvent(&e);
246 	}
247 };
248 
249 //----------------------------------------------------------------------------
250 // FancyLabel
251 //----------------------------------------------------------------------------
252 
253 class FancyLabel::Private : public QObject
254 {
255 public:
256 	MyFancyFrame *frame;
257 	IconLabel *text, *help, *pix;
258 	QColor from, to, font;
259 	QString textStr, helpStr;
260 	static int smallFontSize;
261 
Private(FancyLabel * parent)262 	Private (FancyLabel *parent)
263 	: QObject(parent), from(72, 172, 243), to(255, 255, 255), font(0, 0, 0)
264 	{
265 		QHBoxLayout *mainbox = new QHBoxLayout( parent );
266 		mainbox->setSpacing(0);
267 		mainbox->setMargin(0);
268 
269 		frame = new MyFancyFrame ( parent, &from, &to );
270 		frame->setFrameShape( QFrame::StyledPanel );
271 		frame->setFrameShadow( QFrame::Raised );
272 
273 		QHBoxLayout *frameLayout = new QHBoxLayout(frame);
274 		frameLayout->setMargin(0);
275 		frameLayout->setSpacing(0);
276 		QVBoxLayout *layout = new QVBoxLayout;
277 		layout->setMargin(0);
278 		layout->setSpacing(0);
279 		frameLayout->addLayout( layout );
280 
281 		text = new IconLabel( frame );
282 		text->setSizePolicy( (QSizePolicy::Policy)7, (QSizePolicy::Policy)5 );
283 		layout->addWidget( text );
284 
285 		help = new IconLabel( frame );
286 		layout->addWidget( help );
287 
288 		QFont font = help->font();
289 		font.setPointSize(smallFontSize);
290 		help->setFont(font);
291 
292 		pix = new IconLabel( frame );
293 		pix->setSizePolicy( (QSizePolicy::Policy)1, (QSizePolicy::Policy)5 );
294 		frameLayout->addWidget( pix );
295 
296 		mainbox->addWidget( frame );
297 	}
298 };
299 
300 int FancyLabel::Private::smallFontSize = 0;
301 
FancyLabel(QWidget * parent)302 FancyLabel::FancyLabel (QWidget *parent)
303 : QWidget (parent)
304 {
305 	d = new Private (this);
306 }
307 
~FancyLabel()308 FancyLabel::~FancyLabel ()
309 {
310 }
311 
setText(const QString & text)312 void FancyLabel::setText (const QString &text)
313 {
314 	d->textStr = text;
315 	d->text->setText (QString("<font color=\"%1\"><b>").arg(d->font.name()) + text + "</b></font>");
316 }
317 
setHelp(const QString & help)318 void FancyLabel::setHelp (const QString &help)
319 {
320 	d->helpStr = help;
321 
322 	QString f1 = "<small>";
323 	QString f2 = "</small>";
324 	if ( d->smallFontSize ) {
325 		f1 = "<font>";
326 		f2 = "</font>";
327 	}
328 
329 	d->help->setText (QString("<font color=\"%1\">").arg(d->font.name()) + f1 + help + f2 + "</font>");
330 }
331 
setPixmap(const QPixmap & pix)332 void FancyLabel::setPixmap (const QPixmap &pix)
333 {
334 	d->pix->setPixmap( pix );
335 }
336 
setColorFrom(const QColor & col)337 void FancyLabel::setColorFrom (const QColor &col)
338 {
339 	d->from = col;
340 	d->frame->repaintBackground();
341 }
342 
setColorTo(const QColor & col)343 void FancyLabel::setColorTo (const QColor &col)
344 {
345 	d->to = col;
346 	d->frame->repaintBackground();
347 }
348 
setColorFont(const QColor & col)349 void FancyLabel::setColorFont (const QColor &col)
350 {
351 	d->font = col;
352 	d->frame->repaintBackground();
353 }
354 
text() const355 const QString &FancyLabel::text () const
356 {
357 	return d->textStr;
358 }
359 
help() const360 const QString &FancyLabel::help () const
361 {
362 	return d->helpStr;
363 }
364 
pixmap() const365 const QPixmap *FancyLabel::pixmap () const
366 {
367 	return d->pix->pixmap();
368 }
369 
colorFrom() const370 const QColor &FancyLabel::colorFrom () const
371 {
372 	return d->from;
373 }
374 
colorTo() const375 const QColor &FancyLabel::colorTo () const
376 {
377 	return d->to;
378 }
379 
colorFont() const380 const QColor &FancyLabel::colorFont () const
381 {
382 	return d->font;
383 }
384 
psiIcon() const385 const PsiIcon *FancyLabel::psiIcon () const
386 {
387 	return d->pix->psiIcon();
388 }
389 
setPsiIcon(const PsiIcon * i)390 void FancyLabel::setPsiIcon (const PsiIcon *i)
391 {
392 	d->pix->setPsiIcon(i);
393 }
394 
setPsiIcon(const QString & name)395 void FancyLabel::setPsiIcon (const QString &name)
396 {
397 	d->pix->setPsiIcon(name);
398 }
399 
psiIconName() const400 QString FancyLabel::psiIconName () const
401 {
402 	return d->pix->psiIconName();
403 }
404 
frameShape() const405 FancyLabel::Shape FancyLabel::frameShape () const
406 {
407 	return (FancyLabel::Shape)(int)d->frame->frameShape();
408 }
409 
setFrameShape(FancyLabel::Shape v)410 void FancyLabel::setFrameShape (FancyLabel::Shape v)
411 {
412 	d->frame->setFrameShape( (QFrame::Shape)(int)v );
413 	d->frame->repaintBackground();
414 }
415 
frameShadow() const416 FancyLabel::Shadow FancyLabel::frameShadow () const
417 {
418 	return (FancyLabel::Shadow)(int)d->frame->frameShadow();
419 }
420 
setFrameShadow(FancyLabel::Shadow v)421 void FancyLabel::setFrameShadow (FancyLabel::Shadow v)
422 {
423 	d->frame->setFrameShadow( (QFrame::Shadow)(int)v );
424 	d->frame->repaintBackground();
425 }
426 
lineWidth() const427 int FancyLabel::lineWidth () const
428 {
429 	return d->frame->lineWidth();
430 }
431 
setLineWidth(int v)432 void FancyLabel::setLineWidth (int v)
433 {
434 	d->frame->setLineWidth(v);
435 	d->frame->repaintBackground();
436 }
437 
midLineWidth() const438 int FancyLabel::midLineWidth () const
439 {
440 	return d->frame->midLineWidth();
441 }
442 
setMidLineWidth(int v)443 void FancyLabel::setMidLineWidth (int v)
444 {
445 	d->frame->setMidLineWidth(v);
446 	d->frame->repaintBackground();
447 }
448 
setScaledContents(int width,int height)449 void FancyLabel::setScaledContents(int width, int height)
450 {
451 	d->pix->setScaledContents(width, height);
452 }
453 
setSmallFontSize(int s)454 void FancyLabel::setSmallFontSize(int s)
455 {
456 	Private::smallFontSize = s;
457 }
458 
459 #include "fancylabel.moc"
460