Custom Attributes in Styles.Xml

Custom attributes in styles.xml

I figured it out! The answer is to NOT specify the namespace in the style.

<?xml version="1.0" encoding="utf-8" ?>
<resources xmlns:android="http://schemas.android.com/apk/res/android">
<style name="CustomStyle">
<item name="android:layout_width">wrap_content</item>
<item name="android:layout_height">wrap_content</item>

<item name="custom_attr">value</item> <!-- tee hee -->
</style>
</resources>

Using custom attrs in styles.xml in android

Change your XML to:

xmlns:effects="http://schemas.android.com/apk/res/com.base.view.EffectsTextView"

And change your style:

<style name="EffectsHeaderTextStyle">
<item name="strokeWidth">10</item>
</style>

I did something similar with fonts:

https://github.com/androidfu/CodeExamples/tree/master/com.androidfu.CustomFontsDemo

Custom attrs parameter used in styles.xml

The XML namespace mechanism is used to namespace tags and attributes. When you define a style like this:

<?xml version="1.0" encoding="utf-8"?>
<resources
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:custom="http://schemas.android.com/apk/res/com.my.project">

<style name="my_style"> <item name="custom:tag">some_value</item> </style>

</resources>

you are trying to apply XML namespacing to an attribute value, which won't work. In this case, you should specify the package name directly, like this:

    <style name="my_style"> <item name="com.my.project:tag">some_value</item> </style>

Now Android will be able to resolve where the attribute is defined.

Android : Create your own attribute names in styles.xml

How do I define this "customViewStyle" key?

<attr name="customViewStyle" format="reference"/>, outside of any <declare-styleable> tags.

But I haven't found yet how to exploit it.

Make a style that has the properties you want. You have already done that with MyCustomViewStyle entry in your post, but you've given it a parent style that doesn't exist (as far as I can tell). I would probably use `parent="android:Widget" unless something else is more appropriate.

I presume your custom view class already reads attributes from XML using TypedArray:

TypedArray a = context.obstainStyleAttributes(attrs, R.styleable.CustomView,
R.attr.customViewStyle, 0);

Replace the last argument with your default style you just defined:

TypedArray a = context.obstainStyleAttributes(attrs, R.styleable.CustomView,
R.attr.customViewStyle, R.style.MyCustomViewStyle);

Is it possible to reference attributes from styles.xml file?

Yes, it is definitely possible to add custom attributes and colors to the themes. For this you need to:

  1. Define your custom attribute in your res/values/attrs.xml file:

    <resources>
    <attr name="customColor" format="color" />
    </resources>
  2. Define the attribute's value in your themes:

    <style name="AppTheme" parent="Theme.AppCompat">
    <item name="customColor">#111111</item>
    </style>

    <style name="AppTheme.AnotherColor" parent="Theme.AppCompat">
    <item name="customColor">#222222</item>
    </style>
  3. Use your custom attribute in your styles:

    <style name="CustomActionBar">
    <!-- title text color -->
    <item name="android:textColorPrimary">?attr/customColor</item>
    </style>

Define style and custom attribute in View instead of xml

Yep, you can use the default style attribute in the constructor.

Define a new attribute:

<attr name="customButtonStyle" format="reference" />

Then use the appropriate view constructor:

private val defStyleAttr = R.attr.customButtonStyle

class CustomButton(context: Context, attrs: AttributeSet) : MaterialButton(
ThemeEnforcement.createThemedContext(context, attributeSet, defStyleAttr, 0),
attributeSet,
defStyleAttr
) {

init {
val typedArray = context.obtainStyledAttributes(
attrs,
R.styleable.CustomButton,
defStyleAttr,
0
)
...

}

In your theme, point customButtonStyle to the style resource that you want used by default:

<style name="Theme.Demo" parent="Base.Theme.Demo">
<item name="customButtonStyle">@style/Widget.Demo.Button.Primary</item>
</style>

Note that android:theme should be changed to materialThemeOverlay in that style resource, as it won't be applied when read from a default style. As you're already wrapping the context with the ThemeEnforcement function (newer versions of Material Design Components change this to MaterialThemeOverlay), this custom view supports materialThemeOverlay /p>


You can add your custom attributes to the style too:

<style name="Widget.Demo.Button.Primary" parent="@style/Widget.MaterialComponents.Button">
<item name="abc">primary</item>
<item name="fontFamily">@font/roboto</item>
<item name="android:fontFamily">@font/roboto</item>
<item name="android:minHeight">64dp</item>
<item name="materialThemeOverlay">@style/ThemeOverlay.Demo.GrayPrimary</item>
</style>

Reference (blog + video)



Related Topics



Leave a reply



Submit