Android Getting Started tutorial | SeekBar custom thumb

brief introduction

On the interface of some music or video playback, when resources are still loaded, the origin (thumb) of the progress bar will display a circle effect. After the resource is loaded, it switches back to the static effect. This effect enhances the user experience.

Generally speaking, there are art personnel responsible for design and cutting. When trying to implement it, we can use drawable to simulate the effect of realizing this turn.

Example

dimens.xml

For easy management, you can add some size settings

<dimen name="audio_course_item_seek_bar_progress_height">6dp</dimen>
<dimen name="audio_course_item_seek_bar_radius">2dp</dimen>
<dimen name="audio_seek_bar_thumb_size">20dp</dimen>
<dimen name="audio_seek_bar_thumb_ring_width">4dp</dimen>
drawable

We need to add four drawable files altogether. There are two kinds of thumb, one animation and one progress bar "base".

shape_thumb_round_1.xml # Static thumb
layers_seek_bar_progress_1.xml
layers_thumb_ring_sweep_1.xml
rotate_thumb_1.xml

shape_thumb_round_1.xml

Ring effect made with solid and stroke

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="oval">
    <solid android:color="#ffffff" />
    <stroke
        android:width="@dimen/audio_seek_bar_thumb_ring_width"
        android:color="#7095fc" />
    <size
        android:width="@dimen/audio_seek_bar_thumb_size"
        android:height="@dimen/audio_seek_bar_thumb_size" />
</shape>

layers_thumb_ring_sweep_1.xml

This is the thumb you're going to use to turn around. Use layer list to overlay multiple layers. At the bottom is a half white circle (android:shape="oval"). Add a layer of ring (android:shape="ring") and use gradient color to increase dynamic.

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item>
        <shape android:shape="oval">
            <size
                android:width="@dimen/audio_seek_bar_thumb_size"
                android:height="@dimen/audio_seek_bar_thumb_size" />
            <solid android:color="#ffffff" />
        </shape>
    </item>
    <item>
        <shape
            android:innerRadius="4dp"
            android:thicknessRatio="6"
            android:shape="ring"
            android:useLevel="false">
            <gradient
                android:endColor="#ffffff"
                android:startColor="#7095fc"
                android:type="sweep" />
            <size
                android:width="@dimen/audio_seek_bar_thumb_size"
                android:height="@dimen/audio_seek_bar_thumb_size" />
        </shape>
    </item>
</layer-list>

rotate_thumb_1.xml

Defines the rotation effect. Note that its drawable uses the layers defined above_ thumb_ ring_ sweep_ 1.xml.

<?xml version="1.0" encoding="utf-8"?>
<rotate xmlns:android="http://schemas.android.com/apk/res/android"
    android:drawable="@drawable/layers_thumb_ring_sweep_1"
    android:duration="100"
    android:fromDegrees="0"
    android:pivotX="50%"
    android:pivotY="50%"
    android:toDegrees="-360" />

The rotation parameter android:toDegrees can be defined according to requirements.

layers_seek_bar_progress_1.xml

Defines the style of the progress bar. This is the "base". The color should match the one above. It looks better.

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:id="@android:id/background">
        <shape>
            <size
                android:width="5dp"
                android:height="@dimen/audio_course_item_seek_bar_progress_height" />
            <solid android:color="#e1e5e8" />
        </shape>
    </item>
    <item android:id="@android:id/secondaryProgress">
        <clip>
            <shape>
                <solid android:color="#b7bdc8" />
            </shape>
        </clip>
    </item>
    <item android:id="@android:id/progress">
        <clip>
            <shape>
                <gradient
                    android:angle="0"
                    android:centerColor="#b8cafd"
                    android:endColor="#86a4fd"
                    android:startColor="#eef2ff" />
            </shape>
        </clip>
    </item>
</layer-list>

layout

After the above resource file is prepared. Add a SeekBar to our layout

  • android:maxHeight and android:minHeight need to be set
  • android:progressDrawable   Use the previously defined "base"
  • android:thumb   Use static styles first

    <SeekBar
    android:id="@+id/play_sb"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginTop="16dp"
    android:background="@null"
    android:maxHeight="@dimen/audio_course_item_seek_bar_progress_height"
    android:minHeight="@dimen/audio_course_item_seek_bar_progress_height"
    android:progress="40"
    android:progressDrawable="@drawable/layers_seek_bar_progress_1"
    android:thumb="@drawable/shape_thumb_round_1"
    app:layout_constraintTop_toTopOf="parent" />

Call in Activity

Activities hold Drawable variables and animations. dataBinding is used in the example.

private RotateDrawable mRotateThumbDrawable; //  For the loaded thumb, the Activity holds the drawable
private Drawable mSolidThumb;
private ObjectAnimator mThumbAnimator; // Control animation
// ...
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        mBinding = DataBindingUtil.setContentView(this, R.layout.act_seekbar_1);// ...
        mRotateThumbDrawable = (RotateDrawable) AppCompatResources.getDrawable(getApplicationContext(), R.drawable.rotate_thumb_1);
        mSolidThumb = AppCompatResources.getDrawable(getApplicationContext(), R.drawable.shape_thumb_round_1);
    }

The Drawable object is directly held by the activity, which is more convenient to operate.

Change the thumb of seekbar and use the method setThumb(Drawable thumb)

Use static thumb

mBinding.playSb.setThumb(mSolidThumb);

To use the effect of turning circles, first setThumb, and you need to start the animation

mBinding.playSb.setThumb(mRotateThumbDrawable);
mThumbAnimator = ObjectAnimator.ofInt(mRotateThumbDrawable, "level", 0, 10000);
mThumbAnimator.setDuration(1000);
mThumbAnimator.setRepeatCount(ValueAnimator.INFINITE);
mThumbAnimator.setInterpolator(new LinearInterpolator());
mThumbAnimator.start();

You can switch between static and dynamic.

Remember to close the animation when you leave the page

@Override
protected void onDestroy() {
    if (null != mThumbAnimator) {
        mThumbAnimator.cancel();
    }
    super.onDestroy();
}

Summary

To achieve the effect of turning. It is mainly to directly operate drawable objects and add animation.   setThumb(Drawable thumb) method accepts drawable objects, so our idea is to control drawable.

All use of drawable can achieve the effect in this paper. Picture resources can also be used if conditions permit. Make richer effects.

Android zero foundation tutorial video reference

Keywords: Android

Added by Gwayn on Fri, 26 Nov 2021 16:39:28 +0200