Android SeekBar上方带文字提示

一、前言:

SeekBar控件在开发中还是比较常见的,比如音视频进度、音量调节等,但是原生控件有时还不能满足我们的需求,今天就来学习一下如何自定义SeekBar控件,本文主要实现了一个带文字指示器效果的SeekBar控件,看下最终效果:

图片.png

二、实现

1、TextThumbSeekBar
@SuppressLint("AppCompatCustomView")
public class TextThumbSeekBar extends SeekBar {

    // 画笔
    private Paint mPaint;
    // 进度文字位置信息
    private Rect mProgressTextRect = new Rect();
    // 滑块按钮宽度
    private int mThumbWidth = dp2px(50);

    private int mSeekBarMin;
    public TextThumbSeekBar(Context context) {
        this(context, null);
    }

    public TextThumbSeekBar(Context context, AttributeSet attrs) {
        this(context, attrs, android.R.attr.seekBarStyle);
        initData();
    }

    private void initData() {
        mPaint = new TextPaint();
        mPaint.setAntiAlias(true);
        mPaint.setColor(BaseApplication.getInstance().getResources().getColor(R.color.color_FFFFFF));
        mPaint.setTextSize(sp2px(16));

        // 如果不设置padding,当滑动到最左边或最右边时,滑块会显示不全
        setPadding(mThumbWidth / 2, 0, mThumbWidth / 2, 0);
    }

    public TextThumbSeekBar(Context context,AttributeSet attrs,int defStyleAttr){
        super(context,attrs,defStyleAttr);
        initData();
    }

    @Override
    protected synchronized void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        // 进度文字位置信息
        String progressText = "+"+getProgress();
        mPaint.getTextBounds(progressText, 0, progressText.length(), mProgressTextRect);

        // 进度百分比
        float progressRatio = (float) getProgress() / getMax();
        // thumb偏移量
        float thumbOffset = (mThumbWidth - mProgressTextRect.width()) / 2 - mThumbWidth * progressRatio;
        float thumbX = getWidth() * progressRatio + thumbOffset;
        //这里修改文字的范围,上或下
        float thumbY = getHeight() / 2f - mProgressTextRect.height() / 2f-dp2px(8);
        canvas.drawText(progressText, thumbX, thumbY, mPaint);
    }

    public void setMix(int min){
        mSeekBarMin=min;
    }

    /**
     * dp转px
     *
     * @param dp dp值
     * @return px值
     */
    public int dp2px(float dp) {
        return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp,
                getResources().getDisplayMetrics());
    }

    /**
     * sp转px
     *
     * @param sp sp值
     * @return px值
     */
    private int sp2px(float sp) {
        return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, sp,
                getResources().getDisplayMetrics());
    }
}

2、布局

  <RelativeLayout
        android:id="@+id/rl_adjust"
        android:layout_width="match_parent"
        android:layout_height="@dimen/dp_65">

        <com.sumansoul.slim.tea.ui.view.TextThumbSeekBar
            android:id="@+id/seek_progress"
            android:layout_width="match_parent"
            android:layout_height="@dimen/dp_60"
            android:max="100"
            android:maxHeight="@dimen/dp_5"
            android:progressDrawable="@drawable/seek_bar_white_bg"
            android:thumb="@drawable/c_seekbar"
            android:progress="50"
            android:splitTrack="false"
            android:layout_marginRight="@dimen/dp_12"
            android:layout_marginLeft="@dimen/dp_12"
            android:layout_centerVertical="true"
            />
    </RelativeLayout>

3、背景seek_bar_white_bg

seek_bar_white_bg.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" >
        <shape>
            <solid android:color="#66ffffff"/>
            <corners android:radius="@dimen/dp_3" />
        </shape>
    </item>

    <!--progressBar部分(放下面) -->
    <item android:id="@android:id/progress" >
        <clip>
            <shape>
                <solid android:color="@color/color_FF876DAE" />
                <corners android:radius="@dimen/dp_3" />
            </shape>
        </clip>
    </item>
</layer-list>

4、c_seekbar

就是滑动的图片

5、seekBar使用:

(1)监听
SeekBar可以监听进度条拖拽的状态,代码如下:

 seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
        @Override
        public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
        }

        @Override
        public void onStartTrackingTouch(SeekBar seekBar) {
        }

        @Override
        public void onStopTrackingTouch(SeekBar seekBar) {
        }
    });

1、当拖拽开始时,执行onStartTrackingTouch方法,且只会执行一次;
2、当拖拽结束时,执行onStopTrackingTouch方法,且只会执行一次;
3、当正在拖拽时,执行onProgressChanged方法,进度每次变化都会执行onProgressChanged方法,参数progress表示当前进度。

三、解析

1、最重要的

    @Override
    protected synchronized void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        // 进度文字位置信息
        String progressText = "+"+getProgress();
        mPaint.getTextBounds(progressText, 0, progressText.length(), mProgressTextRect);

        // 进度百分比
        float progressRatio = (float) getProgress() / getMax();
        // thumb偏移量
        float thumbOffset = (mThumbWidth - mProgressTextRect.width()) / 2 - mThumbWidth * progressRatio;
        float thumbX = getWidth() * progressRatio + thumbOffset;
        //文字在seekBar上方,跟随seekBar滑动
        //float thumbY = getHeight() / 2f - mProgressTextRect.height() / 2f-dp2px(8);
        //文字在seekBar正中间,跟随seekBar滑动
        float thumbY = getHeight() / 2f + mProgressTextRect.height() / 2f;
        canvas.drawText(progressText, thumbX, thumbY, mPaint);
    }

**注意: TextThumbSeekBar必须在xml指定高度,不然可能会不显示。

android:layout_height="@dimen/dp_60"

2、自定义SeekBar thumb透明效果

修改前:


图片.png

修改后:


图片.png
<!-- 是否设置一个间隙,让滑块与底部图片分隔 -->
android:splitTrack="false"

参考://www.greatytc.com/p/b753c4a9ddfa

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。