Добрый день!
Создаю компонент со свойствами-множествами (unit MyComponent) и редактором свойств (unit PropertyEditor) по такой схеме:
unit MyComponent;
interface
uses
SysUtils, Types, Classes;
type
TMyDataRecord = record
MyData1 : Double;
MyData2 : Double2;
end;
TMyEnumType = (eFirst, eSecond, eThird);
TMySetTypeFirst = (poFirst1, poSecond1, poThird1);
TMySetTypeSecond = (poFirst2, poSecond2, poThird2);
TMySetTypeThird = (poFirst3, poSecond3, poThird3);
TMyObject = class (TPersistent)
private
FProperty1: Double;
FProperty2: Double;
FProperty3: Double;
function GetDataElement(Index : Integer): Double;
protected
public
procedure Assign (Source: TPersistent);
published
property Property1: Double index 0 read GetDataElement write FProperty1;
property Property2: Double index 1 read GetDataElement write FProperty2;
property Property3: Double index 2 read GetDataElement write FProperty3;
end;
type
TMyComponent = class(TButton)
private
FMyObject: TMyObject;
FMyEnum: TMyEnumType;
FMyOptions: Integer;
procedure SetMyObject(Value: TMyObject);
protected
public
constructor Create(AOwner: TComponent); override;
destructor Destroy; override;
function calculatesomedata : TMyDataRecord;
published
property MyObject : TMyObject read FMyObject write SetMyObject;
property MyEnumProp : TMyEnumType read FMyEnum write FMyEnum;
property MyOptions : Integer read FMyOptions write FMyOptions;
end;
procedure Register;
implementation
procedure TMyComponent.SetMyObject(Value: TMyObject);
begin
if Assigned (Value) then FMyObject.Assign(Value);
end;
constructor TMyComponent.Create (AOwner; TComponent);
begin
inherited Create (AOwner);
FMyObject := TMyObject.Create;
end;
destructor TMyComponent.Destroy;
begin
FMyObject.Free;
inherited Destroy;
end;
function TMyComponent.CalculateSomeData : TMyDataRecord;
begin
if если выбрано одно из подмноджеств TMySetTypeFirst или TMySetTypeSecond или TMySetTypeThird в редакторе свойств then
Result := здесь расчет и присваивание некого результата от TMyDataRecord в зависимости от значения FOptions;
end;
procedure TMyObject.Assign (Source: TPersistent);
begin
if Source is TMyObject then
begin
FProperty1 := TmyObject(Source).Property1;
FProperty2 := TmyObject(Source).Property2;
FProperty3 := TmyObject(Source).Property3;
inherited Assign (Source);
end;
function TMyObject.GetDataElement(Index : Integer): Double;
begin
Result := 0;
with TMyComponent(self) do
case Index of
0 : Result := CalculateSomeData.MyData1;
1 : Result := CalculateSomeData.MyData2;
2 : Result := CalculateSomeData.MyData3;
end;
end;
end.
============================================================
unit PropertyEditor;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, DesignIntf, DesignEditors, TypInfo;
type
TMySetTypeProperty = class(TEnumProperty)
private
function GetTypeInfo: PTypeInfo;
public
function GetValue: string; override;
procedure GetValues(Proc: TGetStrProc); override;
procedure SetValue(const Value: string); override;
end;
procedure Register;
implementation
uses UnitMyComponent;
function TMySetTypeProperty.GetTypeInfo: PTypeInfo;
var
Obj: TPersistent;
begin
Obj := GetComponent(0);
if Assigned(Obj) and (Obj is TMyComponent) then
with TMyComponent(Obj) do
begin
case MyEnumProp of
eFirst: Result := TypeInfo(TMySetTypeFirst);
eSecond: Result := TypeInfo(TMySetTypeSecond);
eThird: Result := TypeInfo(TMySetTypeThird);
end;
end
else
Result := GetPropType;
end;
function TMySetTypeProperty.GetValue: string;
var
L: Longint;
begin
L := GetOrdValue;
with GetTypeData(GetTypeInfo)^ do
if (L < MinValue) or (L > MaxValue) then L := MaxValue;
Result := GetEnumName(GetTypeInfo, L);
end;
procedure TMySetTypeProperty.GetValues(Proc: TGetStrProc);
var
I: Integer;
EnumType: PTypeInfo;
begin
EnumType := GetTypeInfo;
with GetTypeData(EnumType)^ do
begin
for I := MinValue to MaxValue do Proc(GetEnumName(EnumType, I));
end;
end;
procedure TMySetTypeProperty.SetValue(const Value: string);
var
I: Integer;
begin
I := GetEnumValue(GetTypeInfo, Value);
with GetTypeData(GetPropType)^ do
if (I < MinValue) or (I > MaxValue) then
raise Exception.Create('');
SetOrdValue(I);
end;
procedure Register;
begin
RegisterPropertyEditor(TypeInfo(Integer), TMyComponent, 'MyOptions', TMySetTypeProperty)
end;
end.
Вопрос:
Почему компоненнт не реагирует на переключение множеств в редакторе свойств (GetTypeInfo)?
Почему результаты вычислений функции CalculateSomeData не присваиваются полям FProperty1, FProperty2, FProperty3 моего компонента MyComponent?
Подскажите правильно ли я составил код компонента. Где ощибки в коде и как их исправить?
Спасибо.