what's different #android:id/list #+id/android:list? - android

i see two listview xml code:
<ListView
android:id="#android:id/list"
...
and
<ListView
android:id="#+id/android:list"
whats different between those?

#+id/test means you are creating an id named test in the namespace of
your application. You can refer to it using #id/test.
#android:id/test
means you are referring to an id defined in the android namespace.

Using the + tells Android to update the R.java file.
The plus-symbol (+) means that this is a new resource name that must be created and added to our resources (in the R.java file).
Read all about it at Android XML Layouts

Related

How to use Android RRO to overlay a layout?

I'm trying to customize Android 10 AOSP Settings app (com.android.settings) using a Runtime Resource Overlay (RRO).
When using a RRO, I can successfully customize any string in Settings app by putting a new value in the RRO's file ./res/values/strings.xml.
However, I cannot manage to overlay not a string but a layout by putting the layout file in the RRO's ./res/layout/ folder.
The RRO gets built, but the ids are different than the ones in the original layout, so after installing the RRO on device, the Settings app will fail to find the elements it expects in the layout file using findViewById().
For instance, I create a RRO containing the following bluetooth_pin_confirm.xml layout file (copied from Settings app source code and simplified) in its res/layout/folder:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="match_parent"
android:layout_width="match_parent"
android:orientation="vertical">
<TextView
android:id="#+id/pairing_caption"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
...
</LinearLayout>
After installing the RRO on device, the Settings app will successfully inflate this file in BluetoothPairingDialogFragment.java
View view = getActivity().getLayoutInflater().inflate(R.layout.bluetooth_pin_confirm, null);
But then it won't be able to find the views by id:
TextView pairingViewCaption = (TextView) view.findViewById(R.id.pairing_caption);
R.id.pairing_caption cannot be found so pairingViewCaption will be null
So it seems that the IDs in the layout file from the RRO are different than the original ones.
Indeed, when running aap2 dump on Settings app apk I can see:
resource 0x7f0a02e0 com.android.settings:id/pairing_caption: t=0x12 d=0x00000000 (s=0x0008 r=0x00)
While in the RRO I can see:
resource 0x7f010000 com.foo.settings:id/pairing_caption: t=0x12 d=0x00000000 (s=0x0008 r=0x00)
So yes, the Ids are different.
Now, it should be the whole point of the RRO when overlaying a layout to be able to match the Ids so to keep original Ids but change the layout around them. But how?
I've played a bit with aapt2 options --emit-ids and --stable-ids to try to force generated id to be equal to the one in Settings.apk, but that fails miserably as well:
error: can't assign ID 0x7f0a0303 to resource com.foo.settings:id/pairing_caption with conflicting ID 0x7f010000.
Note that this issue is specific to Android 10 and earlier. It seems that in Android 11 there is a new & better way to define mapping between ids in target and overlay package.
I'm pretty stuck here. Any suggestion would be greatly appreciated
On the link rro
you can find the following
Note: If you overlay a layout file, make sure all the IDs and app namespace attributes are included in both overlays.xml and overlayable.xml. For example:
<overlay>
<item target="layout/car_ui_base_layout_toolbar"
value="#layout/car_ui_base_layout_toolbar" />
<item target="id/car_ui_toolbar_background"
value="#id/car_ui_toolbar_background" />
<item target="attr/layout_constraintTop_toBottomOf"
value="#attr/layout_constraintTop_toBottomOf" />
</overlay>

difference in naming xml between res-auto and com.package.name - android

I have seen custom xml with :
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:custom="http://schemas.android.com/apk/res-auto"
and
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:custom="http://schemas.android.com/apk/com.package.custom"
whats the difference between these two separate names?
Is the latter only points to default location like your package?
Is the former points to the reference lib ?
thanks.
If we add a new custom view and its attributes inside our project, you add this at the beginning of your layout:
xmlns:custom="http://schemas.android.com/apk/res/your_main_app_package
If the new custom view is inside a library project linked to your project, you add this:
xmlns:custom="http://schemas.android.com/apk/res-auto
Note: This problem has been fixed in ADT revision 17+ . For any services or Activities, declare the namespace as follows:
xmlns:custom="http://schemas.android.com/apk/res-auto"
The suffix res-auto will be replaced at build time with the actual project package, so make sure you set up your attribute names to avoid collisions if at all possible.

TabHost and TabWidget android:id

I have noticed in my main.xml layout, I'm creating a Tab Layout, that the declaration of "android:id" is different from what I've used for button, textview, etc.
For example:
<TabWidget android:id="#android:id/tabs" />
and example on Buttons:
<Button
android:id="#+id/button_next" />
What is the difference of the two declarations?
When you assign an ID like so:
<Button
android:id="#+id/button_next" />
You are creating a new resource ID in your project's resources in the R.java file.
When you assign an id that is prefixed with #android:id, you are referencing a resource that exists in the android namespace.
I.e:
<TabWidget android:id="#android:id/tabs" />
In this case, you assign the id #android:id/tabs to the TabWidget, because it allows for your instance of TabWidget to inherit from an existing resource in the android namespace.
See this page for more info on the different ID assignments (scroll to the Attributes section)
Certain id's are used by the android framework. Like tabwidget,list etc. When the activity is launched it finds its required elements by searching the layout for these id's.
But when you are setting and id to a view for your own apps purpose, you only use id/yourid.
This is only going to be used by your application code.
blessenm is right. While we load the application it will search for the default id that are created by the android framework. and second one is the is that we use to define it just for our application purpose only.
The first one is use for all the application but the second one is use only for that perticular application.
Hope you got the point.
Thanks.

using merge with layouts giving error for one file, no error on other. same code!

I am creating a few layouts with the root element being merge. inside the merge element i have a ScrollView containing a TextView. Here is the file:
<?xml version="1.0" encoding="utf-8"?>
<merge
xmlns:android="http://schemas.android.com/apk/res/android">
<ScrollView
android:id="#+id/scroll"
android:padding="6dp"
android:layout_below="#id/headingLayout"
android:layout_above="#id/tabsLayout"
android:layout_width="fill_parent"
android:layout_height="wrap_content">
<TextView
android:id="#+id/aboutTxt"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</ScrollView>
</merge>
I am getting 2 errors: there is no resource to match the layout_below and layout_above names i have put in.
I have another layout xml file including very similar components, some of which also reference #id/headingLayout and #id/tabsLayout. Both of these XML layout files do not contain the component with name headingLayout or tabsLayout
Why is it that one layout file has no errors about these references and the other layout file does? What the crap am i doing wrong, the app will build and run like i expect, until i add this merge to another layout?
I have even tried copying the xml from the working layout file, to find that it gives the same errors, something must be wrong with my new layout file. I have tried cleaning, rebuilding, opening/closing eclipse..
Wow, this is a strange fix i have found for this. the layout i have given in my question above(the one giving errors) is named about.xml. the layout with no errors which also includes merge and references to other xml components is named home.xml. the xml file including the referenced components is named base_layout.xml.
in the eclipse Package Explorer under the layout folder, items are listed alphabetically. so the home.xml file came after base_layout.xml, and could therefore reference the components inside it. Since about.xml came before base_layout.xml, about.xml could not reference anything inside base_layout.xml.
so i just renamed base_layout.xml to aaa_base_layout.xml so it would be first, and all errors go away.

why is there different id syntax in the Android docs?

This page in the Android documentation defines an element id as follows:
<TextView android:id="#+id/label"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="Type here:" />
However this page defines it as:
<EditText id="text"
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent" android:layout_height="fill_parent"
android:textColor="#color/opaque_red"
android:text="Hello, World!" />
I thought I had a decent understanding of what was going on until I saw this second example. In the first case, you need the + character so that id 'label' is added to the R file, correct? In the second case, would the EditText's id not be added to the R file because it does not contain the + character?
Also, the second example does not include the android namespace on the id. Does having or not having the Android namespace affect whether that id will be added to the R file?
Thanks for any clarification.
This format without the android: namespace
id="text"
is from an earlier version of the Android SDK.
You are correct in your initial assessment. It's worth noting that the second id tag
<EditText id="text"
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent" android:layout_height="fill_parent"
android:textColor="#color/opaque_red"
android:text="Hello, World!" />
Is missing the android: namespace so it actually isn't an android xml tag. The first one is an example of how to add that view's id to the R file so you can access it in your code. To be honest, I'm not sure what the purpose of the id in the second example is*, but I know that android wouldn't know what to do with it. The first one is the correct syntax.
*This is just speculation, but I'm willing to bet it was a typo somebody didn't notice or didn't care to fix because they were trying to illustrate something else.
The plus-symbol (+) means that this is a new resource name that must be created and added to our resources (in the R.java file). There are a number of other ID resources that are offered by the Android framework. When referencing an Android resource ID, you do not need the plus-symbol, but must add the android package namespace, like so:
android:id="#android:id/empty"
Taken from Declaring Layout | Android Developers in the ID section.
However, in your second example there is no #android:id/ provided before the id text so to be brutally honest, I have never seen that notation before and wonder if that could be a typo on the author's part.
The second example is wrong. The attribute is always android:id and the value should be either #+id/myId (to create a new id called "myId") or #id/myId (to use an already defined id called "myId".) Using #android:id/theId lets you use ids defined by the android platform.

Categories

Resources