There is insufficient information in the question.
There is insufficient information in the question. Where does the "type" of the form objects (in the question) come from? Is it simply a type name?
How does CreateObjects() discover the type that is required for each object? It cannot come from the "type" of the object reference passed in, as this may be (and almost certainly will be, as in your example) merely a base type from which the required concrete type will ultimately derive. Without more detailed information about your specific implementation goals and constraints, a complete, concrete answer is not possible.
However, in general terms what you seek may be achieved by a combination of virtual constructors and the RegisterClass / FindClass infrastructure provided by the VCL. In simple terms, you would have a base class that introduces the common constructor used to instantiate your classes for TComponent derived classes this already exists in the form of the Create(Owner: TComponent) constructor. At runtime you can then obtain a reference to any (registered) class using FindClass('TClassName').
This will return a class reference with which you can then invoke the appropriate virtual constructor: type TFoo = class .... TFooClass = class of TFoo; // etc var someClass: TFooClass; someObj: TFoo; begin someClass := TFooClass(FindClass('TFooDerivedClass')); someObj := someClass. Create(nil); : Note in the above that TFooDerivedClass is a class that ultimately derives from TFooClass (and is assumed for simplicity to derive in turn from TComponent and is instantiated with a NIL owner in this case). Classes that are already registered with the type system can be found using FindClass().
This includes any control or component class that is referenced by some DFM in your application. Any additional classes that need to be registered may be explicitly registered using RegisterClass(). How your specific application identifies the types of objects involved and any mapping of type names onto other arbitrary system of identification is an implementation detail that you must take care of.
1 You could invoke the appropriate non-virtual constructor and get the same effect. Virtual constructors and class references are related, but not co-dependent, concepts. – Rob Kennedy Mar 29 '10 at 15:14 Yes, of course - my mistake.
Thanks for the clarification. – Deltics Mar 29 '10 at 20:23.
Untested concept code: function instantiate(var instancevars : array of tobject; const classtypes : array of TBaseClassType):boolean; begin if (length(instancevars)=0) or (length(instancevars)length(classtypes)) then exit(false); for i:=0 to length(instancevars)-1 do instancevarsi:=classtypesi. Create; result:=true; end; Then use instantiate(lform1,lform2,tform1,tform2); to make it work. Note for this to work "TBaseClassType" must be some baseclass for all classes used for this function, and have a virtual constructor (e.g. TPersistent?
). Possibly you also need to correct the . Create line (e.g. Add (NIL) ) You can't get a type from a variable, the information is only available compiletime.
The constructor only needs to be virtual if descendant classes need to do different things in the constructor. Using a non-virtual constructor will still create instances of the correct type, and all the other virtual methods will still get invoked correctly, including AfterConstruction. – Rob Kennedy Mar 29 '10 at 15:00 You can change TBaseClassType to TObject and it will work for any class.
– skamradt Mar 29 '10 at 16:29 @skamradt overriden constructors will not be called – mjn Mar 29 '10 at 18:23 I know, I just didn't want to make it seem overly broad while there are limitations. – Marco van de Voort Mar 29 '10 at 19:17.
Quoting your comment on Henk's answer : That's what I don't want to do. I have a lot of server side methods where I create a lot of controls at runtime and I was wondering is creating objects as above would reduce the code. What do you mean by "a lot"?
If you mean a lot of components of exactly the same type (e. G : "but1, but2, but3, .. but55 : TButton;" ) then change your code and use an array to represent your variables - you can then make a simple loop to create them. If you mean a lot of components of different types (e.
G : but1 : TAnimatedButton; but2 : TFlatButton; but3 : T3DButton;), I don't see any simple method to do this, and I think you would create a small debugging hell more than anything else.
I cant really gove you an answer,but what I can give you is a way to a solution, that is you have to find the anglde that you relate to or peaks your interest. A good paper is one that people get drawn into because it reaches them ln some way.As for me WW11 to me, I think of the holocaust and the effect it had on the survivors, their families and those who stood by and did nothing until it was too late.