如何以编程方式将 selectableItemBackground 添​​加到 ImageButton?

Posted

技术标签:

【中文标题】如何以编程方式将 selectableItemBackground 添​​加到 ImageButton?【英文标题】:How do I add selectableItemBackground to an ImageButton programmatically? 【发布时间】:2013-12-30 03:45:39 【问题描述】:

android.R.attr.selectableItemBackground 存在,但如何以编程方式将其添加到 ImageButton?

另外,我将如何在文档中找到答案?提到了here,但我没有看到任何关于它实际使用方式的解释。实际上,我似乎很少发现文档有用,但我希望这是我的错,而不是文档的错。

【问题讨论】:

可能重复:***.com/questions/9398610/… 请注意我的问题是一个两部分的问题,第二个问题没有在另一个线程中解决。 【参考方案1】:

这里是一个使用答案的例子:How to get the attr reference in code?

    // Create an array of the attributes we want to resolve
    // using values from a theme
    // android.R.attr.selectableItemBackground requires API LEVEL 11
    int[] attrs = new int[]  android.R.attr.selectableItemBackground /* index 0 */;

    // Obtain the styled attributes. 'themedContext' is a context with a
    // theme, typically the current Activity (i.e. 'this')
    TypedArray ta = obtainStyledAttributes(attrs);

    // Now get the value of the 'listItemBackground' attribute that was
    // set in the theme used in 'themedContext'. The parameter is the index
    // of the attribute in the 'attrs' array. The returned Drawable
    // is what you are after
    Drawable drawableFromTheme = ta.getDrawable(0 /* index */);

    // Finally free resources used by TypedArray
    ta.recycle();

    // setBackground(Drawable) requires API LEVEL 16, 
    // otherwise you have to use deprecated setBackgroundDrawable(Drawable) method. 
    imageButton.setBackground(drawableFromTheme);
    // imageButton.setBackgroundDrawable(drawableFromTheme);

【讨论】:

这不起作用,至少在带有 AppCompat 的 Lollipop 上。但是,this did. 代码在 Lollipop 和 AppCompat 上运行良好(2017 年 5 月) - 唯一的区别是我使用 View.setForeground(Drawable) 而不是 setBackground()【参考方案2】:

如果您使用的是 AppCompat,您可以使用以下代码:

int[] attrs = new int[]R.attr.selectableItemBackground;
TypedArray typedArray = context.obtainStyledAttributes(attrs);
int backgroundResource = typedArray.getResourceId(0, 0);
view.setBackgroundResource(backgroundResource);
typedArray.recycle();

【讨论】:

@Renges 你应该设置标志setClickable(true)setFocusable(true) setFocusable(true) 在这里是不必要的,实际上是多余的,只要项目可以进入“焦点项目”的状态并获得灰色背景。即使没有设置此属性,涟漪效果也会起作用 Focusable 是为了可访问性,它应该在可点击的项目上 前景怎么样?没有像 setForegroundResource 那样的方法【参考方案3】:

这适用于我的TextView

// Get selectable background
TypedValue typedValue = new TypedValue();
getTheme().resolveAttribute(R.attr.selectableItemBackground, typedValue, true);

clickableTextView.setClickable(true);
clickableTextView.setBackgroundResource(typedValue.resourceId);

因为我使用 AppCompat 库,所以我使用 R.attr.selectableItemBackground 而不是 android.R.attr.selectableItemBackground

我认为typedValue.resourceId 包含来自selectableItemBackground 的所有drawable,而不是使用TypeArray#getResourceId(index, defValue)TypeArray#getDrawable(index),它们只检索给定index 的drawable。

【讨论】:

【参考方案4】:

试试这个方法:

public Drawable getDrawableFromAttrRes(int attrRes, Context context) 
    TypedArray a = context.obtainStyledAttributes(new int[] attrRes);
    try 
        return a.getDrawable(0);
     finally 
        a.recycle();
    

// 那么就这样称呼它:

getDrawableFromAttrRes(R.attr.selectableItemBackground, context)

// Example
ViewCompat.setBackground(view,getDrawableFromAttrRes(R.attr.selectableItemBackground, context))

【讨论】:

有时Android Studio会警告使用R.attr.selectableItemBackground,所以用android.R.attr.selectableItemBackground替换它可能更安全

以上是关于如何以编程方式将 selectableItemBackground 添​​加到 ImageButton?的主要内容,如果未能解决你的问题,请参考以下文章

如何以编程方式将活动主题化为对话?

如何以编程方式将元素添加到 ConfigurationElementCollection?

如何在 Swift 中以编程方式将 UILabel 对象居中?

如何以编程方式将 UIImageView 添加到 UIStackView(故事板)

如何以编程方式将 Google Sheet 脚本发布/部署为 API 可执行文件?

如何以编程方式将图像裁剪成碎片