当前位置:主页>仓库管理软件> 列表

控件关联

仓库管理软件版1楼: 如:Label加一个属性HangControl,用来设置要相关联的控件,如Combobox,
则当拖动Label时,Combobox也跟着移动。
这两个不是绑在一起,Label的HangControl也可设置其它的控件

2楼: 可以继承一个TLabel,自己实现,很容易的,在position变化后,跟着变化关了控件的Top和Left. 如管家婆软件报价

3楼: 设计期position变化要写在什么事件

4楼: 如果只是postion,那根本不需要写
用delphi的frame就可以搞定。

5楼: 控件的关联在Delphi中也是很常见的,我们可以设定一个控件的某个属性指向另一个控件。比如我们在窗体上放上Tedit,TpopupMenu两个控件,然后设定Tedit的PopupMenu属性为TpopupMenu控件,运行后在Tedit点击右键就会弹出刚才设定的那个TpopupMenu菜单,也就是说Tedit,TpopupMenu联手完成了任务。再比如TDBEdit控件的DataSource属性就可以指向一个TdataSource控件,这样就可以在TDBEdit控件中显示TdataSource输出的某个字段的值了。

下面我们将写一个简单的实现控件关联的控件。这个控件派生于Tedit,它可以与一个Tlabel控件关联,在控件的编辑框中输入文字时,与它关联的Tlabel控件的文字将随着它而变化。代码如下:



unit MyEdit;

interface

uses

SysUtils, Classes, Controls, StdCtrls;

type

TMyEdit = class(TEdit)

private

FLinkLabel: TLabel;

procedure FSetLinkLabel(AValue: TLabel);

protected

procedure Notification(AComponent: TComponent;Operation: TOperation);

override;

procedure Change;override;

public

published

property LinkLabel: TLabel read FLinkLabel write FSetLinkLabel;

end;



procedure Register;



implementation

procedure Register;

begin

RegisterComponents(''Linco'', [TMyEdit]);

end;

procedure TMyEdit.Change;

begin

inherited;

if LinkLabel <> nil then

LinkLabel.Caption := Text;

end;



procedure TMyEdit.FSetLinkLabel(AValue: TLabel);

begin

FLinkLabel := AValue;

if AValue <> nil then

FLinkLabel.FreeNotification(self);


end;



procedure TMyEdit.Notification(AComponent: TComponent;

Operation: TOperation);

begin

inherited;

if (Operation = opRemove) and (AComponent = LinkLabel) then

LinkLabel := nil;

end;

end.

代码解释:

(1)、我们只要将控件的任意一个属性的类型设定为另外一个控件的类名称,那么我们就可以在控件的Object Inspector中将这个属性指向那个控件(或那个控件的派生控件)的一个实例。比如本例中我们增加了LinkLabel属性,它的类型为 Tlabel,所以我们就可以把LinkLabel属性指向一个标签控件。

(2)、请注意FsetLinkLabel中的这段代码:

if AValue <> nil then

FLinkLabel.FreeNotification(self);

如果我们将控件关联属性指向了一个控件,可是后来又将被指向的控件删除了,那么我们的控件关联属性是不会自动删除的,这样就会造成控件关联属性指向的控件不存在的现象。我们必须自动感知被关联控件的删除并重新设定控件关联属性为不指向任何控件,这样就避免了错误的发生。

FLinkLabel.FreeNotification(self);的作用就是这样的。它调用控件的FreeNotification方法(在Tcomponent中定义)向被指向的控件注册一个“消息”,当被指向控件被删除时,会向所有向他注册的控件发送一个它被删除的消息,此时向他注册的控件就会触发Notification方法,这样我们就可以自动感知被指向控件的状态了。这是设计模式中Observer(观察者)模式的典型应用。

既然向他注册的控件就会触发Notification方法,我们就覆盖父类的Notification方法,写出如下的代码:

if (Operation = opRemove) and (AComponent = LinkLabel) then

LinkLabel := nil;

这句话的意思是:如果控件被删除并且被删除的控件(因为我们的控件可能向多个控件注册了消息)是LinkLabel,那么我们就设定LinkLabel属性不指向任何控件。

(3)覆盖父类的Change调度方法。在此方法里为连接的LinkLabel的Caption赋值就达到我们的目的了。

6楼: 谢谢fengxiaoxiao,你的观点是没错,
但是delphi里设计期没法获得控件位置(如你当前两个控件相差间距多少),从而控件跟着移动
onMouseDown
onMouseUp
onLButtonDown
onLButtonUp
这些消息函数在设计期捕捉不到啊