Using Android Getidentifier()

What does getResources().getIdentifier() do in android?

What getResources().getIdentifier does, is to return the specific resource numeric identifier given its actual resource name. Check the documentation for more specifics.

Documentation quote:

Return a resource identifier for the given resource name.

Note: use of this function is discouraged. It is much more efficient
to retrieve resources by identifier than by name.

A more clear explanation:

Lets say we must use a resource in code, such as for example:

view.setBackground(R.drawable.my_red_box)

In this example my_red_box is the name of the resource, but this name is actually an integer constant located in the resources 'R' file, which is autogenerated by gradle. So effectively, my_red_box is an integer constant, which Android uses to identify a specific resource file.

You can check a resource integer value by pressing the Ctrl key in your keyboard and hover with the mouse over the name of the resource in your code.
If you are more curious about the resource constants, then you can locate them in app/build/intermediates/runtime_symbol_list//R.txt

So, to clarify, whenever you type any resource identifier (R.drawable, R.raw, etc), you are actually typing an integer constant, and the system uses this constant to reference a resource file.

What getResources().getIdentifier does is to allow resolving resource integer constants using the name of the resource.

For example if we want to set the background in a View, we can do as usual:

// Set the resource by using the its identifier (resource integer constant)
view.setBackground(R.drawable.my_red_box)

But with getResources().getIdentifier will be as next:

int resourceID = getResources().getIdentifier("my_red_box", "drawable", getPackageName());
view.setBackground(resourceID);

In this last example the value returned in resourceID is exactly the same one as R.drawable.my_red_box.

The purpose of getResources().getIdentifier, is to obtain resources dynamically. The are many use cases, for example if you have several resources with the same name ending with a numeric index, then you could make a for loop and autogenerate the name dynamically, so "my_red_box_1", "my_red_box_2", etc.

for (int index = 0; index < 3; index++) {
int resourceID = getResources().getIdentifier("my_red_box_" + index, "drawable", getPackageName());
....
}

WARNING:

Using getResources().getIdentifier is not recommended, because Android can't know at compile time if the resource is being used, and therefore can be potentially removed when obfuscating / minimizing your code in a release build. In such case you need to add a proguard rule to keep the specific resources to avoid their removal.

Using Android getIdentifier()

Since you are inside of an activity it is enough to write

int resId = YourActivity.this.getResources().getIdentifier(
"ball_red",
"drawable",
YourActivity.this.getPackageName()
);

or if you're not calling it from an inner class

int resourceID = getResources().getIdentifier(
"ball_red",
"drawable",
getPackageName()
);

Note

getIdentifier() Returns 0 if no such resource was found. (0 is not a valid resource ID.)

Check

Check also in your R.java whether there is a drawable with the name ball_red

e.g.:

public static final class drawable {
public static final int ball_red = 0x7f020000;
}

EDIT
If you're not in any activity then you must pass a context instead of resources as parameter then do this

int resId = context.getResources().getIdentifier(
"ball_red",
"drawable",
context.getPackageName()
);

How to use getResources().getIdentifier to get a Button id?

If you are trying to get an id, the second argument should be "id".

You're trying to get an R.id value, not an R.button value because those don't exist

You also implemented the wrong click listener on your lights Activity (which should not extend Activity anyway, but that's unrelated to your question... Just don't be surprised if your current code doesn't work)

Hint: try this public lights(Context c, int rows, int col) and use c.getResources using that Context to create your resources, or possibly a setButtons(Button[][] buttons) method that you'd call from the Activity (since that's the only place you can call findViewById)

java android getResources().getIdentifier()

The problem appears to be that you are converting drawerSelection to lower case. As is clear in the R.java file, the case of the identifier is preserved. Try calling:

int panelId = this.getResources().getIdentifier(drawerSelection,"id",getActivity().getPackageName());

Obtain a drawable with getResources().getIdentifier() in android

Use setBackgroundResource() to set a background using a drawable (or color) resource given the resource ID.

How to use getResource.getIdentifier() to get Layout?

With this:

int layoutID = getResources().getIdentifier("layout"+n, "layout", getPackageName());

you basically retrieve the id of a layout file that you can inflate. It's the dynamic version of

int layoutID = R.layout.layout1;

What you intend to do is retrieve a view from an already inflated layout. That's how you'd do it:

int layoutID = getResources().getIdentifier("layout"+n, "id", getPackageName());
return (LinearLayout)findViewById(layoutID);

That's the dynamic version of

return (LinearLayout)findViewById(R.id.layout1);

Resources.getIdentifier(), possible values of deftype argument?

getIdentifier returns the id of the resource for the given resource name. typeDef refers to the type of the Resource (read more here). Keep in mind that the content of res is parsed at compile time and the R.java class is generated from the result of this parsing. In the end what you are looking for is a field declared in that class. I don't know the internal implementation, but if you provide array as res type, android will look up only on R.array, instead than on the whole R

getIdentifier() returns an invalid resource ID

After checking the internal classes, I found something interesting.

ResourcesImpl.java (inside package android.content.res)

int getIdentifier(String name, String defType, String defPackage) {
if (name == null) {
throw new NullPointerException("name is null");
}
try {
return Integer.parseInt(name);
} catch (Exception e) {
// Ignore
}
return mAssets.getResourceIdentifier(name, defType, defPackage);
}

In this method, it tries to parse the name as Integer first and if it is an Integer, it simply returns the value.
But if not, then is check it further down the road.

When you pass an integer(which is not a valid resource name anyway), it simply returns the value, per say. But this resource actually doesn't exist at all! And Boom! that why the crash.

Resource string is set to 0 when retrieving via getResources and getIdentifier

Try changing it from:

button_adj1.setText(String.valueOf(getResources().getIdentifier("adj"+ counter,"String", getPackageName())));

To:

button_adj1.setText(getResources().getIdentifier("adj"+ counter,"string", getPackageName()));

The changes:

  1. Use "string" not "String" in the call to getIdentifier() -> This solves the issue with the TextView being set to 0
  2. Remove valueOf and instead pass the resource ID of the string to setText() -> This prevents the TextView being set to 2131755036 for example

setText() has a couple of different overloads. But you want to ensure that this one is invoked:

public final void setText (int resid)

Not this one:

public final void setText (CharSequence text)

If on the other hand you want to use the latter overload, then getString() must be called passing the integer value of the resource ID.

TextView Docs



Related Topics



Leave a reply



Submit