一个简单控件的源程序,有谁可以添加点注释!(300分)

  • 主题发起人 主题发起人 gravel
  • 开始时间 开始时间
G

gravel

Unregistered / Unconfirmed
GUEST, unregistred user!
这是一个可以在运行期间自由改变大小的panel,请添加注释,使注释的多少与
准确加分:
unit DdhSizer;
interface
uses
Classes, Windows, Messages, Controls, StdCtrls;

const
sc_DragMove: Longint = $F012;

type
TDdhSizePanel = class (TPanel)
public
procedure WmNcHitTest (var Msg: TWmNcHitTest);
message wm_NcHitTest;
end;

TDdhSizerControl = class (TCustomControl)
private
FControl: TControl;
FRectList: array [1..8] of TRect;
FPosList: array [1..8] of Integer;
public
constructor Create (AOwner: TComponent;
AControl: TControl);
procedure CreateParams (var Params: TCreateParams);
override;
procedure CreateHandle; override;
procedure WmNcHitTest (var Msg: TWmNcHitTest);
message wm_NcHitTest;
procedure WmSize (var Msg: TWmSize);
message wm_Size;
procedure WmLPanelDown (var Msg: TWmLPanelDown);
message wm_LPanelDown;
procedure WmMove (var Msg: TWmMove);
message wm_Move;
procedure Paint; override;
procedure SizerControlExit (Sender: TObject);
end;

procedure Register;

implementation

uses
Graphics;

// TDdhSizePanel methods
// TddhSizePanel的构造函数
procedure TDdhSizePanel.WmNcHitTest(var Msg: TWmNcHitTest);
var
Pt: TPoint;
begin
Pt := Point (Msg.XPos, Msg.YPos);
Pt := ScreenToClient (Pt);
if (Pt.x < 5) and (pt.y < 5) then
Msg.Result := htTopLeft
else if (Pt.x > Width - 5) and (pt.y < 5) then
Msg.Result := htTopRight
else if (Pt.x > Width - 5) and (pt.y > Height - 5) then
Msg.Result := htBottomRight
else if (Pt.x < 5) and (pt.y > Height - 5) then
Msg.Result := htBottomLeft
else if (Pt.x < 5) then
Msg.Result := htLeft
else if (pt.y < 5) then
Msg.Result := htTop
else if (Pt.x > Width - 5) then
Msg.Result := htRight
else if (pt.y > Height - 5) then
Msg.Result := htBottom
else
inherited;
end;

// TDdhSizerControl 的方法
//
constructor TDdhSizerControl.Create (AOwner: TComponent; AControl: TControl);
var
R: TRect;
begin
inherited Create (AOwner);
FControl := AControl;
// install the new handler
OnExit := SizerControlExit;
// 设置控件的大小和位置
R := FControl.BoundsRect;
InflateRect (R, 2, 2);
BoundsRect := R;
// 设置控件的Parent属性
Parent := FControl.Parent;
// create the list of positions
FPosList [1] := htTopLeft;
FPosList [2] := htTop;
FPosList [3] := htTopRight;
FPosList [4] := htRight;
FPosList [5] := htBottomRight;
FPosList [6] := htBottom;
FPosList [7] := htBottomLeft;
FPosList [8] := htLeft;
end;

procedure TDdhSizerControl.CreateHandle;
begin
inherited CreateHandle;
SetFocus;
end;

procedure TDdhSizerControl.CreateParams (var Params: TCreateParams);
begin
inherited CreateParams(Params);
Params.ExStyle := Params.ExStyle +
ws_ex_Transparent;
end;

procedure TDdhSizerControl.Paint;
var
I: Integer;
begin
Canvas.Brush.Color := clBlack;
for I := 1 to 8 do
Canvas.Rectangle (FRectList .Left, FRectList .Top,
FRectList .Right, FRectList .Bottom);
end;

procedure TDdhSizerControl.WmNcHitTest(var Msg: TWmNcHitTest);
var
Pt: TPoint;
I: Integer;
begin
Pt := Point (Msg.XPos, Msg.YPos);
Pt := ScreenToClient (Pt);
Msg.Result := 0;
for I := 1 to 8 do
if PtInRect (FRectList , Pt) then
Msg.Result := FPosList ;
// if the return value was not set
if Msg.Result = 0 then
inherited;
end;

procedure TDdhSizerControl.WmSize (var Msg: TWmSize);
var
R: TRect;
begin
R := BoundsRect;
InflateRect (R, -2, -2);
FControl.BoundsRect := R;
// setup data structures
FRectList [1] := Rect (0, 0, 5, 5);
FRectList [2] := Rect (Width div 2 - 3, 0,
Width div 2 + 2, 5);
FRectList [3] := Rect (Width - 5, 0, Width, 5);
FRectList [4] := Rect (Width - 5, Height div 2 - 3,
Width, Height div 2 + 2);
FRectList [5] := Rect (Width - 5, Height - 5,
Width, Height);
FRectList [6] := Rect (Width div 2 - 3, Height - 5,
Width div 2 + 2, Height);
FRectList [7] := Rect (0, Height - 5, 5, Height);
FRectList [8] := Rect (0, Height div 2 - 3,
5, Height div 2 + 2);
end;

procedure TDdhSizerControl.SizerControlExit (Sender: TObject);
begin
Free;
end;

procedure TDdhSizerControl.WmLPanelDown (var Msg: TWmLPanelDown);
begin
Perform (wm_SysCommand, sc_DragMove, 0);
end;

procedure TDdhSizerControl.WmMove (var Msg: TWmMove);
var
R: TRect;
begin
R := BoundsRect;
InflateRect (R, -2, -2);
FControl.Invalidate; // repaint entire surface
FControl.BoundsRect := R;
end;

//完成注册
procedure Register;
begin
RegisterComponents ('DDHB', [TDdhSizePanel]);
RegisterNoIcon ([TDdhSizerControl]);
end;

end.
 
主要是前面几个过程不太懂,帮帮忙!
 
问题出得很不合理,如果大家都来添加注释,岂不是每人都要重贴一份源程序?
贴子会越来越长的!!!

不如具体那里不懂提出来的了!
 
我对于编写控件是门外汉,但这个程序对我真的很有用,
请大家说说这个控件编写的思想(方法),我主要对
constructor TDdhSizerControl.Create
procedure TDdhSizerControl.WmNcHitTest
等过程不动。比较急,清各位大虾帮忙!
 
哈哈,考试吗?
 
TDdhSizePanel 和 TDdhSizerControl 有什么关系?
都是自己说,高手都不来大富翁了,真惨!300分也没用!
 
>>constructor TDdhSizerControl.Create
作初始化
>>procedure TDdhSizerControl.WmNcHitTest
使你的鼠标移到控件边框时可以改变大小

>>TDdhSizePanel 和 TDdhSizerControl 有什么关系?
没有直接关系。
 
TDdhSizerControl 应该是模拟Delphi设计时,Form中控件被选中时周围出现八个可以调节
控件大小的手柄,还可以拖动控件的行为的吧。
1、TDdhSizePanel
procedure WmNcHitTest(var Msg: TWmNcHitTest);
//处理WM_NCHITTEST消息,当鼠标在Panel内距边界小于5 pixels 时告诉Windows已到了
//Panel的Border,此时可以用鼠标调整Panel的大小。具体看Windows SDK Help 中对该
//消息的说明
2、TDdhSizerControl
constructor Create(AOwner: TComponent; AControl: TControl);
begin
inherited Create (AOwner); //初始化继承而来的属性
FControl := AControl; //AControl 应该是被选中要画出手柄的Control
OnExit := SizerControlExit; //自身失去焦点时释放自己
R := FControl.BoundsRect;
InflateRect (R, 2, 2);
BoundsRect := R; // 设置自己的位置、大小,叠在AControl之上
Parent := FControl.Parent; //设置了Parent才能显示在屏幕上
FPosList [1] := htTopLeft; //初始化与各手柄位置对应的WM_NCHITTEST消息
... //返回结果的查找表
FPosList [8] := htLeft;
end;
procedure CreateHandle;
//创建自己的窗口,使自己获得输入焦点,注意必须创建了窗口才能拥有焦点,因此不在
//Create中SetFocus
procedure CreateParams (var Params: TCreateParams);
//使创建的窗口具有透明的特性,看CreateWindowEx API的说明
procedure Paint;
//画出八个小手柄
procedure WmNcHitTest(var Msg: TWmNcHitTest);
//处理WM_NCHITTEST消息,当鼠标在手柄上时可以调节自己的大小,原理与TDdhSizePanel
//的一样,用到了Create中初始化的查找表。
procedure WmSize (var Msg: TWmSize);
//处理WM_SIZE消息,改变AControl的大小,计算八个手柄的位置及大小
...
procedure WmLPanelDown (var Msg: TWmLPanelDown);
//处理用户自定义的消息,改为WM_LBUTTONDOWN消息应该也行,给自己发消息,使自己处
//于可以被拖动的状态
procedure WmMove (var Msg: TWmMove);
//处理WM_MOVE消息,移动并重绘AControl
...
两个控件之间好象没有明显的关系,可能 WM_LPANELDOWN 是 TDdhSizePanel 发给
TDdhSizerControl 的自定义消息?
 
看看Delphi高级技术吧,上面有你这控件极其相似的控件的讲解。

实际上TDdhSizerControl可以放在任何一个控件上的。
 
多人接受答案了。
 
后退
顶部