📄 qianb.txt
字号:
a.setPoints( 3, 0, 1, 0, sh-1, sw-1, sh/2 );
...........
p->drawPolygon( a ); //绘制三角形
}else if((pe == PE_ButtonBevel) || (pe == PE_ButtonCommand) || (pe == PE_ButtonTool)
|| (pe == PE_ButtonDropDown) || (pe == PE_HeaderSection))
{ //绘制按钮的各种效果使得看起来凸起或凹下。
qDrawShadePanel(p, r, cg, flags & (Style_Sunken | Style_Down | Style_On),
1, &cg.brush(QColorGroup::Button));
}else{
/*对于其他基本图形元素(PrimitiveElement)的绘制我们不作处理只是简单的调用父类的函数。*/
QWindowsStyle::drawPrimitive( pe, p, r, cg, flags, opt);
}
}
绘制整个spinBox的函数:
void CustomStyle::drawComplexControl( ComplexControl control,
QPainter *p,
const QWidget *widget,
const QRect &r,
const QColorGroup &cg,
SFlags flags,
SCFlags controls,
SCFlags active,
const QStyleOption& opt ) const
{
//下面的代码使得spinWidget呈现垂直显示的风格而不是通常的水平显示
if (control == CC_SpinWidget) {
const QSpinWidget * sw = (const QSpinWidget *) widget;
//绘制向上按钮部分,controls默认为SC_All,即绘制整个spinwidget
if ( controls & SC_SpinWidgetUp ) {
if ( sw->buttonSymbols() == QSpinWidget::PlusMinus )
pe = PE_SpinWidgetPlus; // 使用加减号
else
pe = PE_SpinWidgetUp; // 使用三角形
QRect re = sw->upRect();
QColorGroup ucg = sw->isUpEnabled() ? cg : sw->palette().disabled();
drawPrimitive(PE_ButtonBevel, p, re, ucg, flags); //绘制按钮的边框
drawPrimitive(pe, p, re, ucg, flags); //绘制按钮
}
//绘制向左按钮部分。
if ( controls & SC_SpinWidgetDown ) {
/*与绘制向下按钮相似*/
}
}else{//不处理spinbox之外的其他复杂控制部件,调用父类函数处理
QWindowsStyle::drawComplexControl(control, p, widget, r, cg, flags, controls, active, opt);
}
}
获取部件(widget)中各个子部件布局信息的函数,这个函数控制着一个widget的外观
QRect CustomStyle::querySubControlMetrics( ComplexControl control,
const QWidget *widget,
SubControl sc,
const QStyleOption &opt ) const
{
if(control == CC_SpinWidget){
int fw = pixelMetric( PM_SpinBoxFrameWidth, widget);
/*QSize 定义二维对象的大小,也就是宽和高. 坐标类型是QCOORD定义为int)*/
QSize bs; //此处bs表示每个按钮的大小,因为有两个按钮所以下面除以2.
bs.setWidth(widget->width()/2 -fw);
if(bs.width() < 8) bs.setWidth(8);
/*按钮高度设置为QMIN{按钮宽度的1.6倍, 部件高度的四分之一}
bs.setHeight( QMIN(bs.width()*8/5, widget->height() / 4) );
bs = bs.expandedTo( QApplication::globalStrut() );
int x = fw;
int y, ly, ry;
y = widget->height() - x - bs.height();
ly = fw;
ry = y - fw;
//下面定义了QSpinWidget的各个子部件的坐标位置.
switch ( sc ) {
case SC_SpinWidgetUp:
//返回向右按钮的坐标信息
return QRect(x + bs.width(), y, bs.width(), bs.height());
case SC_SpinWidgetDown:
//返回向左按钮的坐标信息
return QRect(x, y, bs.width(), bs.height());
case SC_SpinWidgetButtonField:
//返回两个按钮的总区域大小
return QRect(x, y, widget->width() - 2*fw, bs.height());
case SC_SpinWidgetEditField:
/*返回可编辑框的坐标信息*/
return QRect(fw, ly, widget->width() - 2*fw, ry);
case SC_SpinWidgetFrame:
//返回整个spinBox的坐标信息
return widget->rect();
default:
break;
}
}else{//其它部件的布局信息调用父类的函数来处理。
return QWindowsStyle::querySubControlMetrics(control,widget,sc,opt );
}
return QRect();
}
3.使用新风格
有两种方法使用新风格,一种是作为插件,一种是在应用程序里直接使用。作为插件的风格可以在不用修改代码、不用重新编译的情况下使用新风格。由于本文着重介绍如何创建风格所以我们使用第一种方法。这种方法很简单,只需在应用程序中包含相应风格类的头文件,然后把main()函数第一句可执行代码设置为 QApplication::setStyle(new MyStyle())即可。
下面我们用一个小例子来看看效果。
#include <qapplication.h>
#include <qspinbox.h>
#include "customstyle.h"
int main( int argc, char **argv )
{
QApplication::setStyle(new CustomStyle()); //使用新风格类来绘制界面。
QApplication a( argc, argv );
QSpinBox spin( 0, 15 );
spin.resize( 20, 100 );
a.setMainWidget( &spin );
spin.show();
return a.exec();
}
然后编译运行即可看到效果。
Ps. qt中编译使用qmake,步骤为
创建源程序
同一目录下运行qmake -project
qmake
make
运行可执行程序。
4.进一步工作
1)默认大小:细心的朋友可能看到上面的代码中有一句:spin.resize( 20, 100 ),这一句设置spinbox的长度为20象素,宽度为100个象素。如果没有这一句的话,显示的结果会一团糟,两个按钮几乎看不到
,因为qt默认的显示是水平显示而根本没有考虑垂直显示的情况。
如果想让spinbox在默认情况下看起来长度窄而宽度高需要修改QSpinBox类中的sizeHint函数,这个函数功能是设置部件(widget)的默认尺寸。在qt中几乎每个GUI部件类都有sizeHint这个函数来设置它自己的默认的长和宽。
文本垂直显示:在此例中虽然控件spinbox达到了垂直显示的效果,但是文本仍旧是水平显示的,因此要达到真正的垂直显示需要了解qt的文本显示机制。这些工作是很有意义的,因为有些民族(如蒙文)的语言传统就是垂直显示的,而现在没有一个真正满足这种需求的系统。笔者现在正在看qt-x11-free- 3.2.2的源码,目前对文本显示机制只有初步了解,还没有真正弄清,非常希望和感兴趣的朋友相互交流、学习。
参考资料
实例 源代码下载
Qt官方文档 http://doc.trolltech.com/3.2/index.html
Qt源代码:QStyle, QCommonStyle,QSpinWidget,QSpinBox从中可以了解很多的细节.
关于作者
姚延栋:中国科学院软件所2002级研究生,方向为系统软件和中文信息处理,对复杂文本处理和系统编程(Qt, Gtk等)很感兴趣,联系方式: ydyao@mails.gscas.ac.cn
对本文的评价
您对这篇文章的看法如何?
太差! (1) 需提高 (2) 一般;尚可 (3) 好文章 (4) 真棒!(5)
建议?
developerWorks 中国 > Linux >
关于 IBM 隐私条约 联系 IBM
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -