The question arose: is it possible to create an array of components of different types?

Very often you need to perform the same action for many objects, for example, to change a property:

TButton *a[]={Button1,Button2,Button3}; for (int i=0;i<sizeof(a)/sizeof(a[0]);i++) a[i]->Enabled=true; 

But what if the components are different, but they have some identical property that needs to be changed? Is it possible to accomplish this?

  • I advise you not only to read, but also to understand the PLO. Then it will be better to understand how to solve your question. - Jakeroid
  • possible on python - sudo97

3 answers 3

We divide the "same properties" into two groups.

The first group, it is mainly found in normal code. Identical properties are defined not in each component, but in some ancestor. It is enough to find a suitable ancestor and the task is greatly simplified. For TButton, see the list TObject -> TPersistent -> TComponent -> TControl -> TWinControl -> -TButtonControl -> TButton. I suspect that TWinControl will suit you. That is, if you create an array with TWinControl, then TButton, TEdit, and others can be added there.

Another group is when the properties, although they are the same, are simply declared on their own. It is not so simple here, there are different methods (reflection, writing of wrapper classes).

  • In theory, the first option is appropriate, but there is a problem: creating an array of TWinControl, because you still need to get a child element, since an error occurs “'property' is not a member of 'TWinControl'” - Crasher
  • Well, choose the right heir. What property exactly do you need to change? - KoVadim
  • You still have the dynamic_cast <> tool for descending the hierarchy, for example, if you need to find TButton * instances in the TWinControl * array. - vladimir_ki
  • one
    yes you can. But I don’t remember whether they have a clear common heir or not. But if that, for such cases you can write like this if obj [i] is TMemo then TMemo (obj [i]). Clear else if obj [i] is TEdit then TEdit (obj [i]). Clear else ShowMessage ('ups ! '); // but you can output nothing. This method is good because if you use the heirs from these components (for example, components with skins), then everything will work. - KoVadim 2:19 pm
  • one
    If I'm not mistaken, then the construction of the form x is TMemo will look like this dynamic_cast<TMemo*>(x) . - KoVadim

If these components have one common base class with the desired property, then you can declare an array containing the basic components, then assign the elements of the array to refer to the necessary components and edit the property.

 TComponent * a[] = {NULL, NULL, NULL}; TEdit edit1, edit2; TButton button; a[0] = edit1; a[1] = button; a[2] = edit2; for (int i=0;i<sizeof(a)/sizeof(a[0]);i++) a[i]->Enabled=true; 

    This is possible if all objects are inherited from one common class (interface), which has the necessary modification methods for the whole set. Example:

     #include "vector" // Абстрактный класс-интерфейс class IWindow { public: virtual ~IWindow(){}; virtual bool SetEnabled(bool enable) = 0; virtual int GetStatus() const = 0; }; class A: public IWindow { //реализация }; class B: public IWindow { //реализация }; class C: public B { //Тоже реализация }; //Набор объектов, в который можно "складывать" унаследованные //от IWindow объекты, чтобы их можно было одинаково обрабатывать. //ВНИМАНИЕ! Контейнер не управляет временем жизни его элементов! std::vector< IWindow* > cont; 
    • To format the code, select it with the mouse and click on the button 101010 of the editor. - Nicolas Chabanovsky