如何动态获取某个类的所有方法/属性,并调用/访问之, 像Java中的反射一样? 800分赠送!
解决方案 »
- 求助:DBGrid中怎樣顯示SQL中固定為空的一列?
- 字符串转成日期类型
- 请问如何将xls文件的int类型保存到 sql server表的int字段中?
- 不知是不是发现了fastreport 中的大bug ,大家见来看看哟
- ADOCONNECTION连接文件DSN时,为什么在对数据库进行删除和更新是会出错啊
- 如何修改mainmenu中的某个Item的enabled属性?
- 给分啦!注册表问题
- 求购 《Delphi构建进销存-POS系统开发实例》 一书,手头有的朋友 请留下联系方式。
- 请问,如何使一个PANEL透明??
- 各位大侠:救命!!!动态生成控件的问题
- 如何设置一个自动编号字段作为索引字段,然后查找?
- 寻C++、Delphi全能高手,200分(之三)
在18章
unit Main;interfaceuses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, TypInfo, StdCtrls, Buttons, ComCtrls, ExtCtrls, ImgList;type
TDynIntArr = array of Integer;
TDynStrArr = array of string;
TDynArrClass = class(TObject)
private
FDynInt: TDynIntArr;
FDynStr: TDynStrArr;
procedure SetDynInt(const Value: TDynIntArr);
procedure SetDynStr(const Value: TDynStrArr);
published
property DynInt: TDynIntArr read FDynInt write SetDynInt;
property DynStr: TDynStrArr read FDynStr write SetDynStr;
end; TMainForm = class(TForm)
ListBoxClasses: TListBox;
MainSplitter: TSplitter;
TreeViewClassInfo: TTreeView;
ImageListClassInfo: TImageList;
procedure ListBoxClassesClick(Sender: TObject);
procedure FormCreate(Sender: TObject);
procedure TreeViewClassInfoGetImageIndex(Sender: TObject;
Node: TTreeNode);
private
{ Private declarations }
public
{ Public declarations }
end;var
MainForm: TMainForm;implementationuses JuTypInfo, JuUtils;{$R *.dfm}procedure TMainForm.ListBoxClassesClick(Sender: TObject); procedure SortBranches();
var
I: Integer;
begin
for I := 0 to Self.TreeViewClassInfo.Items.Count - 1 do
begin
if (Self.TreeViewClassInfo.Items[I].Text = 'Properties') or (Self.TreeViewClassInfo.Items[I].Text = 'Events') then
Self.TreeViewClassInfo.Items[I].CustomSort(nil, 0, False);
end;
end; procedure SetNodeImages();
var
I: Integer;
begin
for I := 1 to Self.TreeViewClassInfo.Items.Count - 1 do
begin
if Self.TreeViewClassInfo.Items[I].HasChildren then
Self.TreeViewClassInfo.Items[I].ImageIndex := 1
else
Self.TreeViewClassInfo.Items[I].ImageIndex := 2;
end;
end;var
StrList: TStrings;
TypeInfo: PTypeInfo;
begin
Self.TreeViewClassInfo.Items.Clear();
TypeInfo := PTypeInfo(Self.ListBoxClasses.Items.Objects[Self.ListBoxClasses.ItemIndex]);
StrList := JuTypInfo.TypeInfoToStrings(TypeInfo);
if Assigned(StrList) then
begin
try
StrList.SaveToFile('Result.txt');
LoadTreeNodesFromStrings(Self.TreeViewClassInfo.Items, nil, StrList);
SortBranches(); // Sort properties branches and events branches
SetNodeImages(); // Change image of node
Self.TreeViewClassInfo.Items[0].Expand(False); // Self.TreeViewClassInfo.FullExpand();
finally
FreeAndNil(StrList);
end;
end;
end;procedure TMainForm.FormCreate(Sender: TObject);
begin
with Self.ListBoxClasses.Items do
begin
AddObject('TApplication', System.TypeInfo(TApplication));
AddObject('TBitBtn', System.TypeInfo(TBitBtn));
AddObject('TButton', System.TypeInfo(TButton));
AddObject('TEdit', System.TypeInfo(TEdit));
AddObject('TLabel', System.TypeInfo(TLabel));
AddObject('TListBox', System.TypeInfo(TListBox));
AddObject('TMemo', System.TypeInfo(TMemo));
AddObject('TComponent', System.TypeInfo(TComponent));
AddObject('TPersistent', System.TypeInfo(TPersistent));
AddObject('TBits', System.TypeInfo(TBits));
AddObject('TObject', System.TypeInfo(TObject));
AddObject('TTypeKind', System.TypeInfo(TypInfo.TTypeKind));
AddObject('TAlignment', System.TypeInfo(TAlignment));
AddObject('TMultiReadExclusiveWriteSynchronizer', System.TypeInfo(TMultiReadExclusiveWriteSynchronizer));
AddObject('TForm', System.TypeInfo(TForm));
AddObject('TInterfacedObject', System.TypeInfo(TInterfacedObject));
AddObject('IStreamPersist', System.TypeInfo(IStreamPersist));
AddObject('TJuUniqueHash', System.TypeInfo(TJuUniqueHash));
AddObject('TDynArrClass', System.TypeInfo(TDynArrClass));
AddObject('TMainForm', System.TypeInfo(TMainForm));
end;
end;procedure TMainForm.TreeViewClassInfoGetImageIndex(Sender: TObject; Node: TTreeNode);
begin
if Node.IsFirstNode() then
begin
Node.ImageIndex := 0;
// if Node.Expanded then Node.ImageIndex := 0 else Node.ImageIndex := 1;
exit;
end;
if Node.HasChildren then
begin
if Node.Expanded then Node.ImageIndex := 2 else Node.ImageIndex := 1;
end
else
Node.ImageIndex := 3;
end;{ TDyn }procedure TDynArrClass.SetDynInt(const Value: TDynIntArr);
begin
FDynInt := Value;
end;procedure TDynArrClass.SetDynStr(const Value: TDynStrArr);
begin
FDynStr := Value;
end;end.
//将类的所有公开属性值组成字符串************************************************
//==============================================================================
function PropSaveStr(Instance: TObject): string;
var TypeInfo, PropTypeInfo: PTypeInfo;
TypeData: PTypeData;
PropInfo: PPropInfo;
PropList: PPropList;
PropName: string;
PropCount: word;
i: integer;
begin
Result := '';
TypeInfo := Instance.ClassInfo;
TypeData := GetTypeData(TypeInfo);
PropCount := TypeData^.PropCount;
GetMem(PropList, PropCount*SizeOf(Pointer));
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
try
{ Получаем список свойств}
GetPropInfos(TypeInfo, PropList);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
for i:=1 to PropCount do
begin
PropTypeInfo := PropList^[i-1]^.PropType^;
PropName := PropList^[i-1]^.Name;
PropInfo := PropList^[i-1];
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
case PropTypeInfo^.Kind of
tkEnumeration: Result := Result + PropName + ':' + GetEnumProp (Instance, PropInfo) + #13;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkVariant : Result := Result + PropName + ':' + GetVariantProp(Instance, PropInfo) + #13;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkInteger : Result := Result + PropName + ':' + IntToStr(GetOrdProp (Instance, PropInfo)) + #13;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkFloat : Result := Result + PropName + ':' + FloatToStr(GetFloatProp (Instance, PropInfo)) + #13;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkSet : Result := Result + PropName + ':' + GetSetProp (Instance, PropInfo) + #13;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkChar,
tkWChar,
tkString,
tkLString,
tkWString : Result := Result + PropName + ':' + GetStrProp (Instance, PropInfo) + #13;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkClass : Result := Result + PropName + ':' + VarToStr(GetPropValue (Instance, PropName)) + #13;
end;
end;
finally
FreeMem(PropList, PropCount*SizeOf(Pointer));
end;
end;//==============================================================================
//取得指定对象指定属性字符串值**************************************************
//==============================================================================
function GetPropStr(Instance: TObject; PropName: string): string;
var PropInfo: PPropInfo;
begin
PropInfo := GetPropInfo(Instance.ClassInfo, PropName);
case PropInfo.PropType^.Kind of
tkEnumeration: Result := GetEnumProp(Instance, PropInfo);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkVariant : Result := GetVariantProp(Instance, PropInfo);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkInteger : Result := IntToStr(GetOrdProp(Instance, PropInfo));
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkFloat : Result := FloatToStr(GetFloatProp(Instance, PropInfo));
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkSet : Result := GetSetProp(Instance, PropInfo);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkChar,
tkWChar,
tkString,
tkLString,
tkWString : Result := GetStrProp(Instance, PropInfo);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkClass : Result := VarToStr(GetPropValue(Instance, PropName));
else Result := '';
end;
end;//==============================================================================
//设置指定对象指定属性字符串值************************************************
//==============================================================================
function SetPropStr(Instance: TObject; PropName: string; PropValue: string): Boolean;
var PropInfo: PPropInfo;
begin
Result := True;
PropInfo := GetPropInfo(Instance.ClassInfo, PropName);
if Assigned(PropInfo) then
case PropInfo.PropType^.Kind of
tkEnumeration: SetEnumProp(Instance, PropInfo, PropValue);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkVariant : SetVariantProp(Instance, PropInfo, Variant(PropValue));
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkInteger : SetOrdProp(Instance, PropInfo, StrToInt(PropValue));
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkFloat : SetFloatProp(Instance, PropInfo, StrToFloat(PropValue));
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkSet : SetSetProp(Instance, PropInfo, PropValue);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkChar,
tkWChar,
tkString,
tkLString,
tkWString : SetStrProp(Instance, PropInfo, PropValue);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
tkClass : SetPropValue(Instance, PropName, Variant(PropValue));
else Result := False;
end else Result := False;
end;
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
改变控件颜色
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
procedure TForm_Main.Button30Click(Sender: TObject);
var PropInfo: PPropInfo;
i: integer;
begin
for i:=0 to ComponentCount-1 do
begin
PropInfo := GetPropInfo(Components[i].ClassInfo, 'Color');
if PropInfo<>nil then SetOrdProp(Components[i], PropInfo, clRed);
end;
end;
如果還不行, 可參考<<參透>>一書!建議: 這個問題, 給多個 100, 200分就算了, 不要搞什麼800分了!到時可能又有爭論