I make ActionBar in app.I change ActionBar style.There are some questions.
I want to change the title in the ActionBar.
So I write the follow code.
<resources>
<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
<!-- Customize your theme here. -->
<item name="android:actionBarStyle">#style/ActionBar</item>
<item name="actionBarStyle">#style/ActionBar</item>
<item name="actionOverflowButtonStyle">#style/overflowButton</item>
</style>
<!--ActionBar-->
<style name="ActionBar" parent="#style/Widget.AppCompat.Light.ActionBar.Solid.Inverse">
<item name="android:background">#color/bg</item>
<item name="background">#color/bg</item>
<item name="android:title">#string/test</item>
<item name="title">#string/test</item>
</style>
<style name="overflowButton">
<item name="android:src">#mipmap/ic_add_black_48dp</item>
<item name="android:showAsAction"></item>
</style>
</resources>
when I only write <item name="android:title">#string/test</item> ,it doesn't work,but write <item name="title">#string/test</item> it work.
I have try to solve in Android Developer,but fail.Please help me.
<item name="title">#string/test</item>
this tag works on supporting library, and
<item name="android:title">#string/test</item>
this one works on your android. For more detail please have a look on here
I hope you understand, If not please let me know.
Note: If you are using the Support Library APIs for the action bar, then you must use (or override) the Theme.AppCompat family of styles (rather than the Theme.Holo family, available in API level 11 and higher). In doing so, each style property that you declare must be declared twice: once using the platform's style properties (the android: properties) and once using the style properties included in the Support Library (the appcompat.R.attr properties—the context for these properties is actually your app).
Related
I would like to change the action bar size. I have tried the following coding.
<style name="MyTheme" parent="#android:style/Theme.Holo.Light">
<item name="android:actionBarStyle">#style/CustomActionBar</item>
</style>
<style name="CustomActionBar" parent="#android:style/Widget.Holo.Light.ActionBar">
<!-- <item name="android:background">#drawable/action_bar_style</item> -->
<item name="android:actionBarSize">15dp</item>
<item name="android:background">#drawable/header_bar</item>
</style>
But the action bar size didn't change. Is there another way? I am using api level 11.
Thanks.
Use height attribute, actionBarSize if for something else.
<item name="android:height">#dimen/bar_height</item>
Explanantion:
From source code of ActionBar:
mContentHeight = a.getLayoutDimension(R.styleable.ActionBar_height, 0);
We can see that R.styleable.ActionBar_height is being used for height. Stylable property names are generated as component_attribute (If you have ever used a custom stylable view, you'd have notice this). Hence, Actionbar is the name of component and height is the name of the attribute to use. Since this is a system attribute, hence defined under android namespace.
Update Dec-2014:
AppCompat library is now provided to extend support for latest ActionBar (or Toolbar) and theme support to old android versions. Below is an example of such an application theme /res/values/styles.xml:
<resources>
<!-- Application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light">
<!-- Main theme colors -->
<!-- your app branding color for the app bar -->
<item name="colorPrimary">#color/primary</item>
<!-- darker variant for the status bar and contextual app bars -->
<item name="colorPrimaryDark">#color/primary_dark</item>
<!-- theme UI controls like checkboxes and text fields -->
<!-- native widgets will now be "tinted" with accent color -->
<item name="colorAccent">#color/accent</item>
<!--Action bar style-->
<item name="android:actionBarStyle">#style/AppTheme.ActionBar</item>
<item name="actionBarStyle">#style/AppTheme.ActionBar</item>
</style>
<style name="AppTheme.ActionBar" parent="Widget.AppCompat.Light.ActionBar">
<item name="android:titleTextStyle">#style/AppTheme.ActionBar.TitleText</item>
<item name="titleTextStyle">#style/AppTheme.ActionBar.TitleText</item>
<item name="android:height">#dimen/bar_height</item>
<item name="height">#dimen/bar_height</item>
</style>
<style name="AppTheme.ActionBar.TitleText" parent="TextAppearance.AppCompat.Widget.ActionBar.Title">
<item name="android:textSize">#dimen/bar_text_size</item>
<item name="android:textColor">#color/bar_text_color</item>
</style>
</resources>
This style can now be set as app theme by using android:theme="#style/AppTheme" in <application> tag of the AndroidManifest.xml.
Note the use of duplicate entries
<item name="android:actionBarStyle">
<item name="actionBarStyle">
The ones without android namespace are there for supporting both compatibility library and native attributes.Some of these attributes didn't exist under android namespace on older versions and belong to support library.
In some other places, you'll need to use app namespace (xmlns:app="http://schemas.android.com/apk/res-auto"), for example app:showAsAction="always" in menu xml files.
Update Apr 2015
AppCompat Library v22 is also available. Read through the article to know what's new.
Simply put actionBarSize item under MyTheme style, like this:
<style name="MyTheme" parent="#android:style/Theme.Holo.Light">
<item name="android:actionBarSize">15dp</item>
<item name="actionBarSize">15dp</item>
...
</style>
Explanation:
In R.styleable we see that R.styleable.Theme_actionBarSize is a styleable attribute defined at Theme level.
Also, from source code res/values/styles.xml we see how actionBarSize is used to set height:
<style name="Widget.ActionBar">
...
<item name="android:height">?android:attr/actionBarSize</item>
Add this to the custom theme style XML that you are referencing from your manifest file:
<item name="android:windowTitleSize">58dip</item>
For instance if your manifest file looks something like this:
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
**android:theme="#style/AppTheme"** >
Your theme style should be -at least- like this:
<!-- Application theme. -->
<style name="AppTheme" parent="AppBaseTheme">
<item name="android:windowTitleSize">54dip</item>
</style>
S.D.'s solution does not work for me.
I used AppCompat v-21 library in my case.
And I just add
android:layout_height="#dimen/actionBarSize"
android:minHeight="#dimen/actionBarSize"
to my layout file and it works.
Make sure to add S.D.'s code to styles.xml and then add
android:theme="#style/thin_ab"
to the <application> element in the main manifest. (I'm a noob and it took me about 2 hours to find that out.)
Android Studio 2.1 preview 3
This is just a question, as I am confused as I have seen many alternatives in doing this.
I have created a new android project and my Activity extends AppCompatActivity
public class MainActivity extends AppCompatActivity {
I want to have the transparent statusbar on devices running 21 and over.
So in my values/styles I have the following
<resources>
<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">#color/colorPrimary</item>
<item name="colorPrimaryDark">#color/colorPrimaryDark</item>
<item name="colorAccent">#color/colorAccent</item>
</style>
</resources>
And in my values-21/styles I have the following
<resources>
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">#color/colorPrimary</item>
<item name="colorPrimaryDark">#color/colorPrimaryDark</item>
<item name="colorAccent">#color/colorAccent</item>
<!-- Make the statusbar transparent -->
<item name="android:windowTranslucentStatus">true</item>
</style>
</resources>
My Manifest I select the theme
android:theme="#style/AppTheme"
Just some questions
Is this the correct way, or is there any better way to do this?
Would values-21/styles inherit all the colors in values/styles so I would have to repeat this?
It's the right way. May I suggest you to organize your style better?
values/styles.xml
<resources>
<!-- Base application theme. -->
<style name="AppTheme" parent="CommonTheme">
</style>
<style name="CommonTheme" parent="Theme.AppCompat.Light.NoActionBar">
<item name="colorPrimary">#color/colorPrimary</item>
<item name="colorPrimaryDark">#color/colorPrimaryDark</item>
<item name="colorAccent">#color/colorAccent</item>
</style>
</resources>
values-v21/styles.xml
<resources>
<!-- Base application theme. -->
<style name="AppTheme" parent="CommonTheme">
<!-- All customization of the theme for this version -->
<item name="android:windowTranslucentStatus">true</item>
</style>
</resources>
So you don't need to repeat the common values of the style for every api level.
I will try to answer it giving some references
Maintaining Compatibility
To avoid duplication of code, define your styles inside res/values/,
modify the styles in res/values-v21/ for the new APIs, and use style
inheritance, defining base styles in res/values/ and inheriting from
those in res/values-v21/
So you should try to avoid code duplication in your style.xml at different folders res/values/ and res/values-v21/ by using style inheritance.
Style Inheritence
If you want to inherit from styles that you've defined yourself, you
do not have to use the parent attribute. Instead, just prefix the name
of the style you want to inherit to the name of your new style,
separated by a period.
If you want to inherit a style that you've defined yourself you can skip adding a parent attribute and inherit from it using a dot or period notation.
With this, you can define a base theme BaseTheme in res/values/ with different colors and inherit from it as BaseTheme.StyledStatusBar without specifying a parent attribute.
<resources>
<style name="BaseTheme.StyledStatusBar"></style>
<!-- Base application theme. -->
<style name="BaseTheme" parent="Theme.AppCompat.Light.NoActionBar">
<item name="colorPrimary">#color/colorPrimary</item>
<item name="colorPrimaryDark">#color/colorPrimaryDark</item>
<item name="colorAccent">#color/colorAccent</item>
</style>
</resources>
In values-21/, add item android:windowTranslucentStatus to BaseTheme.StyledStatusBar
<resources>
<style name="BaseTheme.StyledStatusBar">
<item name="android:windowTranslucentStatus">true</item>
</style>
</resources>
In manifest, select the theme
android:theme="#style/BaseTheme.StyledStatusBar"
1) Is this the correct way, or is there any better way to do this?
Yes. That's the correct/recommended way of having different values for different API versions.
2) Would values21/styles inherit all the colors in values/styles so I would have to repeat this?
I'm not sure I fully follow this question. Both styles you showed will inherit from Theme.AppCompat.Light.NoActionBar so your colors should be declared again, but I'll present two better alternatives:
Alternative 1, a little bit better:
Use a BaseTheme that is common for both. To view the code for it, please check #mimmo-grottoli answer.
Alternative 2, much better:
If the only different on the two themes is the android:windowTranslucentStatus that was introduced in KitKat (API level 19), you can put it all in the same theme in values/styles, like the following:
<resources>
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<!-- Customize your theme here. -->
<item name="colorPrimary">#color/colorPrimary</item>
<item name="colorPrimaryDark">#color/colorPrimaryDark</item>
<item name="colorAccent">#color/colorAccent</item>
<!-- Make the statusbar transparent -->
<item name="android:windowTranslucentStatus">true</item>
</style>
</resources>
The Android Framework ignores XML parameters that it does not recognize. That means that on JellyBean or ICS, the device will ignore windowTranslucentStatus while correctly applying the colors and in KitKat and up, it will correctly apply windowTranslucentStatus.
That tricky is valid for all XML in Android (even layouts), the IDE might give you warnings about API level, but in XML they're always safe to use.
Different folders of values/styles are made to give a unique style when your app is running on a specific version of Android.
So yes you are right when saying that the newer version inherits from the older one. When adding items in your latest version of styles you keep the latest version up to date to the latest APIs.
To conclude, your way is the very commun way, it's an organized and a clean way to keep your app updated.
Is this the correct way, or is there any better way to do this?
Yes. That's the right way of having different values for different API versions.
Would values-21/styles inherit all the colors in values/styles so I would have to repeat this?
Yes
technically <item name="android:windowTranslucentStatus">true</item> won't give you fully transparent statusbar.
If you want it to by fully transparent, you can use <item name="android:statusBarColor">#android:color/transparent</item>
I'm new to Android development, but I found really hard understanding how to style my apps using XML in "res/values/styles.xml".
In all the tutorials I found it seems that you can just inherit most of the style by declaring the "parent" field in tag, then change what you need to.
However most of the styles inherited in that way are non-public and recent restrictions on styling android Apps make inheritance of non-public styles nearly impossible.
I said "nearly" because I found solutions involving in lots of copy-paste from "Styles.xml" in the android SDK.
a clear example, found here on StackOverflow is:
http://android-argentina.blogspot.it/2011/08/error-retrieving-parent-for-item.html
applying these solutions, my simple xml:
<style name="MyActionBar" parent="#style/Widget.Holo.Light.ActionBar.Solid.Inverse">
<item name="android:background">#FF0000</item>
</style>
became:
<!-- Application theme. -->
<style name="AppTheme" parent="AppBaseTheme">
<!-- All customizations that are NOT specific to a particular API-level can go here. -->
<item name="android:actionBarStyle">#style/MyActionBar</item>
</style>
<!-- ActionBar styles -->
<style name="MyActionBar">
<!--copied from Widget.Holo.Light.ActionBar.Solid.Inverse -->
<item name="android:titleTextStyle">
#android:style/TextAppearance.Holo.Widget.ActionBar.Title.Inverse
</item>
<item name="android:subtitleTextStyle">
#android:style/TextAppearance.Holo.Widget.ActionBar.Subtitle.Inverse
</item>
<item name="android:background">#android:drawable/ab_solid_dark_holo</item>
<item name="android:backgroundStacked">#android:drawable/ab_stacked_solid_dark_holo</item>
<item name="android:backgroundSplit">#android:drawable/ab_bottom_solid_inverse_holo</item>
<item name="android:divider">#android:drawable/list_divider_holo_dark</item>
<item name="android:progressBarStyle">#android:style/Widget.Holo.ProgressBar.Horizontal</item>
<item name="android:indeterminateProgressStyle">#android:style/Widget.Holo.ProgressBar</item>
<item name="android:progressBarPadding">32dip</item>
<item name="android:itemPadding">8dip</item>
<!-- custom items -->
<item name="android:background">#FF0000</item>
</style>
At this point resouces like "#android:drawable/ab_bottom_solid_inverse_holo" are not public, and others cannot be fond inside the project (yes, even if they were "#android:drawable/SOMETHING") and will cause compiling errors, so this solution, found nearly everywhere in internet, just doesn't solve the problem at all.
I just wanted to change the background of an action bar without loosing all the base style, there MUST be an easy and smart way to do it.
So please help, there must be something stupid that i don't consider.
(sorry for my bad english)
Try this:
<style name="YourCustomTheme" parent="android:Theme.Holo.Light">
<item name="android:actionBarStyle">#style/Widget.Holo.ActionBar.XYZ</item>
</style>
<style name="Widget.Holo.ActionBar.XYZ" parent="#android:style/Widget.Holo.ActionBar">
<item name="android:background">#color/aw_blue</item>
</style>
I would like to change the action bar size. I have tried the following coding.
<style name="MyTheme" parent="#android:style/Theme.Holo.Light">
<item name="android:actionBarStyle">#style/CustomActionBar</item>
</style>
<style name="CustomActionBar" parent="#android:style/Widget.Holo.Light.ActionBar">
<!-- <item name="android:background">#drawable/action_bar_style</item> -->
<item name="android:actionBarSize">15dp</item>
<item name="android:background">#drawable/header_bar</item>
</style>
But the action bar size didn't change. Is there another way? I am using api level 11.
Thanks.
Use height attribute, actionBarSize if for something else.
<item name="android:height">#dimen/bar_height</item>
Explanantion:
From source code of ActionBar:
mContentHeight = a.getLayoutDimension(R.styleable.ActionBar_height, 0);
We can see that R.styleable.ActionBar_height is being used for height. Stylable property names are generated as component_attribute (If you have ever used a custom stylable view, you'd have notice this). Hence, Actionbar is the name of component and height is the name of the attribute to use. Since this is a system attribute, hence defined under android namespace.
Update Dec-2014:
AppCompat library is now provided to extend support for latest ActionBar (or Toolbar) and theme support to old android versions. Below is an example of such an application theme /res/values/styles.xml:
<resources>
<!-- Application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light">
<!-- Main theme colors -->
<!-- your app branding color for the app bar -->
<item name="colorPrimary">#color/primary</item>
<!-- darker variant for the status bar and contextual app bars -->
<item name="colorPrimaryDark">#color/primary_dark</item>
<!-- theme UI controls like checkboxes and text fields -->
<!-- native widgets will now be "tinted" with accent color -->
<item name="colorAccent">#color/accent</item>
<!--Action bar style-->
<item name="android:actionBarStyle">#style/AppTheme.ActionBar</item>
<item name="actionBarStyle">#style/AppTheme.ActionBar</item>
</style>
<style name="AppTheme.ActionBar" parent="Widget.AppCompat.Light.ActionBar">
<item name="android:titleTextStyle">#style/AppTheme.ActionBar.TitleText</item>
<item name="titleTextStyle">#style/AppTheme.ActionBar.TitleText</item>
<item name="android:height">#dimen/bar_height</item>
<item name="height">#dimen/bar_height</item>
</style>
<style name="AppTheme.ActionBar.TitleText" parent="TextAppearance.AppCompat.Widget.ActionBar.Title">
<item name="android:textSize">#dimen/bar_text_size</item>
<item name="android:textColor">#color/bar_text_color</item>
</style>
</resources>
This style can now be set as app theme by using android:theme="#style/AppTheme" in <application> tag of the AndroidManifest.xml.
Note the use of duplicate entries
<item name="android:actionBarStyle">
<item name="actionBarStyle">
The ones without android namespace are there for supporting both compatibility library and native attributes.Some of these attributes didn't exist under android namespace on older versions and belong to support library.
In some other places, you'll need to use app namespace (xmlns:app="http://schemas.android.com/apk/res-auto"), for example app:showAsAction="always" in menu xml files.
Update Apr 2015
AppCompat Library v22 is also available. Read through the article to know what's new.
Simply put actionBarSize item under MyTheme style, like this:
<style name="MyTheme" parent="#android:style/Theme.Holo.Light">
<item name="android:actionBarSize">15dp</item>
<item name="actionBarSize">15dp</item>
...
</style>
Explanation:
In R.styleable we see that R.styleable.Theme_actionBarSize is a styleable attribute defined at Theme level.
Also, from source code res/values/styles.xml we see how actionBarSize is used to set height:
<style name="Widget.ActionBar">
...
<item name="android:height">?android:attr/actionBarSize</item>
Add this to the custom theme style XML that you are referencing from your manifest file:
<item name="android:windowTitleSize">58dip</item>
For instance if your manifest file looks something like this:
<application
android:allowBackup="true"
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
**android:theme="#style/AppTheme"** >
Your theme style should be -at least- like this:
<!-- Application theme. -->
<style name="AppTheme" parent="AppBaseTheme">
<item name="android:windowTitleSize">54dip</item>
</style>
S.D.'s solution does not work for me.
I used AppCompat v-21 library in my case.
And I just add
android:layout_height="#dimen/actionBarSize"
android:minHeight="#dimen/actionBarSize"
to my layout file and it works.
Make sure to add S.D.'s code to styles.xml and then add
android:theme="#style/thin_ab"
to the <application> element in the main manifest. (I'm a noob and it took me about 2 hours to find that out.)
I am doing a personal theme to use holo widget in 2.3 android.
I did this:
<resources xmlns:android="http://schemas.android.com/apk/res/android">
<style name="AppThemes" parent="#style/Theme.Sherlock">
<item name="android:editTextStyle">#style/EditTextAppTheme</item>
<item name="android:checkboxStyle">#style/CheckBoxAppTheme</item>
<item name="android:radioButtonStyle">#style/RadioButtonAppTheme</item>
<item name="android:buttonStyle">#style/ButtonAppTheme</item>
<item name="android:imageButtonStyle">#style/ImageButtonAppTheme</item>
<item name="android:spinnerStyle">#style/SpinnerAppTheme</item>
<item name="android:dropDownSpinnerStyle">#style/SpinnerAppTheme.DropDown</item>
<item name="android:spinnerDropDownItemStyle">#style/SpinnerDropDownItemAppTheme</item>
</style>
</resources>
the problem is that widgets don't take the correct style but take the default style. I tried to force assign the #style/EditTextAppTheme at an edittext and it worked.. so the problem is that the theme don't apply.
any idea?
update: the theme apply and work good..the solo problem is some edittext inside a dialog that show with the standard theme
To get the holo theme style in an App for API 10 and below, you can use HoloEverywhere. It's well integrated with ActionBarSherlock. ActionBarSherlock is included as a subproject. https://github.com/ChristopheVersieux/HoloEverywhere
If you want to use a customized Theme you have to set these style attributes in your Application theme. Then apply this theme to the whole App or to a single Activity by defining it in the manifest or setting it programmaticaly in the onCreate() method.
For example(for ABS):
<style name="Theme.myStyle" parent="Theme.Sherlock">
<item name="android:editTextStyle">#style/EditTextAppTheme</item>
<item name="android:checkboxStyle">#style/CheckBoxAppTheme</item>
<item name="android:radioButtonStyle">#style/RadioButtonAppTheme</item>
<item name="android:buttonStyle">#style/ButtonAppTheme</item>
<item name="android:imageButtonStyle">#style/ImageButtonAppTheme</item>
<item name="android:spinnerStyle">#style/SpinnerAppTheme</item>
<item name="android:dropDownSpinnerStyle">#style/SpinnerAppTheme.DropDown</item>
<item name="android:spinnerDropDownItemStyle">#style/SpinnerDropDownItemAppTheme</item>
</style>
And then set this theme to your Application or your Activity in the Manifest with:
android:theme="#style/Theme.myStyle"
or programmatically:
setTheme(R.style.Theme.myStyle);