注册页面 android 仿摩拜单车共享单车进度条实现StepView

效果图

Step1:定义StepBean

定义五个状态,分别为:为完成、正在进行、已完成、终点完成、终点未完成。

复制代码
public class StepBean{
public static final int STEP_UNDO = -1;//未完成
public static final int STEP_CURRENT = 0;//正在进行
public static final int STEP_COMPLETED = 1;//已完成
public static final int STEP_LAST_COMPLETED = 2;//终点完成
public static final int STEP_LAST_UNCOMPLETED = 3;//终点未完成
private String name;
private int state;

public String getName(){
    return name;
}

public void setName(String name){
    this.name = name;
}

public int getState(){
    return state;
}

public void setState(int state){
    this.state = state;
}

public StepBean(){
}

public StepBean(String name, int state){
    this.name = name;
    this.state = state;
}

}
复制代码
Step2:自定义HorizontalStepsViewIndicator

复制代码
public class HorizontalStepsViewIndicator extends View {
private int defaultStepIndicatorNum = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 40, getResources().getDisplayMetrics());//定义默认的高度
private float mCompletedLineHeight;//完成线的高度
private float mCircleRadius;//圆的半径

private Drawable mCompleteIcon;//完成的默认图片
private Drawable mAttentionIcon;//正在进行的默认图片
private Drawable mDefaultIcon;//默认的背景图
private Drawable mLastCompleteIcon;//终点未完成图片
private Drawable mLastUnCompleteIcon;//终点完成图片

private float mCenterY;//该view的Y轴中间位置
private float mLeftY;//左上方的Y位置
private float mRightY;//右下方的位置

private List<StepBean> mStepBeanList ;//当前有几步流程
private int mStepNum = 0;
private float mLinePadding;//两条连线之间的间距

private List<Float> mCircleCenterPointPositionList;//定义所有圆的圆心点位置的集合
private Paint mUnCompletedPaint;//未完成Paint
private Paint mCompletedPaint;//完成paint
private int mUnCompletedLineColor = ContextCompat.getColor(getContext(), R.color.uncompleted_color);//定义默认未完成线的颜色
private int mCompletedLineColor = ContextCompat.getColor(getContext(), R.color.completed_color);//定义默认完成线的颜色
private PathEffect mEffects;
private int mComplectingPosition;//正在进行position

private Path mPath;
private OnDrawIndicatorListener mOnDrawListener;
private int screenWidth;

/**
 * 设置监听
 * @param onDrawListener
 */
public void setOnDrawListener(OnDrawIndicatorListener onDrawListener){
    mOnDrawListener = onDrawListener;
}

/**
 * get圆的半径  get circle radius
 * @return
 */
public float getCircleRadius(){
    return mCircleRadius;
}

public HorizontalStepsViewIndicator(Context context){
    this(context, null);
}

public HorizontalStepsViewIndicator(Context context, AttributeSet attrs){
    this(context, attrs, 0);
}

public HorizontalStepsViewIndicator(Context context, AttributeSet attrs, int defStyle){
    super(context, attrs, defStyle);
    init();
}

private void init(){
    mStepBeanList = new ArrayList<>();
    mPath = new Path();
    mEffects = new DashPathEffect(new float[]{8, 8, 8, 8}, 1);
    mCircleCenterPointPositionList = new ArrayList<>();//初始化

    mUnCompletedPaint = new Paint();
    mCompletedPaint = new Paint();
    mUnCompletedPaint.setAntiAlias(true);
    mUnCompletedPaint.setColor(mUnCompletedLineColor);
    mUnCompletedPaint.setStyle(Paint.Style.STROKE);
    mUnCompletedPaint.setStrokeWidth(2);
    mCompletedPaint.setAntiAlias(true);
    mCompletedPaint.setColor(mCompletedLineColor);
    mCompletedPaint.setStyle(Paint.Style.STROKE);
    mCompletedPaint.setStrokeWidth(2);
    mUnCompletedPaint.setPathEffect(mEffects);
    mCompletedPaint.setStyle(Paint.Style.FILL);

    mCompletedLineHeight = 0.03f * defaultStepIndicatorNum;//已经完成线的宽高
    mCircleRadius = 0.28f * defaultStepIndicatorNum;//圆的半径
    mLinePadding = 1.0f * defaultStepIndicatorNum;//线与线之间的间距

    mCompleteIcon = ContextCompat.getDrawable(getContext(), R.drawable.complted);//已经完成的icon
    mAttentionIcon = ContextCompat.getDrawable(getContext(), R.drawable.attention);//正在进行的icon
    mDefaultIcon = ContextCompat.getDrawable(getContext(), R.drawable.default_icon);//未完成的icon
    mLastCompleteIcon= ContextCompat.getDrawable(getContext(), R.drawable.last_complted);//终点已完成的icon
    mLastUnCompleteIcon= ContextCompat.getDrawable(getContext(), R.drawable.last_uncomplted);//终点未完成的icon
}

@Override
protected synchronized void onMeasure(int widthMeasureSpec, int heightMeasureSpec){
    int width = defaultStepIndicatorNum * 2;
    if(MeasureSpec.UNSPECIFIED != MeasureSpec.getMode(widthMeasureSpec)){
        screenWidth = MeasureSpec.getSize(widthMeasureSpec);
    }
    int height = defaultStepIndicatorNum;
    if(MeasureSpec.UNSPECIFIED != MeasureSpec.getMode(heightMeasureSpec)){
        height = Math.min(height, MeasureSpec.getSize(heightMeasureSpec));
    }
    width = (int) (mStepNum * mCircleRadius * 2 - (mStepNum - 1) * mLinePadding);
    setMeasuredDimension(width, height);
}

@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh){
    super.onSizeChanged(w, h, oldw, oldh);
    //获取中间的高度,目的是为了让该view绘制的线和圆在该view垂直居中
    mCenterY = 0.5f * getHeight();
    //获取左上方Y的位置,获取该点的意义是为了方便画矩形左上的Y位置
    mLeftY = mCenterY - (mCompletedLineHeight / 2);
    //获取右下方Y的位置,获取该点的意义是为了方便画矩形右下的Y位置
    mRightY = mCenterY + mCompletedLineHeight / 2;

    mCircleCenterPointPositionList.clear();
    for(int i = 0; i < mStepNum; i++){
        //先计算全部最左边的padding值(getWidth()-(圆形直径+两圆之间距离)*2)
        float paddingLeft = (screenWidth - mStepNum * mCircleRadius * 2 - (mStepNum - 1) * mLinePadding) / 2;
        //add to list
        mCircleCenterPointPositionList.add(paddingLeft + mCircleRadius + i * mCircleRadius * 2 + i * mLinePadding);
    }

    /**
     * set listener
     */
    if(mOnDrawListener!=null){
        mOnDrawListener.ondrawIndicator();
    }
}

@Override
protected synchronized void onDraw(Canvas canvas){
    super.onDraw(canvas);
    if(mOnDrawListener!=null){
        mOnDrawListener.ondrawIndicator();
    }
    mUnCompletedPaint.setColor(mUnCompletedLineColor);
    mCompletedPaint.setColor(mCompletedLineColor);
    //-----------------------画线-------draw line-----------------------------------------------
    for(int i = 0; i < mCircleCenterPointPositionList.size() -1; i++){
        //前一个ComplectedXPosition
        final float preComplectedXPosition = mCircleCenterPointPositionList.get(i);
        //后一个ComplectedXPosition
        final float afterComplectedXPosition = mCircleCenterPointPositionList.get(i + 1);
        if(i <= mComplectingPosition&&mStepBeanList.get(0).getState()!=StepBean.STEP_UNDO){//判断在完成之前的所有点
            //判断在完成之前的所有点,画完成的线,这里是矩形,很细的矩形,类似线,为了做区分,好看些
            canvas.drawRect(preComplectedXPosition + mCircleRadius - 10, mLeftY, afterComplectedXPosition - mCircleRadius + 10, mRightY, mCompletedPaint);
        } else{
            mPath.moveTo(preComplectedXPosition + mCircleRadius, mCenterY);
            mPath.lineTo(afterComplectedXPosition - mCircleRadius, mCenterY);
            canvas.drawPath(mPath, mUnCompletedPaint);
        }
    }
    //-----------------------画线-------draw line-----------------------------------------------

    //-----------------------画图标-----draw icon-----------------------------------------------
    for(int i = 0; i < mCircleCenterPointPositionList.size(); i++){
        final float currentComplectedXPosition = mCircleCenterPointPositionList.get(i);
        Rect rect = new Rect((int) (currentComplectedXPosition - mCircleRadius), (int) (mCenterY - mCircleRadius), (int) (currentComplectedXPosition + mCircleRadius), (int) (mCenterY + mCircleRadius));
        StepBean stepsBean = mStepBeanList.get(i);
        if(stepsBean.getState()==StepBean.STEP_UNDO){
            mDefaultIcon.setBounds(rect);
            mDefaultIcon.draw(canvas);
        }else if(stepsBean.getState()==StepBean.STEP_CURRENT){
            mCompletedPaint.setColor(Color.WHITE);
            canvas.drawCircle(currentComplectedXPosition, mCenterY, mCircleRadius * 1.1f, mCompletedPaint);
            mAttentionIcon.setBounds(rect);
            mAttentionIcon.draw(canvas);
        }else if(stepsBean.getState()==StepBean.STEP_COMPLETED){
            mCompleteIcon.setBounds(rect);
            mCompleteIcon.draw(canvas);
        }else if(stepsBean.getState()==StepBean.STEP_LAST_COMPLETED){
            mLastCompleteIcon.setBounds(rect);
            mLastCompleteIcon.draw(canvas);
        }else if(stepsBean.getState()==StepBean.STEP_LAST_UNCOMPLETED){
            mLastUnCompleteIcon.setBounds(rect);
            mLastUnCompleteIcon.draw(canvas);
        }
    }
    //-----------------------画图标-----draw icon-----------------------------------------------
}

/**
 * 得到所有圆点所在的位置
 * @return
 */
public List<Float> getCircleCenterPointPositionList()
{
    return mCircleCenterPointPositionList;
}

/**
 * 设置流程步数
 * @param stepsBeanList 流程步数
 */
public void setStepNum(List<StepBean> stepsBeanList) {
    this.mStepBeanList = stepsBeanList;
    mStepNum = mStepBeanList.size();

    if(mStepBeanList!=null&&mStepBeanList.size()>0){
        for(int i = 0;i<mStepNum;i++){
            StepBean stepsBean = mStepBeanList.get(i);
                if(stepsBean.getState()==StepBean.STEP_COMPLETED){
                    mComplectingPosition = i;
                }
        }
    }
    requestLayout();
}

/**
 * 设置未完成线的颜色
 * @param unCompletedLineColor
 */
public void setUnCompletedLineColor(int unCompletedLineColor){
    this.mUnCompletedLineColor = unCompletedLineColor;
}

/**
 * 设置已完成线的颜色
 * @param completedLineColor
 */
public void setCompletedLineColor(int completedLineColor){
    this.mCompletedLineColor = completedLineColor;
}

/**
 * 设置默认图片
 * @param defaultIcon
 */
public void setDefaultIcon(Drawable defaultIcon){
    this.mDefaultIcon = defaultIcon;
}

/**
 * 设置已完成图片
 * @param completeIcon
 */
public void setCompleteIcon(Drawable completeIcon){
    this.mCompleteIcon = completeIcon;
}

public void setLastCompleteIcon(Drawable lastcompleteIcon){
    this.mLastCompleteIcon = lastcompleteIcon;
}

public void setLastUnCompleteIcon(Drawable lastUnCompleteIcon){
    this.mLastUnCompleteIcon = lastUnCompleteIcon;
}

/**
 * 设置正在进行中的图片
 * @param attentionIcon
 */
public void setAttentionIcon(Drawable attentionIcon){
    this.mAttentionIcon = attentionIcon;
}

/**
 * 设置对view监听
 */
public interface OnDrawIndicatorListener{
    void ondrawIndicator();
}

}
复制代码
Step3:自定义HorizontalStepView

复制代码
public class HorizontalStepView extends LinearLayout implements HorizontalStepsViewIndicator.OnDrawIndicatorListener{
private RelativeLayout mTextContainer;
private HorizontalStepsViewIndicator mStepsViewIndicator;
private List mStepBeanList;
private int mComplectingPosition;
private int mUnComplectedTextColor = ContextCompat.getColor(getContext(), R.color.uncompleted_text_color);//定义默认未完成文字的颜色;
private int mComplectedTextColor = ContextCompat.getColor(getContext(), R.color.completed_color);//定义默认完成文字的颜色;
private int mTextSize = 14;//default textSize
private TextView mTextView;

public HorizontalStepView(Context context){
    this(context, null);
}

public HorizontalStepView(Context context, AttributeSet attrs){
    this(context, attrs, 0);
}

public HorizontalStepView(Context context, AttributeSet attrs, int defStyleAttr){
    super(context, attrs, defStyleAttr);
    init();
}

private void init(){
    View rootView = LayoutInflater.from(getContext()).inflate(R.layout.widget_horizontal_stepsview, this);
    mStepsViewIndicator = (HorizontalStepsViewIndicator) rootView.findViewById(R.id.steps_indicator);
    mStepsViewIndicator.setOnDrawListener(this);
    mTextContainer = (RelativeLayout) rootView.findViewById(R.id.rl_text_container);
}

/**
 * 设置显示的文字
 * @param stepsBeanList
 * @return
 */
public HorizontalStepView setStepViewTexts(List<StepBean> stepsBeanList) {
    mStepBeanList = stepsBeanList;
    mStepsViewIndicator.setStepNum(mStepBeanList);
    return this;
}


/**
 * 设置未完成文字的颜色
 * @param unComplectedTextColor
 * @return
 */
public HorizontalStepView setStepViewUnComplectedTextColor(int unComplectedTextColor) {
    mUnComplectedTextColor = unComplectedTextColor;
    return this;
}

/**
 * 设置完成文字的颜色
 * @param complectedTextColor
 * @return
 */
public HorizontalStepView setStepViewComplectedTextColor(int complectedTextColor) {
    this.mComplectedTextColor = complectedTextColor;
    return this;
}

/**
 * 设置StepsViewIndicator未完成线的颜色
 * @param unCompletedLineColor
 * @return
 */
public HorizontalStepView setStepsViewIndicatorUnCompletedLineColor(int unCompletedLineColor) {
    mStepsViewIndicator.setUnCompletedLineColor(unCompletedLineColor);
    return this;
}

/**
 * 设置StepsViewIndicator完成线的颜色
 * @param completedLineColor
 * @return
 */
public HorizontalStepView setStepsViewIndicatorCompletedLineColor(int completedLineColor) {
    mStepsViewIndicator.setCompletedLineColor(completedLineColor);
    return this;
}

/**
 * 设置StepsViewIndicator默认图片
 * @param defaultIcon
 */
public HorizontalStepView setStepsViewIndicatorDefaultIcon(Drawable defaultIcon) {
    mStepsViewIndicator.setDefaultIcon(defaultIcon);
    return this;
}

/**
 * 设置StepsViewIndicator已完成图片
 * @param completeIcon
 */
public HorizontalStepView setStepsViewIndicatorCompleteIcon(Drawable completeIcon) {
    mStepsViewIndicator.setCompleteIcon(completeIcon);
    return this;
}

/**
 * 设置StepsViewIndicator正在进行中的图片
 * @param attentionIcon
 */
public HorizontalStepView setStepsViewIndicatorAttentionIcon(Drawable attentionIcon) {
    mStepsViewIndicator.setAttentionIcon(attentionIcon);
    return this;
}

public HorizontalStepView setStepsViewIndicatorLastCompleteIcon(Drawable lastCompleteIcon) {
    mStepsViewIndicator.setLastCompleteIcon(lastCompleteIcon);
    return this;
}

public HorizontalStepView setStepsViewIndicatorLastUnCompleteIcon(Drawable lastUnCompleteIcon) {
    mStepsViewIndicator.setLastUnCompleteIcon(lastUnCompleteIcon);
    return this;
}

/**
 * set textSize
 * @param textSize
 * @return
 */
public HorizontalStepView setTextSize(int textSize) {
    if(textSize > 0) {
        mTextSize = textSize;
    }
    return this;
}

@Override
public void ondrawIndicator() {
    if(mTextContainer != null) {
        mTextContainer.removeAllViews();
        List<Float> complectedXPosition = mStepsViewIndicator.getCircleCenterPointPositionList();
        if(mStepBeanList != null && complectedXPosition != null && complectedXPosition.size() > 0) {
            for(int i = 0; i < mStepBeanList.size(); i++) {
                mTextView = new TextView(getContext());
                mTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, mTextSize);
                mTextView.setText(mStepBeanList.get(i).getName());
                int spec = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);
                mTextView.measure(spec, spec);
                // getMeasuredWidth
                int measuredWidth = mTextView.getMeasuredWidth();
                mTextView.setX(complectedXPosition.get(i) - measuredWidth / 2);
                mTextView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));

                if(i <= mComplectingPosition) {
                    mTextView.setTypeface(null);
                    mTextView.setTextColor(mComplectedTextColor);
                } else{
                    mTextView.setTextColor(mUnComplectedTextColor);
                }
                mTextContainer.addView(mTextView);
            }
        }
    }
}

}
复制代码
Step4:如何使用?

在布局文件xml中:

复制代码
<cn.comnav.utrain.ui.widget.HorizontalStepView
android:id="@+id/hsv_step_view"
android:layout_width="match_parent"
android:layout_height="80dp"
android:layout_below="@+id/ll_role"
android:layout_marginBottom="40dp"
/>
复制代码
在Activity中的使用,部分代码截取:

复制代码
private List stepsBeanList;
private HorizontalStepView mHorizontalStepView;
mHorizontalStepView=(HorizontalStepView)findViewById(R.id.hsv_step_view);

              stepsBeanList = new ArrayList<>();
                    StepBean stepBean0=null;
                    StepBean stepBean1=null;
                    StepBean stepBean2=null;
                    StepBean stepBean3=null;
                    switch (stepIndex){
                        case 1:
                            stepBean0 = new StepBean("手机绑定",1);
                            stepBean1 = new StepBean("实名认证",0);
                            stepBean2 = new StepBean("学时充值",-1);
                            stepBean3 = new StepBean("开始用车",3);
                            break;
                        case 2:
                            stepBean0 = new StepBean("手机绑定",1);
                            stepBean1 = new StepBean("实名认证",1);
                            stepBean2 = new StepBean("学时充值",0);
                            stepBean3 = new StepBean("开始用车",3);
                            break;
                        case 3:
                            stepBean0 = new StepBean("手机绑定",1);
                            stepBean1 = new StepBean("实名认证",1);
                            stepBean2 = new StepBean("学时充值",1);
                            stepBean3 = new StepBean("开始用车",2);
                            break;
                    }
                    stepsBeanList.add(stepBean0);
                    stepsBeanList.add(stepBean1);
                    stepsBeanList.add(stepBean2);
                    stepsBeanList.add(stepBean3);
                mHorizontalStepView.setStepViewTexts(stepsBeanList);
posted on 2017-06-12 16:50  魅影王小冶  阅读(156)  评论(0编辑  收藏  举报