Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I dynamically create a list of all Android ui components programmatically? e.g. TextView, ImageView etc

I'm creating a program, and within which I need to create a list of all the different Android components but rather than figuring out and typing the List by hand. I'd like to figure out programmatically whether I could accomplish this to be added to String Arrays like the below?

Components[] = {"TextView", "ImageView", "RelativeLayout", "LinearLayout", "Random", "DecimalFormat ...

Similarly I would like to programatically create a List of all the different Data-Types e.g. Int, String, ArrayList etc. to be added to String Arrays like the below

DataTypes[] = {"Int", "String", "Object", "Double", "Char", "Boolean ...

What I have been able to do so far, is above. So far I've been physically typing them out as above.

How can I accomplish this? Thanks

Clarification

By data types: I mean variables types declared to holds data e.g Int, String, object, boolean, double, arrays, arraylists etc.

By Components: I mean any visual component which can be added to an Android's xml e.g. ImageView, TextView, LinearLayout, RelativeLayout etc.

Yes, I know the number of these components can be infinite (determined by the APIs in use), for which i would like to generate them dynamically

Preferably without using someone else's library


2 Answers

You don't have to use any third-party libraries, since Java has reflections. This method will do everything for you and make the UI without problems:

for(String s : arrayWithNames){
    View view = createViewInstance(0, s);
    if(view instance of View){
        //handle if it is view
    }else{
        //this is viewgroup
    }
}

And createViewInstance():

private View createViewInstance(String name){
    View view = null;
    try{
        if(name.equalsIgnoreCase("View"){ // if it is view
            Class viewClass = Class.forName("android.view." + name);
            view = (View) viewClass.getConstructor(Context.class).newInstance(new Object[]{ctx});
        }else{ // if it is widget: ImageView, RelativeLayout etc
            Class viewClass = Class.forName("android.widget." + name);
            view = (View) viewClass.getConstructor(Context.class).newInstance(new Object[]{ctx});
        }
    } catch (ClassNotFoundException | InvocationTargetException | NoSuchMethodException
            | InstantiationException | IllegalAccessException e) {
        e.printStackTrace();
    }
    return view;
}

That's it. You have everything to handle any kind of View. I've tested the code above and used in project. It works just fine. Exactly same situation with other Objects. You cannot create int with reflection, but you can create Integer, so what basically is same.

One problem with it there are much more types than just View and ViewGroup. But it also depends on how many kinds of Objects you want to create... In given example let's say I'll do char, String, int, Object and then you can easily extend it.

for(String s : arrayWithNames){
    if(s.equalsIgnoreCase("int")){
        Integer integer = (Integer)createVarInstance(s); //ready to use. Integer, not int!
    }else if(s.equalsIgnoreCase("String"){
        String string = (String)createVarInstance(s);
    }else if(s.equalsIgnoreCase("char"){
        Character character = (Character)createVarInstance(s); //Character, not char!
    }else if(s.equalsIgnoreCase("Object"){
        Object object = (Object)createVarInstance(s);
    }
}

Since all those data type are in the same package it makes much more easier for us. Method createVarInstance():

private Object createVarInstance(String name){
    Object obj = null;
    try{
        Class varClass = Class.forName("java.lang." + name);
        object = (Object) varClass.newInstance();
    } catch (ClassNotFoundException | InvocationTargetException | NoSuchMethodException
            | InstantiationException | IllegalAccessException e) {
        e.printStackTrace();
    }
    return object;
}

If it will be desired it is possible to make the one method for different packages. If in future you want to create more and different types of variables, which are in different packages, so you will have to check names or do similar operations as in example with Views.

like image 116
Yurets Avatar answered Sep 15 '25 04:09

Yurets


You can list UI components all the classes into the android.view package or the android.view.View sub-classes using The Reflection Library:

Reflections reflections = new Reflections("android.view");
//Reflections reflections = new Reflections("android.view.View");

Set<Class<? extends Object>> allClasses = reflections.getSubTypesOf(Object.class);

To create a list of all the data-type you could do the same above using th Object class, but first, I'd personally ask myself what's the point doing this.

like image 20
Mario Lenci Avatar answered Sep 15 '25 05:09

Mario Lenci