是否有可能在一个自定义的控制,从设计师接受控制子面板?

问题描述 投票:2回答:1

我已经创建了一个简单的测试控制从Tcustom控制,其中包含2个面板继承。首先是对准到对准为alClient顶部和客户端面板的报头。

我想在客户端面板从设计师接受控制,虽然我可以放置在面板上的控制,它们在运行时不可见,并在项目被关闭,他们无法正确保存。

对于控制样品代码如下

unit Testcontrol;

interface
uses Windows,System.SysUtils, System.Classes,System.Types, Vcl.Controls,
     Vcl.Forms,Vcl.ExtCtrls,graphics,Messages;

type
  TtestControl = class(TCustomControl)
  private
    FHeader:Tpanel;
    FClient:Tpanel;
  protected
  public
    constructor Create(Aowner:Tcomponent);override;
    destructor Destroy;override;
  published
    property Align;
  end;

implementation

{ TtestControl }

constructor TtestControl.Create(Aowner: Tcomponent);
begin
  inherited;
  Fheader:=Tpanel.create(self);
  Fheader.Caption:='Header';
  Fheader.Height:=20;
  Fheader.Parent:=self;
  Fheader.Align:=altop;
  Fclient:=Tpanel.Create(Self);
  with Fclient do
  begin
    setsubcomponent(true);
    ControlStyle := ControlStyle + [csAcceptsControls];
    Align:=alclient;
    Parent:=self;
    color:=clwhite;
    BorderStyle:=bssingle;
    Ctl3D:=false;
    ParentCtl3D:=false;
    Bevelouter:=bvnone;
  end;
end;

destructor TtestControl.Destroy;
begin
  FHeader.Free;
  FClient.Free;
  inherited;
end;

end.

如果我把测试组件上的一个按钮,该结构显示它的形式,而不是测试组件的子组件的一部分....然后它不反正工作。

有没有办法做到这一点?

delphi delphi-10.2-tokyo
1个回答
2
投票

大量的谷歌搜索周围后,我发现这让我凑齐,似乎工作的解决方案的一些信息。

似乎有需要重写,以更新控制在基类中两个过程。

首先是所谓的“装”的方法当流结束时调用。

这似乎流的地方所有的基本组件上放置设计者子面板组件,而不是在面板上,他们原本是父母。所以加载过程结束后,该程序手动重新分配父属性。

第二种方法叫做的GetChildren,我找不到太多的信息,以什么这个方法实际上比CHM帮助非常模糊的文字做其他。不过我改编自另一个例子我这也有类似的要求在网络上找到的重写代码和它的工作。因此,如果任何人都可以提供一些见解,为什么这是必要的,那么这将是有用的信息。

我已经粘贴下面让任何人谁在未来有类似的要求,可以用它作为自己的组件的起始模板样本定制组件的完整源代码。

unit Testcontrol;

interface
uses Windows, System.Classes, Vcl.Controls, Vcl.Forms, Vcl.ExtCtrls,graphics;

type
  TtestControl = class(TCustomControl)
  private
    FHeader:Tpanel;
    FClient:Tpanel;
  protected
    procedure Loaded;override;
    procedure GetChildren(Proc:TGetChildProc; Root:TComponent);override;
  public
    constructor Create(Aowner:Tcomponent);override;
    destructor Destroy;override;
  published
    property Align;
  end;

implementation

{ TtestControl }

constructor TtestControl.Create(Aowner:Tcomponent);
begin
  inherited;
  Fheader:=Tpanel.create(self);
  Fheader.setsubcomponent(true);
  Fheader.Caption:='Header';
  Fheader.Height:=20;
  Fheader.Parent:=self;
  Fheader.Align:=altop;
  Fclient:=Tpanel.Create(Self);
  with Fclient do
  begin
    setsubcomponent(true);
    ControlStyle := ControlStyle + [csAcceptsControls];
    Align:=alclient;
    Parent:=self;
    color:=clwhite;
    BorderStyle:=bssingle;
    Ctl3D:=false;
    ParentCtl3D:=false;
    Bevelouter:=bvnone;
  end;
end;

destructor TtestControl.Destroy;
begin
  FHeader.Free;
  FClient.Free;
  inherited;
end;

procedure TtestControl.Loaded;
var i:integer;
begin
  inherited;
  for i := ControlCount - 1 downto 0 do
   if (Controls[i] <> Fheader) and (Controls[i] <> Fclient) then
     Controls[i].Parent := Fclient;
end;

procedure TtestControl.GetChildren(Proc:TGetChildProc; Root:TComponent);
var i:integer;
begin
  inherited;
  for i := 0 to Fclient.ControlCount-1 do
    Proc(Fclient.Controls[i]);
end;

end.
© www.soinside.com 2019 - 2024. All rights reserved.