动态创建的对像,如何响应事件?(50分)

  • 主题发起人 主题发起人 sxwy
  • 开始时间 开始时间
S

sxwy

Unregistered / Unconfirmed
GUEST, unregistred user!
动态创建了一个BUTTON和LABEL,如何让他们也响应MOUSEDOWN事件?
 
procedure Form1.MouseDown(Sender: TObject);
begin
//do something;
end;

Button.OnMouseDown := MouseDown;
 
老问题了咯!!
来自:eloveme, 时间:2006-11-18 19:23:13, ID:3626610 | 编辑
参考下面的过程吧!!

procedure PP(Sender:TObject);
begin
showmessage('');
end;
procedure TForm1.FormCreate(Sender: TObject);
var
M: TMethod;
begin
M.Code:=@PP;
Button1.OnClick:=TNotifyEvent(M)
end;
记得分散分 :)
 
我想传递参数过去.这样参数传不了呢.

Procedure PP(Sender:Tobject;I:Integer);
begin
Showmessage('事件触发成功...');
end;
procedure TForm1.FormCreate(Sender: TObject);
Var Tmpbutt:Tbutton;
M: TMethod;
begin
Tmpbutt := Tbutton.Create(Self);
Tmpbutt.Caption := '测试';
Tmpbutt.Parent:= Form1;
Tmpbutt.Visible := True;
Tmpbutt.Top := 0;
Tmpbutt.Left := 10;
M.Code:=@PP(Tmpbutt,10);
Tmpbutt.OnClick := Tnotifyevent(M);
end;
 
to sxwy:
注意 :
把 M.Code:=@PP(Tmpbutt,10)
改成无参数形式传入
M.Code:=@PP
既可。
自己要多调试,才会学东西!!
 
现在要将传一个整形变量i或者字符到自定义响应过程PP里去.但是M.Code:=@PP
这样并没有传参数过去.
 
procedure Form1.DoMouseDown(I: Integer);
begin
ShowMessage(IntToStr(I));
end;
procedure Form1.MouseDown(Sender: TObject);
begin
DoMouseDown(100);
end;

Button.OnMouseDown := MouseDown;
 
to sxwy
你把要实现的事情和所想要做的事情可放在过程中完成啊,
你甚至可以在过程中再调用其他过程来完成所要做的事情啊。
 
ANiDelphi,你好,将动态创建的控件与窗体或者其它已经存在的控件关联事件,这个我会了.
比如;BUTTON.ONCLICK := FORM1.ONCLICK;这样按下动态创建的组件时,FORM1的ONCLICK会响应.但这样不能传递任意参数;
现在我想动态创建的组件有一个单独的事件响应,并且可以传入任意参数.

TO ELOVME:

能否写一个单独的过程,可传入参数,然后与动态创建的BUTTON关联,并让可传任意参数到过程.
 
由于button的OnClick已经定义为了TNotifyEvent,所以其参数是不能修改的。
TNotifyEvent已经被定死了:只能有一个TObject参数
type TNotifyEvent = procedure (Sender: TObject) of object;

不知道为什么你要传这么多参数呢
 
type TNotifyEvent = procedure (Sender: TObject) of object;
可以定义为
type TNotifyEvent = procedure (Sender: TObject;S:String) of object;
我见过这样的定义.但要将它关联到到一个动态创建的组件就不清楚.
 
TButton已经定了,要么自己写个事件咯。
type
TMyEvent = procedure (Sender: TObject; S: string) of object;
TMyButton = class(TButton)
private
FOnMyClick: TMyEvent;
published
property OnMyClick: TMyEvent read FOnMyClick write FOnMyClick;
end;

procedure TForm1.MyButtonClick(Sender; TObject; S: string);
begin
//do something
end;

procedure TForm1.AddMyButton(Sender; TObject);
var
MyButton: TMyButton;
begin
MyButton := TMyButton.Create(Self);
MyButton.OnMyClick := MyButtonClick;
MyButton.OnClick := MyButtonClick; //这样就出错了,类型不相同
end;

事件类型在类定义中已经定了,你要想要新的参数就要修改类了,象上面这样创建个新类,就可以用新的事件类型,也就可以用不同的参数了。
 
可以编译,但是动态生成的BUTTON显示在窗体上后,按下并没有响应事件.

procedure TForm1.Button2Click(Sender: TObject);
var
MyButton: TMyButton;
begin
MyButton := TMyButton.Create(Self);
Mybutton.Top := 10;
Mybutton.Parent := Form1;
Mybutton.Caption :='测试CLICK';
MyButton.OnMyClick := MyButtonClick;

这个时侯在窗体上会出现一个BUTTON,按下后,下面过程并没有触发;
procedure TForm1.MyButtonClick(Sender: TObject; S: string);
begin
//do something
Showmessage('');
end;
 
要在TMyButton内部写触发该事件的代码
unit Unit1;

interface

uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;

type
TMyEvent = procedure (Sender: TObject; S: string) of object;

TMyButton = class(TButton)
private
FOnMyClick: TMyEvent;
public
procedure Click; override; //重载TButton.Click;
published
property OnMyClick: TMyEvent read FOnMyClick write FOnMyClick;
end;

TForm1 = class(TForm)
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
procedure MyClick(Sender: TObject; S: string);
procedure ButtonClick(Sender: TObject);
public
{ Public declarations }
end;

var
Form1: TForm1;

implementation

{$R *.dfm}

{ TMyButton }

procedure TMyButton.Click;
begin
inherited Click; //引用TButton.Click,当中会触发OnClick事件
if Assigned(FOnMyClick) then //如果写了OnMyClick事件则运行其中的代码
FOnMyClick(Self, '');
end;

{ TForm1 }

procedure TForm1.ButtonClick(Sender: TObject);
begin
ShowMessage('ButtonClick');
end;

procedure TForm1.FormCreate(Sender: TObject);
var
MyButton: TMyButton;
begin
MyButton := TMyButton.Create(Self);
MyButton.Parent := Self;
MyButton.Name := 'MyButton';
MyButton.OnMyClick := MyClick;
MyButton.OnClick := ButtonClick;
end;

procedure TForm1.MyClick(Sender: TObject; S: string);
begin
ShowMessage(S); //S = '';在TMyButton的Click中赋的值
end;

end.
 
我想再重载BUTTON的MOUSE事件,怎么不行了呢.
unit Unit1;

interface

uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls;
type
TMyEvent = procedure (Sender: TObject; S: string) of object;
Tmyeventdown = Procedure (Sender:Tobject;S :String) of Object;
TMyButton = class(TButton)
private
FOnMyClick: TMyEvent;
FonMousedown:Tmyeventdown;
public
procedure Click; override; //重载TButton.Click;
procedure Mousedown; override; //重载TButton.mousedown;
published
property OnMyClick: TMyEvent read FOnMyClick write FOnMyClick;
Property Onmousedown: Tmyeventdown read Fonmousedown Write Fonmousedown;
end;


另,有没有办法不用继承实现这种方法,直接将动态创建的BUTTON的MOUSEDOWN事件或者CLICK事件指向到一个过程或者事件(不是窗体上已有的事件,而是自已定义的事件)呢.上面的方法太麻烦了.
 
重载要TButton原先就有的事件才行,还是用我原先的方法最简单了
procedure Form1.DoMouseDown(I: Integer);
begin
ShowMessage(IntToStr(I));
end;
procedure Form1.MouseDown(Sender: TObject);
begin
DoMouseDown(100);
end;

Button.OnMouseDown := MouseDown;
 
ANiDelphi:
BUTTON本来就有MOUSEDOWN呀.为什么不能续承呢.
 
MouseDown是在TControl声明的,而且其定义如下:
procedure MouseDown(Button: TMouseButton; Shift: TShiftState;
X, Y: Integer); dynamic;

要重载必须用相同的参数;
procedure MouseDown(Button: TMouseButton; Shift: TShiftState;
X, Y: Integer); override;
 
还是不能实现功能.唉,把想实现的功能说一下吧,
是这样的,动态创建了三个LABEL,显示在窗体上.
而在用户点击其中某一个LABEL时,要求得到点击LABEL的HANDLE,
并且要求本身可以响应MOUSEDOWN事件;
也就是要将动态创建LABEL的HANDLE传到其本身的MOUSEDOWN中,然后在其MOUSEDOWN中向这个HANDLE发消息,让其可以移动.

如果让你在动态创建LABEL中向本身发消息,你会怎么做呢.
 
Label没有Handle的吧
不如用Edit试试

procedure EditMouseDown(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer);
begin
if Sender is TEdit then
(Sender as TEdit).Handle;
end;
 
后退
顶部