Comments (13)
Works great, thanks! If you wish to resolve attr value from Activity theme to style resource, just use this code:
val View.contextThemeWrapper: ContextThemeWrapper
get() = context.contextThemeWrapper
val Context.contextThemeWrapper: ContextThemeWrapper
get() = when (this) {
is ContextThemeWrapper -> this
is ContextWrapper -> baseContext.contextThemeWrapper
else -> throw IllegalStateException("Context is not an Activity, can't get theme: $this")
}
@StyleRes
fun View.attrStyle(@AttrRes attrColor: Int): Int = contextThemeWrapper.attrStyle(attrColor)
@StyleRes
private fun ContextThemeWrapper.attrStyle(@AttrRes attrRes: Int): Int =
attr(attrRes) {
it.getResourceId(0, 0)
}
private fun <R> ContextThemeWrapper.attr(@AttrRes attrRes: Int, block: (TypedArray)->R): R {
val typedValue = TypedValue();
if (!theme.resolveAttribute(attrRes, typedValue, true)) throw IllegalArgumentException("$attrRes is not resolvable")
val a = obtainStyledAttributes(typedValue.data, intArrayOf(attrRes));
val result = block(a)
a.recycle()
return result
}
then,
textView(attrStyle(R.attr.my_title)) {
}
from anko.
Resolving the attr does not actually work in all cases. Example:
button("My Button", theme = attrStyle(R.attr.buttonBarButtonStyle))
will not apply the correct background, since the one-argument constructor of Button
that Anko uses calls through to the three-argument constructor with a default value for int defStyleAttr
which overrides the button background with the default.
While working in some cases, the theme support of Anko 0.9 is not a full replacement for the style
XML attribute. Can we reopen this issue?
from anko.
Nevermind. I created this shim:
public inline fun ViewManager.styledButton(text: CharSequence?, styleRes: Int = 0, init: Button.() -> Unit): Button {
return ankoView({ if (styleRes == 0) Button(it) else Button(ContextThemeWrapper(it, styleRes), null, 0) }) {
init()
setText(text)
}
}
public fun ViewManager.styledButton(text: CharSequence?, styleRes: Int = 0): Button = styledButton(text, styleRes) {}
Works perfectly, I just call styledButton("text", R.style.MyStyle)
. Thanks @sfunke!
from anko.
Is there any way to set style? So now you can set theme for each widget, like AppTheme, AppTheme.Light, but what if you need to set individual styles, eg. Widget.Button, Widget.Button.Colored?
from anko.
Anko has a style()
function, though traditional Android XML styles are unsupported now.
Android SDK does not provide a good way to set View
styles in code out of the box, and we are trying to find a way to support it.
from anko.
Inspired by the default Anko textView
extension methods, and after doing some research on how to set a theme to a view by code, I came up with the following extension methods, which work very well so far (can be applied to any view class):
public inline fun ViewManager.textView(text: CharSequence?, styleRes: Int = 0, init: TextView.() -> Unit): TextView {
return ankoView({ if (styleRes == 0) TextView(it) else TextView(ContextThemeWrapper(it, styleRes), null, 0) }) {
init()
setText(text)
}
}
public fun ViewManager.textView(text: CharSequence?, styleRes: Int = 0): TextView = textView(text, styleRes) {}
Key is, you have to use ContextThemeWrapper, and the 3 argument constructor of the passed view, see this link: http://stackoverflow.com/a/28613069/1128600
That allows to pass an XML style, and have it fully applied to the newly created view (not comparable to the crappy setTextAppearance
method)
@yanex Would it make sense to consider this for potential adoption into the standard library?
from anko.
@sfunke, does this only work for styling the text in a TextView, or is it generalized to applying any style resource to any view (including things like padding, backgrounds, borders, etc.?)
from anko.
@sfunke I think
public inline fun ViewManager.AnyView(theme: Int = 0, init: TextView.() -> Unit): AnyView
is enough.
from anko.
#143
;)
from anko.
@fboldog +1
from anko.
@simophin depends on what version you're targeting. on API 21+, Google added a 4th parameter to all Views constructors allowing you to set the style resource: https://developer.android.com/reference/android/view/View.html#View(android.content.Context,%20android.util.AttributeSet,%20int,%20int)
So if you're only targeting devices running 21+, it's easy to make custom Anko views calling that constructor. If you want to target devices running below 21, you're out of luck. There's no (easy) way to set the style programmatically because it's all private APIs used by the XML layout inflater.
What we ended up doing was to create very small XML layout files containing just <Button style="@style/WhiteButton" />
and then instantiating that layout with Anko's include<Button>(R.layout.white_button)
from anko.
@hannesstruss I've created the new issue for this: #361.
I also mark this issue as "closed". If you have other problems with themed views, please feel free to create the new issues.
from anko.
now you can use horizontalProgressBar { }
so no need to set style horizontal to progressBar
from anko.
Related Issues (20)
- Alerts with no system bar, or: how to get dialog before show() ? HOT 1
- How to use linearLayout in verticalLayout? HOT 1
- hintTextColor can not work in anko? HOT 1
- Error: void org.jetbrains.anko.appcompat.v7._AlertDialogLayout.forceUniformWidth(int, int) is not being kept as e, but remapped to d
- Feature request: share file
- Android Q support
- Maybe Not update anymore for this project? HOT 1
- Maybe Not update anymore for this project? HOT 11
- Is this project discontinued? HOT 5
- Textview cannot accept new line from Resources strings HOT 2
- something issues of anko.include() dsl
- ***** BEWARE -- this project seems to be abandoned. ***** HOT 14
- Fix reference - Listeners not working HOT 1
- about Anko performance HOT 8
- Selector no cancel listener HOT 1
- textView.setMaxWidth() does not work
- Is SDK28 Available In A Repo Somewhere? HOT 1
- Style selector text? HOT 1
- Please archive this repository. HOT 3
- What if I don't want to add the view directly?
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from anko.