android自定義支持橫豎方向切換seekbar控件

android自定義支持橫豎方向切換seekbar控件

先上運行效果截圖
這是運行的樣式

下面貼上java代碼

public class RodSeekBar extends SeekBar implements SeekBar.OnSeekBarChangeListener {
   
   
    private final String TAG="RodSeekBar";
    private final String VERTICAL = "vertical";
    private final String HORIZONTAL = "horizontal";
    private final String TOP = "top";
    private final String BOTTOM = "bottom";
    private String direction = HORIZONTAL;
    private String verticalDirection = BOTTOM;
    private int progressDisabledColor;
    private int progressForeColor;
    private int progressBackColor;
    private int thumbEnableColor;
    private int thumbDisableColor;
    private OnSeekBarChangeListener mOnSeekBarChangeListener;

    public RodSeekBar(Context context) {
   
   
        super(context);
    }

    public RodSeekBar(Context context, AttributeSet attrs) {
   
   
        super(context, attrs);
        initData(attrs);
    }

    public RodSeekBar(Context context, AttributeSet attrs, int defStyle) {
   
   
        super(context, attrs, defStyle);
        initData(attrs);
    }

    private void initData( AttributeSet attrs) {
   
   
        TypedArray typedArray = getContext().obtainStyledAttributes(attrs, R.styleable.RodSeekBar);
        if (typedArray != null) {
   
   
            progressDisabledColor = typedArray.getColor(R.styleable.RodSeekBar_progress_disable_color, Color.parseColor("#ffffff"));
            progressBackColor = typedArray.getColor(R.styleable.RodSeekBar_progress_background_color, Color.parseColor("#232939"));
            thumbEnableColor = typedArray.getColor(R.styleable.RodSeekBar_thumb_enable_color, Color.parseColor("#ffffff"));
            thumbDisableColor = typedArray.getColor(R.styleable.RodSeekBar_thumb_disable_color, Color.parseColor("#ffffff"));
            verticalDirection = typedArray.getString(R.styleable.RodSeekBar_rod_progress_vertical_direction);
            direction = typedArray.getString(R.styleable.RodSeekBar_rod_progress_direction);
            progressForeColor = typedArray.getColor(R.styleable.RodSeekBar_progress_enable_color, Color.parseColor("#00aa00"));
            if (!VERTICAL.equals(direction) && !HORIZONTAL.equals(direction)) {
   
   
                direction = HORIZONTAL;
            }
            if (!TOP.equals(verticalDirection) && !BOTTOM.equals(verticalDirection)) {
   
   
                verticalDirection = BOTTOM;
            }
            typedArray.recycle();
        }
        Logger.d(TAG,""+direction);
        setProgressDrawable(null);
        setThumb(drawThumb(isEnabled()));
        setThumbOffset(0);
        setPadding(0, getPaddingTop(), 0, getBottom());
        setSplitTrack(false);
        super.setOnSeekBarChangeListener(this);
    }

    /**
     * thumb的drawable
     *
     * @param isEnable
     * @return
     */
    private Drawable drawThumb(final boolean isEnable) {
   
   
        //畫thumb
        return new Drawable() {
   
   
            @Override
            public void draw(Canvas canvas) {
   
   
                int height = RodSeekBar.this.getHeight();
                int width = RodSeekBar.this.getWidth();
                int max = RodSeekBar.this.getMax();
                int progress = RodSeekBar.this.getProgress();

                Paint paint = new Paint();
                //是否可用顏色
                if (isEnable) {
   
   
                    paint.setColor(thumbEnableColor);
                } else {
   
   
                    paint.setColor(thumbDisableColor);
                }
                paint.setAntiAlias(true);
                //根據方向繪製
                if (HORIZONTAL.equals(direction)) {
   
   
                    float radius = (float) (height / 2.0);
                    float offset = (float) ((width - height) * 1.0 / max);
                    float x = progress * offset + radius;
                    canvas.drawCircle(x, radius, radius, paint);
                } else {
   
   
                    float radius = (float) (width / 2.0);
                    float offset = (float) ((height - width) * 1.0 / max);
                    float y = progress * offset + radius;
                    //根據垂直方向繪製,從上開始、從下開始
                    if (TOP.equals(verticalDirection)) {
   
   
                        canvas.drawCircle(y, -radius, radius, paint);
                    } else {
   
   
                        canvas.drawCircle(height - y, -radius, radius, paint);
                    }
                }
            }

            @Override
            public void setAlpha(int alpha) {
   
   

            }

            @Override
            public void setColorFilter(ColorFilter colorFilter) {
   
   

            }

            @Override
            public int getOpacity() {
   
   
                return PixelFormat.UNKNOWN;
            }
        };
    }

    @SuppressLint("DrawAllocation")
    @Override
    protected void onDraw(Canvas canvas) {
   
   
        int width = getWidth();
        int height = getHeight();
        int max = getMax();
        int progress = getProgress();

        Paint paint = new Paint();
        paint.setColor(progressBackColor);
        paint.setAntiAlias(true);
        RectF rect = new RectF(0, 0, width, height);
        //根據方向繪製
        if (HORIZONTAL.equals(direction)) {
   
   
            //畫背景色
            canvas.drawRoundRect(rect, height, height, paint);
            //畫前景色
            if (isEnabled()) {
   
   
                paint.setColor(progressForeColor);
            } else {
   
   
                paint.setColor(progressDisabledColor);
            }
            float offset = (float) ((width - height) * 1.0 / max * progress + height);
            rect = new RectF(0, 0, offset, height);
            canvas.drawRoundRect(rect, height, height, paint);
        } else {
   
   
            //畫背景色
            canvas.drawRoundRect(rect, width, width, paint);
            //畫前景色
            if (isEnabled()) {
   
   
                paint.setColor(progressForeColor);
            } else {
   
   
                paint.setColor(progressDisabledColor);
            }
            float offset = (float) ((height - width) * 1.0 / max * progress + width);
            //根據垂直方向繪製,從上開始、從下開始
            if (TOP.equals(verticalDirection)) {
   
   
                rect = new RectF(0, 0 , width, offset);
            } else {
   
   
                rect = new RectF(0, height, width, height - offset);
            }
            canvas.drawRoundRect(rect, width, width, paint);
            canvas.rotate(90);
        }

        super.onDraw(canvas);
    }

    @SuppressLint("ClickableViewAccessibility")
    @Override
    public boolean onTouchEvent(MotionEvent event) {
   
   
        if (!isEnabled()) {
   
   
            return false;
        }
        if (VERTICAL.equals(direction)) {
   
   
            switch (event.getAction()) {
   
   
                case MotionEvent.ACTION_DOWN:
                case MotionEvent.ACTION_MOVE:
                case MotionEvent.ACTION_UP:
                    //根據垂直方向響應,從上開始、從下開始
                    if (TOP.equals(verticalDirection)) {
   
   
                        setProgress((int) (getMax() * event.getY() / getHeight()));
                    } else {
   
   
                        setProgress((int) ((int) getMax() - (getMax() * event.getY() / getHeight())));
                    }
                    break;
                default:
                    return super.onTouchEvent(event);
            }
        } else {
   
   
            return super.onTouchEvent(event);
        }
        return true;
    }

    @Override
    protected void onAttachedToWindow() {
   
   
        super.onAttachedToWindow();
    }

    @Override
    protected void onDetachedFromWindow() {
   
   
        super.onDetachedFromWindow();
    }


    @Override
    public void setEnabled(boolean enable) {
   
   
        super.setEnabled(enable);
        setThumb(drawThumb(enable));
        invalidate();
    }

    @Override
    public void setOnSeekBarChangeListener(OnSeekBarChangeListener l) {
   
   
        mOnSeekBarChangeListener = l;
    }

    @Override
    public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
   
   
        if (mOnSeekBarChangeListener != null) {
   
   
            mOnSeekBarChangeListener.onProgressChanged(seekBar, progress, fromUser);
        }
    }

    @Override
    public void onStartTrackingTouch(SeekBar seekBar) {
   
   
        if (mOnSeekBarChangeListener != null) {
   
   
            mOnSeekBarChangeListener.onStartTrackingTouch(seekBar);
        }
    }

    @Override
    public void onStopTrackingTouch(SeekBar seekBar) {
   
   
        if (mOnSeekBarChangeListener != null) {
   
   
            mOnSeekBarChangeListener.onStopTrackingTouch(seekBar);
        }
    }

    public int getProgressDisabledColor() {
   
   
        return progressDisabledColor;
    }

    public void setProgressDisabledColor(int progressDisabledColor) {
   
   
        this.progressDisabledColor = progressDisabledColor;
        invalidate();
    }

    public int getProgressForeColor() {
   
   
        return progressForeColor;
    }

    public void setProgressForeColor(int progressForeColor) {
   
   
        this.progressForeColor = progressForeColor;
        invalidate();
    }

    public int getProgressBackColor() {
   
   
        return progressBackColor;
    }

    public void setProgressBackColor(int progressBackColor) {
   
   
        this.progressBackColor = progressBackColor;
        invalidate();
    }

    public int getThumbEnableColor() {
   
   
        return thumbEnableColor;
    }

    public void setThumbEnableColor(int thumbEnableColor) {
   
   
        this.thumbEnableColor = thumbEnableColor;
        invalidate();
    }

    public int getThumbDisableColor() {
   
   
        return thumbDisableColor;
    }

    public void setThumbDisableColor(int thumbDisableColor) {
   
   
        this.thumbDisableColor = thumbDisableColor;
        invalidate();
    }
}

然後是attrs.xml文件內容

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <declare-styleable name="RodSeekBar">
        <attr name="progress_enable_color" format="color" />
        <attr name="progress_disable_color" format="color" />
        <attr name="progress_background_color" format="color"/>
        <attr name="thumb_enable_color" format="color" />
        <attr name="thumb_disable_color" format="color" />
        <attr name="rod_progress_direction" format="string"/>
        <attr name="rod_progress_vertical_direction" format="string"/>
    </declare-styleable>

</resources>

使用方法
app:rod_progress_direction=“horizontal” 橫向
app:rod_progress_direction=“vertical” 豎向
app:rod_progress_vertical_direction="top"豎向時thumb開始的方向top、bottom
app:progress_enable_color 進度條可用顏色
app:progress_disable_color 進度條不可用顏色
app:progress_background_color 背景色
app:thumb_enable_color 小圓點可用顏色
app:thumb_disable_color 小圓點不可用顏色







發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章