用DELPHI中Canvas特性开发图形软件---TCanvas方法说明

本文对比了Delphi中的TCanvas与VC++中的CDC绘图功能,通过具体实例介绍了如何利用Delphi进行Windows图形软件开发,包括绘制图形、设置画笔属性、图形复制与粘贴等功能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


======================================================
注:本文源代码点此下载
======================================================

http://www.yesky.com/20000713/93524.shtml

2000-07-13··-··-

p>以往开发windows图形软件大多用 vc ++ 作为开发工具, vc++强大的图形功能可以让程序员编制出许多优秀的与图形相关的软件。

vc++ 中与绘图相关的函数都封装在cdc及其衍生的cclientdc,cpaintdc,cwindowdc中。

delphi中也有一个与cdc相类似的类tcanvas,它封装了delphi 中的绘图函数。我们可以把delphi和vc中相同或相近的方法做个有趣的比较。

(一)canvas和 cdc绘图方法比较:

我们可以从以下表格中看到tcanvas和 cdc相似的函数:

表 1--1

canvas方法cdc方法功能

arcarc画一个椭圆弧

chordchord画一根玄。

copyrect拷贝指定矩形区域中图象到指定矩形

drawbitblt拷贝位图

ellipseellipse画椭圆

fillrectpaintrgn使用刷子填充一个又一个矩型

floodfillfloodfill用当前刷子填充区域

framerectframerect画一个矩形框

linetolineto画线到

movetomoveto移到

piepie画扇形

polygonpolygon画多边形

polylinepolyline画多根相连的线

rectanglerectangle画一个实心矩形

roundrectroundrect画一个圆角的矩形

stretchdrawstretchblt从源图象中

移动图象到指定矩形

textwidthgetcharwidth返回字符宽

textouttextout在指定坐标写字

textrectexttextout在制定矩形中写字

上表中,我们只列出部分绘图函数,详细了解,请参阅有关delphi和vc书籍.

与vc++ 相类似, delphi也提供了绘图工具,如tpen,tbrush等,与vc不同的是, delphi的绘图工具封装在tcanvas中。delphi也提供字形及字体大小的类tfont,下面我们用具体例子来分析它们的用法。

(二)用delphi 制作window95/nt图形软件。

象使用vc 一样,我们先用delphi的wizard建立一个 sdi 应用程序。delphi 自动建立sdi 框架, 先运行一次。程序现在还不能干任何事。下一步开始添加代码。

编辑主菜单。 增加write,draw俩个下拉菜单项。 在"write"下增加"helloworld!!","iamateacher","font.."菜单项.在aw"下增加"arc","line","polygon","roundrect","rectangle","color.","linestyle","widthline". 在"linestyle"菜单下增加"solid","dash","dot","dashdot","dashdotdot" 子菜单。

相应的在sdiform中增加colordialog,fontdialog,控件。

在onpaint事件中增加如下代码:

proceduretsdiappform.formpaint(sender:tobject);

begin

canvas.fillrect(rect);{清空桌面画布}

withsdiappformdo

posx:=clientwidthdiv2;

posy:=clientheightdiv2;{确定客户区中心点}

casedetectiof

1:

begin

setpenstate;

canvas.ellipse(posx-50,posy-50,posx+50,posy+50);

//penwidth:=oldwidth;

end;{在客户区中心点画圆}

2:

begin

setpenstate;

canvas.moveto(posx-60,posy-60);

canvas.lineto(posx+60,posy+60);

//penwidth:=oldwidth;

end;{在客户区画直线}

3:

begin

fposx:=trunc(50*cos(pi/6));

fposy:=trunc(50*sin(pi/6));

setpenstate;

canvas.polygon([point(posx-fposy,posy-fposx),

point(posx+fposy,posy-fposx),

point(posx+50,posy),point(posx+fposy,posy+fposx),

point(posx-fposy,posy+fposx),point(posx-50,posy)]);

//penwidth:=oldwidth;

end;{在客户区中心点画多边形}

4:

begin

setpenstate;

canvas.roundrect(posx-100,posy-50,posx+100,posy+50,

20,20);

end;{在客户区中心点画带圆角的矩形}

5:

begin

setpenstate;

sdiappform.canvas.brush.color:=clred;

canvas.rectangle(posx-100,posy-50,posx+100,posy+50);

sdiappform.canvas.brush.color:=bcolor;

end{在客户区中心点用红色刷子画矩形}

else

begin

canvas.font:=formfont;

canvas.textout(30,posy,str);

end;

end;{写字}

end;

上面程序中出现的变量在事件oncreate中初始化。

proceduretsdiappform.formcreate(sender:tobject);

begin

str:=;{要写在画布上的字符串}

formfont:=canvas.font;{字体和大小}

detecti:=0;{确定画布上出现何种图形的参数}

rect:=sdiappform.clientrect;{客户区矩形}

oldwidth:=sdiappform.canvas.pen.width;{最初画笔宽度}

penwidth:=oldwidth;{画笔宽度}

penstyle:=sdiappform.canvas.pen.style;{画笔类型}

pencolor:=sdiappform.canvas.pen.color;{画笔颜色}

bcolor:=sdiappform.canvas.brush.color;{画刷颜色}

end;

为了减少代码,定义了一个public过程,设定画笔。代码如下:

proceduretsdiappform.setpenstate;

begin

withsdiappform.canvas.pendo

begin

color:=pencolor;

style:=penstyle;

width:=penwidth;

end;

end;

响应每一个菜单项onclick事件本程序设计得非常简单,如果有兴趣,读者也可以加上一些代码,完成许多复杂的工作。

proceduretsdiappform.linecolor1click(sender:tobject);

begin

ifcolordialog1.executethen

begin

pencolor:=colordialog1.color;

sdiappform.canvas.pen.style:=psinsideframe;

ifpenwidth$#@60;1then

sdiappform.canvas.pen.width:=3;

sdiappform.canvas.pen.color:=pencolor;

invalidate;

end;

end;{完成画笔颜色设定}

//{完成画笔笔形设定}

proceduretsdiappform.solid1click(sender:tobject);

begin

penstyle:=pssolid;

invalidate;

end;

proceduretsdiappform.dot1click(sender:tobject);

begin

penstyle:=psdot;

invalidate;

end;

proceduretsdiappform.dash1click(sender:tobject);

begin

penstyle:=psdash;

invalidate;

end;

proceduretsdiappform.dashdot1click(sender:tobject);

begin

penstyle:=psdashdot;

invalidate;

end;

proceduretsdiappform.dashdotdot1click(sender:tobject);

begin

penstyle:=psdashdotdot;

invalidate;

end;

//////////////////////////////////

proceduretsdiappform.roundrect1click(sender:tobject);

begin

detecti:=4;

invalidate;

end;

proceduretsdiappform.rectangle1click(sender:tobject);

begin

detecti:=5;

invalidate;

end;

proceduretsdiappform.helloworld1click(sender:tobject);

begin

detecti:=0;

str:=helloworld!!;

invalidate;

end;

proceduretsdiappform.imateacher1click(sender:tobject);

begin

detecti:=0;

str:=iamateacher!!;

invalidate;

end;

proceduretsdiappform.fonts1click(sender:tobject);

begin

iffontdialog1.executethen

begin

detecti:=0;

formfont:=fontdialog1.font;

invalidate;

end;

end;{设定字体和大小}

编译并运行,可以看到画图的效果。

(三)图形的拷贝和剪贴

通过剪贴板可以完成拷贝和剪贴的功能。canvas不直接支持剪贴板,完成canvas上图画拷贝和张贴关键技巧是通过一个tbitmap变量,把canvas上的图形先复制到tbitmap上,再把tbitamp和window的剪贴板连起来,反过来也一样。

delphi通过鉴定wizard建立的sdi程序中,有关edit命令的click事件定义在actionlist控件中,相关代码如下:

//拷贝图形到剪贴板

proceduretsdiappform.editcopy1execute(sender:tobject);

var

bmp:tbitmap;//设置一个图形变量

begin

bmp:=tbitmap.create;

bmp.width:=rect.right+10;

bmp.height:=rect.bottom+10;

bmp.canvas.copyrect(rect,sdiappform.canvas,rect);

clipboard.assign(bmp);

bmp.free;

end;

//从剪贴板上复制

proceduretsdiappform.editpaste1execute(sender:tobject);

var

bmp:tbitmap;//设置一个图形变量

begin

ifclipboard.hasformat(cf_bitmap)then

begin

bmp:=tbitmap.create;

bmp.assign(clipboard);

sdiappform.canvas.draw(0,0,bmp);

bmp.free;

end

elseifclipboard.hasformat(cf_text)then

begin

str:=clipboard.astext;

detecti:=0;

invalidate;

end;

end;

//剪下图形拷贝到剪贴板

proceduretsdiappform.editcut1execute(sender:tobject);

begin

editcopy1execute(sender);

withsdiappform.canvasdo

begin

copymode:=cmwhiteness;

copyrect(rect,sdiappform.canvas,rect);

copymode:=cmsrccopy;

end;

end;

也可以把已有的图形文件直接拷贝在canvas上,本程序通过菜单open命令完成这一操作。

proceduretsdiappform.fileopen1execute(sender:tobject);

var

bmp:tbitmap;

currentfile:string;

begin

ifopendialog.executethen

begin

currentfile:=opendialog.filename;

ifcurrentfile$#@60;$#@62;then

try

bmp:=tbitmap.create;

bmp.loadfromfile(currentfile);

sdiappform.canvas.stretchdraw(rect,bmp);

finally

bmp.free;

end;

end;

end;

本程序只是简单的讨论了canvas绘图功能,离图形软件包还相差很远,而且打开图形文件显示在canvas中还有些问题,希望读者中编程高手能帮我改正。

绿色通道:好文要顶关注我收藏该文与我联系


======================================================
在最后,我邀请大家参加新浪APP,就是新浪免费送大家的一个空间,支持PHP+MySql,免费二级域名,免费域名绑定 这个是我邀请的地址,您通过这个链接注册即为我的好友,并获赠云豆500个,价值5元哦!短网址是http://t.cn/SXOiLh我创建的小站每天访客已经达到2000+了,每天挂广告赚50+元哦,呵呵,饭钱不愁了,\(^o^)/
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值