Как исправить компонент Delphi с помощью свойства TFont, которое «не может назначить NIL для TFont» во время разработки? - PullRequest
6 голосов
/ 08 сентября 2011

Я начал создавать новый компонент в Delphi 6 Pro. В настоящее время у него есть только одно опубликованное свойство TFont. Однако, когда я перетаскиваю компонент на форму во время разработки и нажимаю кнопку редактирования свойства textAttr_1 (многоточие), я получаю исключение, говорящее «не может присвоить NIL TFont». Что я делаю не так, что вызывает эту ошибку? Ниже приведен код для компонента:

unit JvExtendedTextAttributes;

interface

uses
  Windows, Messages, SysUtils, Classes, JvRichEdit, Graphics;

type
  TJvExtendedTextAttributes = class(TComponent)
  private
    { Private declarations }
  protected
    { Protected declarations }
    FTextAttr_1: TFont;
  public
    { Public declarations }
    constructor Create(AOwner: TComponent);
  published
    { Published declarations }
    property textAttr_1: TFont read FTextAttr_1 write FTextAttr_1;
  end;

procedure Register;

implementation

procedure Register;
begin
  RegisterComponents('FAVORITES', [TJvExtendedTextAttributes]);
end;

// ---------------------------------------------------------------

constructor TJvExtendedTextAttributes.Create(AOwner: TComponent);
begin
    inherited Create(AOwner);

    FTextAttr_1 := TFont.Create;
end;

// ---------------------------------------------------------------


end.

1 Ответ

16 голосов
/ 08 сентября 2011

Ваша главная проблема в том, что вы забыли добавить override в конструктор вашего компонента.Это означает, что он не вызывается, потому что инфраструктура VCL использует преимущества виртуального конструктора TComponent.Это объясняет, почему ваш экземпляр шрифта равен nil.

Вам также необходим метод set, который вызывает Assign для копирования свойств шрифта, а не заменяет экземпляр, который неизбежно приводит к ошибкам повреждения памяти.1007 *

Источник VCL имеет бесчисленное множество примеров этого паттерна.Это выглядит так:

property Font: TFont read FFont write SetFont;
...
procedure TMyComponent.SetFont(Value: TFont);
begin
  FFont.Assign(Value);
end;
...