您的位置:首页 > 编程语言 > Delphi

Delphi经验技巧集锦

2004-12-18 18:51 309 查看

Delphi经验技巧集锦

---- 一.为列表框添光彩
---- 为了改变Listbox和Combobox两个控件的单调风格, 我想在它们的每一项前面加上个图标。从表面上看好像不大可能啦。就在走投无路的时候,我忽然发现这两个构件都有一个style属性, 它可以设为lbOwnerDrawFixed,Draw这个单词吸引了我,然后我又从Delphi的在线帮助中找到了一个相关的事件OnDrawItem,在这个事件中写一段代码,就可以在列表框中的每一项前面添加一个小图标啦。
---- 下面是在Listbox 的OnDrawItem事件中添加的代码:
procedure TForm1.ListBox1DrawItem(Control:
TWinControl; Index: Integer;
Rect: TRect; State: TOwnerDrawState);
var
Bitmap: TBitmap;
Offset: Integer;
begin
with (Control as TListBox).Canvas do
begin
FillRect(Rect);
Offset := 2;
Bitmap := TBitmap.create;
Bitmap.LoadFromFile(′d:/temp1/1.bmp′);
//指定图文件是d:/temp1/1.bmp
BrushCopy(Bounds(Rect.Left + 2, Rect.Top,
Bitmap.Width, Bitmap.Height),
Bitmap, Bounds(0, 0, Bitmap.Width,
Bitmap.Height), clRed);
Offset := Bitmap.width + 6;
TextOut(Rect.Left + Offset, Rect.Top,
(Control as TListBox).Items[Index])
end;
end;
---- 进一步,利用OnDrawItem事件的参数Index还可以在不同项前面添加不同的图标。还要告诉你的是, 当用add方法为列表框或下拉框添加项目时, 会自动执行 OnDrawItem事件,这样新添加的项目前面也就有了一个图标。
---- 二.获取count值
---- Delphi与Power Builder一样,都提供了SQL语言,来实现对数据库的访问,仅仅是实现语句的长短不同。Delphi是在Pascal语言基础之上发展起来的,它提供了强大的功能,各种控件提供了丰富的属性和方法。我们应该充分利用这些属性和方法。要想知道某数据库的记录数, 用一个简单的语句即可完成。例如求Delphi的DBDemos数据库中表 day.db的记录总数,假设Table控件已加到Form上,具体实现语句为:
Edit1.text:=inttostr(Table1.recordcount);
如果是要知道符合某条件的记录数,也非常方便,具体实现语句为:
Edit1.text:=inttostr(Query1.recordcount);
Recordcount属性用来表示为数据集相连的表的记录总数。
还有一种通用的方法,具体实现语句为:
VAR i:integer;
Begin
i:=0;
Table1.open;
Table1.First;
While not Table1.eof do
BEG1N
i:=i+1;
Table1.next;
End;
Edit1.text:=inttostr(i);
如果使用了TQuery控件,具体步骤如下:
Query1.close;
Query1.SQl.clear;
query1.SQL.add (′ ...... ′);
//某查询语句
Query1.open
Query1.first;
i:=0;
While not Query1.eof do
BEG1N
i:=i+1;
Query1.next;
EnD
Edit1.text:=Inttostr(i);
---- 三.给数据库报表加上网格线
---- Delphi 1.0和2.0版捆绑了Reportsmith报表制作工具,实现报表打印。如果打印一个很简单的报表,在程序中启动Reportsmith,就显得比较麻烦。对于比较简单的报表,我们一般按本报63期相应文章的方法实现报表打印。例如,用Delphi 1.0编写的商业财务软件《保灵商务营销管理系统》中报表打印就是自主开发的,整个系统显得短小、整体性比较好。Delphi 3.0和Delphi 4.0就不再捆绑Reportsmith,但增加了QReport组中报表控件的功能, 使得报表制作更加灵活。给报表加上网格线就太容易了。在QReport 组件中用来显示数据的TQRExpr。 它就有一个Frame属性, 按下 F11键, 在 “Object inspect”中,修改“Frame”属性,它提供7个子属性,其功能如下:
Color 显示网格线颜色
Style 报表网格线的形状,如实线、虚线等
Width 网格线的宽度
DrawBottom 网格的底部
Drawlefl 网格的左边
DrawRight 网格的右边
DrawTop 网格的底部
---- 在制做报表前,最好在数据库表中添加几个记录,然后根据需要修改这些属性,使用报表的预览功能在设计期间看修改效果,不满意可立即修改。
---- 四.定制Speedbar
---- 在Delphi的可视化设计界面中,使用最频繁的地方要数位于屏幕左上角的加速按钮栏(Speedbar)了。在实践过程中,笔者无意中发现了Speedbar的定制方法,这在我用过的四本Delphi参考书中均未提及到。步骤如下:
---- 右键点击Speedbar, 在弹出菜单中选Properties, 这时会出现一个名为Speedbar Editor的对话框。假设想要增设一项“语法检查”的功能,可在左边Categories列表框中选Project, 再把右侧的Syntax Check图标拖放到Speedbar的合适的位置上,这项功能就已经加上了。 如果speedbar上没有多余的空间来容纳新的按钮, 可将鼠标停在 speedbar右框处,变为双向箭头的形状时,向右拖动一段距离,就可腾出空间。如想删除speedbar上的某个按钮,可简单地把它拖出speedbar的范围,就能删除。操作十分方便。 建议把Syntax Check、 Project Options(工程选项) 、 WindowsApi Help加到 Speedbar中,可以提高开发效率。
---- 五.设计Form时的快捷键
---- 使用快捷键可以加快设计速度。下面列出的快捷键,可根据实际情况,有选择地熟练掌握。
Del :删除所选组件;
Esc :选择当前组件的容器(通常是Panel,Group或Form);
F11 :在Form或Unit和对象检查器之间切换;
F12 :在Form和代码编辑器间切换;
Ctrl+F12 :显示“查看Unit”对话框;
Shift+F12 :显示“查看Form”对话框;
TAB :下一个组件;
Shift+TAB :上一个组件;
方向键 :选中此方向上最近的组件;
Ctrl+方向键 :将所选组件移动一个点;
Shift+方向键 :将所选组件改变一个点的大小;
Ctrl+Shift+方向键 :将所选组件移动一个格;
Shift+click :按住Shift键再用鼠标点击组件,可以选择多个组件。
---- 下面这条是我摸索出来的: Ctrl+drag :按住Ctrl键在一个容器组件(如Panel,QReport,Groupbox等)里拖动鼠标,可强制选择鼠标拖过的矩形框中的所有属于此容器的可视组件(不包括该容器组件)。
---- 六.命令行参数的使用
---- Delphi提供了访问命令行参数的方便的方式,那就是使用ParamStr和ParamCount函数。其中ParamStr(0)返回的是当前程序名,如C:/TEST/MYPROG.EXE,ParamStr(1)返回第一个参数,以此类推;ParamCount则是参数个数。示例如下:
var
I: Word;
Y: Integer;
begin
Y := 10;
for I := 1 to ParamCount do begin
Canvas.TextOut(5, Y, ParamStr(I));

Y := Y + Canvas.TextHeight(ParamStr(I)) + 5;
end;
end;
---- 七.DCU文件(编译的库单元)的重用
---- (1)在interface里的uses子句中引用。如Windows,Dialogs等,要求被引用的DCU一定要放在Delphi4/Lib子目录中。
---- (2)在implementation里的uses子句中引用。如果是自行编写的DCU文件,应采用这一方式,并将被引用的DCU文件放入当前工程所在的子目录中。
---- 八.使用字符串资源的技巧
---- 不同于其它资源,字符串资源不能直接编辑,需要先按格式编制一个文本文件,再用程序将其编译成资源文件。下面用一个简单的例子来说明。首先用文本编辑器编一个文件lb.rc,其内容如下:
STRINGTABLE
BEGIN
1,"开始"
2,"退出"
END
---- 然后, 找到Delphi的Bin子目录下的BRCC32.EXE文件进行编译, 命令格式为: BRCC32 LB.RC,编译结束后即生成一个资源文件lb.res。要使用该资源文件,需要在单元文件implementation部分的开始处包括资源文件:{$R LB.RES}。在本例中,上面的字符串用于给一个命令按钮更换Caption设置, 使用的函数是Windows API函数 LoadString,以下是使用实例:
//在FormCreat过程中:
var
txtCaption:array [0..255] of char;
begin
//
if LoadString(HInstance,1,txtCaption,SizeOf
(txtCaption))〉0 then
btnStart.Caption:=StrPas(txtCaption);
end;
//在btnStartClick过程中:
var
txtCaption:array [0..255] of char;
begin
if LoadString(HInstance,2,txtCaption,
SizeOf(txtCaption))〉0 then
btnStart.Caption:=StrPas(txtCaption);
end;
---- 这样就可以在程序运行时改变各种属性,而不需要在程序中出现字符串。如果使用另一个Delphi函数LoadStr,会显得更加简单:
var
txtCaption:String;
begin
txtCaption:=LoadStr(2);
if txtCaption〈〉′′ then
btnStart.Caption:=txtCaption;
end;
---- 或许大家可以从以上的过程中看出, 使用123来标识一个字符串有些简陋,也很容易出错,那么怎么办呢?我们可以采取像C++中使用字符串的方法,为每个字符串预定义一个ID,如:
const
IDC—START=1;
IDC—EXIT=2;
---- 当然要把它放在一个unit里(类似于C++的.h文件) ,在使用的单元里再uses一下就可以了,这样应用感觉是不是很爽呢?
txtCaption:=LoadStr(IDC—EXIT);
---- 九.让图像旋转
---- Delphi中的Image构件可以显示位图,进一步,我们还可以用它完成位图旋转。
---- 把一个点绕原点旋转α角度后,新的坐标位置与原坐标位置的关系是:
X=xcosα-ysinα
Y= xsinα+ycosα
例如要把位图顺时针旋转90度,坐标变换公式为:X=-y Y=x
---- 把这一公式用到Image构件上,显示位图的主要问题是Image构件显示的位图只有一个象限, 并且x、y坐标也是互相颠倒的,为了解决这个问题,必须在Image构件上建立一个新的坐标原点。下面就举例说明。
---- 1. 新建一工程project1, 在form1上添加image1、 image2、 image3、image4,其 Autosize属性设为True, image1用来显示原图,image2、image3、image4分别用来显示旋转90度、180度和270度后的图像。双击image1,选定一幅bmp图。
---- 2. 添加Button1、Button2、Button3和Button4按钮,其caption属性分别为“原图”、 “旋转90度”、“旋转180度”、“旋转270度”。
---- 3. 编写“旋转90度”按钮的On Click事件。
procedure TForm1. Button2Click (Sender: TObject);
var
i,j:integer;
begin
//确定旋转后位图的大小
image2.Picture.Bitmap.Height:=image1.picture.width;
image2.Picture.Bitmap.Width:=image1.picture.height;
for i:=0 to image1.Height do
for j:=0 to image1.Width do
image2.canvas.Pixels[(-i+ image1.Height),
j]:=image1.canvas.Pixels[j,i];
end;
---- 4. 编写“旋转180度”按钮的On Click事件。
procedure TForm1.Button3Click(Sender: TObject);
var
i,j:integer;
begin
//确定旋转后位图的大小
image3.Picture.Bitmap.Height:=image1.picture.Height;
image3.Picture.Bitmap.Width:=image1.picture.Width;
for i:=0 to image1.Height do
for j:=0 to image1.Width do
image3.canvas.Pixels[(image1.Width
-j),(image1.Height-i)]:=image1.canvas.Pixels[j,i];
end;
---- 5. 编写“旋转270度” 按钮的On Click事件。代码和步骤3相似,只需要用image4 替换image2,然后用以下的语句替换步骤3 for循环中的原有的语句。
image4.canvas.Pixels[i,(image1.Width-j)]:=image1.canvas.Pixels[j,i];
---- 十.编程实现文件关联
---- 文件关联的目的是要实现某种扩展名的文件由相应的应用程序来打开,对于编写的应用软件来说,由于一般都有设计者特定的扩展名的数据文件,软件编制者应在程序中实现自动关联而不能由用户手工去实现。下面给出实现文件关联的实用程序。
---- 实现文件关联的核心是对注册表的操作, 所有的文件关联都在HKEY—CLASSES— ROOT 下面, 要实现文件关联必须在HKEY—CLASSES—ROOT 中增加两个键值,一是和文件扩展名对应的类型说明,二是对这种类型文件的操作所需要执行的应用程序。下面举例说明,本例实现将扩展名为.xyz的文件定义为“我自己的文件”类型,双击此种类型的文件时执行的打开功能使用记事簿程序。 实现这一功能需要用到Delphi中的函数 RegCreateKey、RegSetValue。实现如下:
---- 在窗体中放置一个按钮,双击按钮写如下代码:
procedure TForm1.Button1Click(Sender: TObject);
var
lphKey: HKEY;
sKeyName: string;
sKeyValue: string;
begin
sKeyName := ′myfile′;
sKeyValue := ′我的文档′;
RegCreateKey(HKEY—CLASSES—ROOT,
pchar(sKeyName), lphKey);
RegSetValue(lphKey, ′′, REG—SZ,
pchar(sKeyValue), 0);
sKeyName := ′.xyz′;
sKeyValue := ′myfile′;
RegCreateKey(HKEY—CLASSES—ROOT,
pchar(sKeyName), lphKey);
RegSetValue(lphKey, ′′, REG—SZ,
pchar(sKeyValue), 0);
sKeyName := ′myfile′;
sKeyValue := ′c:/Windows/NotePad.exe %1′;
RegCreateKey(HKEY—CLASSES—ROOT,
pchar(sKeyName), lphKey);
RegSetValue(lphKey, ′shell/open/command′, REG—SZ,
pchar(sKeyValue), MAX—PATH);
end;
---- 建立一新文件,使其扩展名为.xyz,然后双击它看是否是启动记事簿来打开的。
---- 十一.在一个Dbgrid中显示多数据库
---- 在数据库编程中,不必要也不可能将应用程序操作的所有数据库字段放入一个数据库文件中。正确的数据库结构应是:将数据库字段放入多个数据库文件,相关的数据库都包含一个唯一的关键字段,在多数据库结构里可以建立联系。
---- 例如:要编制一个人事管理程序,为简化演示程序,只建立两个数据库,每个数据库都只建立两个字段。
---- 个人简介 jianjie.dbf,由人事处维护;工资情况 gongzi.dbf,由财务处维护。
---- 1.数据库的建立
进入DataBase Desktop,建立数据库结构如下:
jianjie.dbf
编号 字段名:bianhao size:4 type:number
姓名 字段名:xingming size:10 type:character
gongzi.dbf
编号 字段名:bianhao size:4 type:number
工资 字段名:gongzi size:4 Dec 2 type:number
---- 注意: 两个数据库的bianhao字段的size、type必须一致。实际上,两数据库文件可以分布在网络的不同计算机上,为便于演示,分别存为″c: /test/jianjie.dbf″和 ″c:/test/gongzi.dbf″。
---- 2.应用程序的编制
---- 启动Delphi, 新建一个工程,在窗体中加入Query控件Query1,databasename属性设为c:/test;
---- 加入DataSource控件datasource1, DataSet属性设为Query1; 加入DbGrid控件 dbgrid1,DataSource属性设为DataSource1,将Query1.sql属性设为
SELECT DISTINCT A.bianhao,a.xingming, b.gongzi
FROM ″jianjie.dbf″ A, ″gongzi.DBF″ b
WHERE A.bianhao=b.bianhao
---- 再将Query1.enabled属性设为True, 不用编译, DbGrid1就会显示: bianhao, xingming, gongzi三个字段。如果jianjie.dbf和gongzi.dbf中有记录,则记录会显示出来。因篇幅所限,此文只介绍了Dbgrid中显示多个数据库内容的一般方法,读者可在此基础上进行完善,使该方法更好地适应您的需要。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: