自定义 RatingBar 着色 API < 21 支持库 22.1.1
Custom RatingBar tinting API < 21 with support library 22.1.1
我正在使用支持库 22.1.1。我的目标是为自定义 RatingBar 着色,以避免在我的 APK 中包含多张图片。
着色在 API 22 上正确应用,但在 API 19 上未正确应用。我希望它在 API >= 16 上工作。请注意,我尝试仅对 "progress" 着色,而不是对整个条着色。
这是 RatingBar 样式:
<style name="customRatingBar" parent="Widget.AppCompat.RatingBar">
<item name="android:progressDrawable">@drawable/custom_ratingbar</item>
<item name="android:minHeight">24dp</item>
<item name="android:maxHeight">24dp</item>
<item name="android:progressTint">@color/md_red_700</item>
<item name="android:secondaryProgressTint">@color/md_red_700</item>
</style>
和 custom_ratingbar.xml
文件:
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@android:id/background"
android:drawable="@drawable/ic_heart_outline_grey600_24dp" />
<item android:id="@android:id/progress"
android:drawable="@drawable/ic_heart_grey600_24dp" />
</layer-list>
它在我的布局中以这种方式应用,它在一个片段中扩展 android.support.v4.Fragment
本身在 activity 扩展 android.support.v7.app.AppCompatActivity
:
中
<RatingBar
android:layout_width="wrap_content"
android:layout_height="22dp"
android:id="@+id/checkin_rating"
style="@style/customRatingBar"
android:isIndicator="true"
android:numStars="5"
android:stepSize="1"
android:layout_marginBottom="8dp"/>
我从 lint 工具收到一条警告,说 API < 21 不支持 android:progressTint
。有什么方法可以在不使用多个可绘制对象的情况下实现这一点?
在支持库 > 22 的情况下,我设法使用 getProgressDrawable
做到了这一点
LayerDrawable stars = (LayerDrawable) bar.getProgressDrawable();
stars.getDrawable(0).setColorFilter(NONE_COLOR, PorterDuff.Mode.SRC_ATOP);
stars.getDrawable(1).setColorFilter(FULL_COLOR, PorterDuff.Mode.SRC_ATOP);
stars.getDrawable(2).setColorFilter(PARTIAL_COLOR, PorterDuff.Mode.SRC_ATOP);
这在支持库 22 之前不起作用,所以我认为这会解决您的问题。
我不想一定要编辑 Gary 已被接受的答案(如果我能的话),但我发现 FULL/PARTIAL/NONE 的顺序对我来说不正确。这就是我实现它的方式,它适用于 API 18+.
将星标(我的 AppCompatRatingBar 的子类)设置为黄色和灰色以表示未填充的星标:
int yellow = ContextCompat.getColor(getContext(), R.color.starbar_star_yellow);
int gray = ContextCompat.getColor(getContext(), R.color.starbar_star_gray);
Drawable starbarDrawable = this.getProgressDrawable();
DrawableCompat.setTint(starbarDrawable, yellow); // this works for API 21+
// this ensures it works for API 18-20
if(starbarDrawable instanceof LayerDrawable) {
LayerDrawable stars = (LayerDrawable) starbarDrawable;
stars.getDrawable(0).setColorFilter(gray, PorterDuff.Mode.SRC_ATOP); // UNFILLED
stars.getDrawable(1).setColorFilter(yellow, PorterDuff.Mode.SRC_ATOP); // PARTIAL OR FULL?
stars.getDrawable(2).setColorFilter(yellow, PorterDuff.Mode.SRC_ATOP); // PARTIAL OR FULL?
}
我正在使用支持库 22.1.1。我的目标是为自定义 RatingBar 着色,以避免在我的 APK 中包含多张图片。
着色在 API 22 上正确应用,但在 API 19 上未正确应用。我希望它在 API >= 16 上工作。请注意,我尝试仅对 "progress" 着色,而不是对整个条着色。
这是 RatingBar 样式:
<style name="customRatingBar" parent="Widget.AppCompat.RatingBar">
<item name="android:progressDrawable">@drawable/custom_ratingbar</item>
<item name="android:minHeight">24dp</item>
<item name="android:maxHeight">24dp</item>
<item name="android:progressTint">@color/md_red_700</item>
<item name="android:secondaryProgressTint">@color/md_red_700</item>
</style>
和 custom_ratingbar.xml
文件:
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:id="@android:id/background"
android:drawable="@drawable/ic_heart_outline_grey600_24dp" />
<item android:id="@android:id/progress"
android:drawable="@drawable/ic_heart_grey600_24dp" />
</layer-list>
它在我的布局中以这种方式应用,它在一个片段中扩展 android.support.v4.Fragment
本身在 activity 扩展 android.support.v7.app.AppCompatActivity
:
<RatingBar
android:layout_width="wrap_content"
android:layout_height="22dp"
android:id="@+id/checkin_rating"
style="@style/customRatingBar"
android:isIndicator="true"
android:numStars="5"
android:stepSize="1"
android:layout_marginBottom="8dp"/>
我从 lint 工具收到一条警告,说 API < 21 不支持 android:progressTint
。有什么方法可以在不使用多个可绘制对象的情况下实现这一点?
在支持库 > 22 的情况下,我设法使用 getProgressDrawable
LayerDrawable stars = (LayerDrawable) bar.getProgressDrawable();
stars.getDrawable(0).setColorFilter(NONE_COLOR, PorterDuff.Mode.SRC_ATOP);
stars.getDrawable(1).setColorFilter(FULL_COLOR, PorterDuff.Mode.SRC_ATOP);
stars.getDrawable(2).setColorFilter(PARTIAL_COLOR, PorterDuff.Mode.SRC_ATOP);
这在支持库 22 之前不起作用,所以我认为这会解决您的问题。
我不想一定要编辑 Gary 已被接受的答案(如果我能的话),但我发现 FULL/PARTIAL/NONE 的顺序对我来说不正确。这就是我实现它的方式,它适用于 API 18+.
将星标(我的 AppCompatRatingBar 的子类)设置为黄色和灰色以表示未填充的星标:
int yellow = ContextCompat.getColor(getContext(), R.color.starbar_star_yellow);
int gray = ContextCompat.getColor(getContext(), R.color.starbar_star_gray);
Drawable starbarDrawable = this.getProgressDrawable();
DrawableCompat.setTint(starbarDrawable, yellow); // this works for API 21+
// this ensures it works for API 18-20
if(starbarDrawable instanceof LayerDrawable) {
LayerDrawable stars = (LayerDrawable) starbarDrawable;
stars.getDrawable(0).setColorFilter(gray, PorterDuff.Mode.SRC_ATOP); // UNFILLED
stars.getDrawable(1).setColorFilter(yellow, PorterDuff.Mode.SRC_ATOP); // PARTIAL OR FULL?
stars.getDrawable(2).setColorFilter(yellow, PorterDuff.Mode.SRC_ATOP); // PARTIAL OR FULL?
}