【问题标题】:How to change the default value for the Margins property?如何更改 Margins 属性的默认值?
【发布时间】:2014-01-13 13:00:20
【问题描述】:

使用 Delphi XE2 向导创建组件,我选择了要继承的 TPanel,并更改了一些属性的默认值以适合我的应用程序。

我的问题是更改 Margins 的默认值:

  TControl = class(TComponent)
    ...
    property Margins: TMargins read FMargins write SetMargins;

Margins 是一个 TMargin 类,声明了 4 个属性,我需要重新定义默认值:

  TMargins = class(TPersistent)
  published
    property Left: TMarginSize index 0 read FLeft write SetMargin default 3;
    property Top: TMarginSize index 1 read FTop write SetMargin default 3;
    property Right: TMarginSize index 2 read FRight write SetMargin default 3;
    property Bottom: TMarginSize index 3 read FBottom write SetMargin default 3;

当调用组件的构造函数时,我可以/将在代码上设置边距,但是我不知道如何重新定义上面的这些默认值以便显示在属性编辑器上。

【问题讨论】:

  • 我有一种感觉,不能重新定义默认值。
  • @DavidHeffernan 是的,这是允许的,我在很多简单的情况下这样做,比如“property AlignWithMargins default true;”以前的默认值是假的。它可以工作并且它是文档的一部分,只需指定属性和新的默认值。但是我不知道在上述情况下如何做到这一点。

标签: delphi components delphi-xe2


【解决方案1】:

您可以使用自己的默认值声明您的TMargins 后代,以便在您的面板中使用

type
  TMyMargins = class(TMargins)
  protected
    class procedure InitDefaults(Margins: TMargins); override;
  published
    property Left default 10;
    property Top default 10;
    property Right default 10;
    property Bottom default 10;
  end;

class procedure TMyMargins.InitDefaults(Margins: TMargins);
begin
  with Margins do begin
    Left := 10;
    Right := 10;
    Top := 10;
    Bottom := 10;
  end;
end;


然后,当您创建面板时,关闭现有面板并使用您的面板

  TMyPanel = class(TPanel)
  private
    procedure DoMarginChange(Sender: TObject);
  public
    constructor Create(AOwner: TComponent); override;
  end;

constructor TMyPanel.Create(AOwner: TComponent);
begin
  inherited Create(AOwner);
  Margins.Free;
  Margins := TMyMargins.Create(Self);
  Margins.OnChange := DoMarginChange;
end;

procedure TMyPanel.DoMarginChange(Sender: TObject);
begin
  // same as in TControl which is private
  RequestAlign;
end;

只有当它们与默认值不同时,边距才会存储在 dfm 中。



虽然我不知道为什么上面的工作......上面代码的问题是,Margins 属性有一个只分配给边距(左,右......)的设置器。代码从不写入支持字段,但它仍然有效。线

Margins := TMyMargins.Create(Self);

实际上与

相同

TMyMargins.Create(Self);

这也有效。

我所说的“有效”是指,它有效。边距 f.i. 被正确销毁,不是因为所有权等原因。(边距是 TPersistent,不是组件),而是在上升的 TControl 调用 FMargins.Free 时。

无论如何,由于我不明白它是如何工作的,作为一种更安全但又很老套的方法,我会使用这个:

constructor TMyPanel.Create(AOwner: TComponent);
var
  Addr: NativeUInt;
begin
  inherited Create(AOwner);

  Addr := NativeUInt(@Margins);
  Margins.Free;
  PUINT_PTR(Addr)^ := NativeUInt(TMyMargins.Create(Self));
  Margins.OnChange := DoMarginChange;
end;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-01-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-08-04
    • 2014-01-05
    • 1970-01-01
    相关资源
    最近更新 更多