I wish to have the default margin for EditText's be 10dp. Therefore, in my styles.xml file I set up the following:
<resources xmlns:android="http://schemas.android.com/apk/res/android">
<style name="MyTheme" parent="android:style/Theme.NoTitleBar">
<item name="android:editTextStyle">@style/edit_text_default</item>
</style>
<style name="edit_text_default" parent="android:style/Widget.EditText">
<item name="android:layout_margin">10dp</item>
</style>
</resources>
Then in AndroidManifest.xml, I set the applications theme to the one I defined:
<application
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/MyTheme" >
...
The "No Title Bar" aspect of the theme is working. However, the default margin for EditText's is not, it is still filling the parent. Here is my table view:
<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#FFFFFF" >
<TableRow>
<EditText android:hint="@string/last_name" />
</TableRow>
<TableRow>
<EditText android:hint="@string/first_name" />
</TableRow>
</TableLayout>
Short Answer: If you are specifying layout_margin in a custom style, this style must be explicitly applied to each individual view that you wish to have the specified margin (as seen in the code sample below). Including this style in a theme and applying it to your application or an activity will not work.
<TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#FFFFFF" >
<TableRow>
<EditText android:hint="@string/last_name" style="@style/edit_text_default" />
</TableRow>
<TableRow>
<EditText android:hint="@string/first_name" style="@style/edit_text_default" />
</TableRow>
</TableLayout>
Explanation: Attributes which begin with layout_
are LayoutParams, or one of its subclasses (e.g. MarginLayoutParams). LayoutParams
are used by views to tell their parent ViewGroup how they want to be laid out. Each and every ViewGroup
class implements a nested class that extends ViewGroup.LayoutParams
. Therefore, LayoutParams
are specific to the ViewGroup
's type. What this means is that while a TableLayout
and a LinearLayout
may both have layout_margin
as one of it's LayoutParams
, they are considered to be completely different attributes.
So layout_margin
is not just general attribute that can be applied anywhere. It must be applied within the context of a ViewGroup
that specifically defines it as a valid argument. A view must be aware of the type of its parent ViewGroup
when LayoutParams
are applied.
Specifying layout_margin in a style, including that style in a theme, and attempting to apply that theme to an application/activity will result in the layout attributes being dropped, because no ViewGroup parent has been specified yet and so the arguments are invalid. However, applying the style to an EditText
view that has been defined with a TableLayout
works, because the parent ViewGroup
(the TableLayout
) is known.
Sources:
Android documentation on Layout Parameters.
Answer given to this question by Android framework engineer and StackOverflow user adamp.
Also, answer given to this question by StackOverflow user inazaruk.