我如何能实现某种类型的所有实例我自己的自定义属性编辑器?(How can I implement m

2019-07-05 19:47发布

我按照创建自定义属性编辑器对话框一些教程,但也有参与,我不能让它的工作权利,使很多事情。 我试图做到的是用日期选择器(日历),时间选择器,并确定和取消按钮自定义表单。 形式是完全没有问题的,但我将如何去实施,这样我可以在某种类型的任何组件发布的属性与按钮启动属性编辑器?

我想完全覆盖TDateTime类型,并把我的自定义编辑器在它的地方,所以只要一个TDateTime的出版,在Object Inspector中可见,我可以用这个编辑器在同一窗口中修改日期和时间在一起。

问题是,在创建自定义属性编辑器的文件很糟糕,虽然有些资源是非常彻底的,他们进入的功能,太多的细节,并没有得到该点上最常见的情况。

Answer 1:

我并不想在这里问这个问题,并希望任何人回答对我来说,我做了自己的研究来解决我的问题,我想与大家分享参与此项目的迷你独特的体验,因为我相信别人沮丧以同样的事情。

有自定义属性编辑器,对话框和组件编辑器很多不同的可能性。 这尤其会要求一个TDateTimeProperty后代。 这将让你能够直接在Object Inspector为纯文本(字符串)编辑属性的值,同时保持日期时间格式。

我假设你已经创建自定义组件,并在其中您可以发布从这个属性编辑器包的一般知识,因为这是在自己的一课,我将不包括。 这就要求只有一个行代码放在里面Register过程,但我们会在稍后谈到。

首先,你需要在你创建一个新的形式Design-Time包,你的组件注册。 命名单元DateTimeProperty.pas ,并命名形式DateTimeDialog (从而使窗体类TDateTimeDialog )。 任何地方控制你的需要,在这种情况下TMonthCalendarTDateTimePicker (与Kind设定为dtkTime ),和2所TBitBtn控制,一个标记为OKModalResultmrOK和其他标记CancelModalResultmrCancel

你的单位应该是这个样子:

unit DateTimeProperty;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants,
  System.Classes, Vcl.Graphics, Vcl.Controls, Vcl.Forms, Vcl.Dialogs,
  Vcl.ComCtrls, Vcl.StdCtrls, Vcl.Buttons;

type
  TDateTimeDialog = class(TForm)
    dtDate: TMonthCalendar;
    dtTime: TDateTimePicker;
    BitBtn1: TBitBtn;
    BitBtn2: TBitBtn;
  private

  public

  end;         

var
  DateTimeDialog: TDateTimeDialog;

implementation

{$R *.dfm}

end.

这里是DFM后面这种形式的代码:

object DateTimeDialog: TDateTimeDialog
  Left = 591
  Top = 158
  BorderIcons = [biSystemMenu]
  BorderStyle = bsToolWindow
  Caption = 'Pick Date/Time'
  ClientHeight = 231
  ClientWidth = 241
  Color = clBtnFace
  Font.Charset = DEFAULT_CHARSET
  Font.Color = clWindowText
  Font.Height = -11
  Font.Name = 'Tahoma'
  Font.Style = []
  OldCreateOrder = False
  Position = poScreenCenter
  DesignSize = (
    241
    231)
  PixelsPerInch = 96
  TextHeight = 13
  object dtDate: TMonthCalendar
    Left = 8
    Top = 31
    Width = 225
    Height = 166
    Anchors = [akLeft, akRight, akBottom]
    Date = 41261.901190613430000000
    TabOrder = 1
  end
  object dtTime: TDateTimePicker
    Left = 8
    Top = 8
    Width = 113
    Height = 21
    Date = 41261.000000000000000000
    Time = 41261.000000000000000000
    Kind = dtkTime
    TabOrder = 2
  end
  object BitBtn1: TBitBtn
    Left = 158
    Top = 200
    Width = 75
    Height = 25
    Caption = 'OK'
    Default = True
    ModalResult = 1
    TabOrder = 0
  end
  object BitBtn2: TBitBtn
    Left = 77
    Top = 200
    Width = 75
    Height = 25
    Caption = 'Cancel'
    ModalResult = 2
    TabOrder = 3
  end
end

现在,添加DesignEditorsDesignIntfuses条款。 请确保您有DesignIDE宣布在Requires如此Design-Time包。 这是必需的发布任何属性编辑器。

在窗体中,创建一个新的名为公共财产DateTime类型的TDateTime与属性getter和setter。 此属性将让你轻松读/写完整的TDateTime值的选择实际上代表。 所以,你应该有这个在您的形式:

private
  function GetDateTime: TDateTime;
  procedure SetDateTime(const Value: TDateTime);
public
  property DateTime: TDateTime read GetDateTime write SetDateTime;

....

function TDateTimeDialog.GetDateTime: TDateTime;
begin
  Result:= Int(dtDate.Date) + Frac(dtTime.Time);
end;

procedure TDateTimeDialog.SetDateTime(const Value: TDateTime);
begin
  dtDate.Date:= Value;
  dtTime.DateTime:= Value;
end;

接下来,我们需要添加实际的属性编辑器类。 创建这个类就在下面{$R *.dfm}这是刚下implementation

type
  TDateTimeEditor = class(TDateTimeProperty)
  public
    procedure Edit; override;
    function GetAttributes: TPropertyAttributes; override;
    function GetValue: String; override;
    procedure SetValue(const Value: String); override;
  end;

procedure TDateTimeEditor.Edit;
var
  F: TDateTimeDialog;
begin
  //Initialize the property editor window
  F:= TDateTimeDialog.Create(Application);
  try
    F.DateTime:= GetFloatValue;
    if F.ShowModal = mrOK then begin
      SetFloatValue(F.DateTime);
    end;
  finally
    F.Free;
  end;
end;

function TDateTimeEditor.GetAttributes: TPropertyAttributes;
begin
  //Makes the small button show to the right of the property
  Result := inherited GetAttributes + [paDialog];
end;

function TDateTimeEditor.GetValue: String;
begin
  //Returns the string which should show in Object Inspector
  Result:= FormatDateTime('m/d/yy h:nn:ss ampm', GetFloatValue);
end;

procedure TDateTimeEditor.SetValue(const Value: String);
begin
  //Assigns the string typed in Object Inspector to the property
  inherited;
end;

最后,我们需要添加一个Register程序来执行这个新属性编辑器的实际注册:

procedure Register;
begin
  RegisterPropertyEditor(TypeInfo(TDateTime), nil, '', TDateTimeEditor);
end;

现在有这个调用了解的重要棋子RegisterPropertyEditor 。 由于第二和第三个参数是nil和一个空字符串,这意味着编辑将适用于所有情况TDateTime 。 看这个过程大约使其具体到某些组件和财产情况的更多信息。

下面是安装后的最终结果...

对于这有助于自定义属性编辑器有一些很好的资源,如下所示:

  1. 如何让自定义组件属性?
  2. http://delphi.about.com/library/bluc/text/uc092501d.htm
  3. http://www.sandownet.com/propedit.html


文章来源: How can I implement my own custom property editor for all instances of a certain type?