Android中怎么通过自定义View实现横行时间轴效果-创新互联
今天就跟大家聊聊有关Android中怎么通过自定义View实现横行时间轴效果,可能很多人都不太了解,为了让大家更加了解,小编给大家总结了以下内容,希望大家根据这篇文章可以有所收获。
专注于为中小企业提供成都网站建设、网站建设服务,电脑端+手机端+微信端的三站合一,更高效的管理,为中小企业淮滨免费做网站提供优质的服务。我们立足成都,凝聚了一批互联网行业人才,有力地推动了1000多家企业的稳健成长,帮助中小企业通过网站建设实现规模扩充和转变。一、已经有很多 RecycleView 实现时间轴的例子,为何还要费劲的使用自定义 view 去实现时间轴?
根据上图可以总结出以下几点:
每个阶段要显示时间、阶段名、状态图标、中间有虚线;文字上下交错显示;相邻阶段的文字在垂直方向上是可以相交的;时间轴的个数不确定,但是要铺满屏幕并且不可滑动; 如果只实现上两点的效果,使用 RecycleView 无疑是好的选择,但是要同时实现以上整个效果目前想到的好的办法就是使用自定义 view。
二、如何开始?
相信也有人跟我一样,对自定义的绘制过程 view、canvas、path、paint 的使用有了解,但是真的要去写自定义 view 确不知道从何开始,不知道第一步如何下手。我个人的总结就是:想要的太多,迟迟不动手,所以有想法一定要去动手试验! 不要想着写完第一次运行就是最终想展示的完美效果,而是要抱着整体拆分成不重复的小块,然后去绘制重复块,然后去一点点实现一步步完美的心态才能做出来。
所以首先要把想实现的 view 拆分成一个个小的可绘制的并且没有重复的块,以目前想实现的时间轴效果来说,最小可绘制无重复块也就是只包括一个时间结点的块如图:
它包括:
垂直居中的一条虚线;一个表示状态的图标;一个显示时间的文本块;一个显示阶段名的文本块;
三、开始画
有了上面的分析,接下来就要开始画了。
1. 画中间的线
首先画虚线,如果虚线不知道怎么画,可以先画一条实线,然后再去找画虚线的方法。
使用 canvas 中画线的方法 drawLine(float startX, float startY, float stopX, float stopY, @NonNull Paint paint)
根据参数得知需知道线的起点与终点坐标以及一个 paint 对象,因为是垂直居中且横穿整个控件的直线所以可以确定两个点的 y 坐标是一样的,也就是控件高的一半,起点的 x 坐标为0,终点的 x 坐标为控件的宽。也就是知道控件的宽和高之后就可以绘制出这条线。获取控件的宽高,可以在 onMeasure 方法中获取:
@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); mViewWidth = MeasureSpec.getSize(widthMeasureSpec) - dip2px(mContext, mSafeDistance * 2); mViewHeight = MeasureSpec.getSize(heightMeasureSpec);}
画线的代码(在 onDraw 方法中添加,下面其它的绘制方法同样是在 onDraw 方法中添加):
// 定义画笔,并设置相关属性Paint mLinePaint = new Paint();mLinePaint.setColor(Color.parseColor("#999999"));mLinePaint.setStrokeWidth(1);mLinePaint.setStyle(Paint.Style.STROKE);// 画虚线canvas.drawLine(0, mViewHeight / 2, mViewWidth, mViewHeight / 2, mLinePaint);
2. 画图标
canvas 画图标的方法:drawBitmap(@NonNull Bitmap bitmap, float left, float top, @Nullable Paint paint),根据方法的参数去分析如何准备值,这里需要一个 bitmap 对象,起点坐标以及 paint。bitmap 对象可以将资源文件 drawable 转为 bitmap 格式;坐标就是控件的中心点。画图标的代码:
// 图标 x,y 坐标Bitmap statusBitmap = BitmapFactory.decodeResource(mContext.getResources(), R.mipmap.ic_no_pass);float bX = mViewWidth / 2;// 垂直的中心点在图标的顶部,所以要减去 bitmap 高的一半float bY = mViewHeight / 2 - statusBitmap.getHeight() / 2f;Paint mBitmapPaint = new Paint();mBitmapPaint.setFilterBitmap(true);canvas.drawBitmap(statusBitmap, bX, bY, mBitmapPaint);
3. 画文本
canvas 画文本的方法:drawText(@NonNull String text, float x, float y, @NonNull Paint paint),依然是根据方法得知需要知道绘制的内容,开始的坐标点以及 paint。当文本在图标上方时,文本的 y 坐标需要使用图标的 y 坐标减去文本到图标的距离,x 坐标同图片的 x 坐标一样;当文本在图标下方时,文本的 y 坐标需要使用图标的 y 坐标加上文本到图标的距离。画文本的代码:
// 定义画笔Paint mDatePaint = new Paint();mDatePaint.setColor(Color.parseColor("#666666"));mDatePaint.setTextSize(dip2px(mContext, 12));mDatePaint.setStyle(Paint.Style.FILL);mDatePaint.setTextAlign(Paint.Align.CENTER);mDatePaint.setAntiAlias(true);Paint mNamePain = new Paint();mNamePain.setColor(Color.parseColor("#666666"));mNamePain.setTextSize(dip2px(mContext, 13));mNamePain.setStyle(Paint.Style.FILL);mNamePain.setTextAlign(Paint.Align.CENTER);mNamePain.setAntiAlias(true);// 定义坐标变量float dateX = bX + statusBitmap.getWidth() / 2f;float dateY;dateY = mViewHeight / 2 - dip2px(mContext, 19);// 画文字,在图标上canvas.drawText("有效时间", dateX, dateY, mNamePain);canvas.drawText("09.27-09.29", dateX, dateY - dateTextHeight mDatePaint);// 画文字,在图标下dateY = mViewHeight / 2 + dip2px(mContext, 19);canvas.drawText("09.27-09.29", dateX, dateY, mDatePaint);canvas.drawText("有效时间", dateX, dateY + dateTextHeigh, mNamePain);
4. 由局部到整体
上面已经完成了只有一个时间点的绘制,接下来思考如果有多个时间点时如何绘制。只有一个时间点时计算坐标是以控件的宽高进行计算,那么当有两个时间点的时候需要首先把控件均分成两部分,然后在均分的部分中计算对应的坐标,完成绘制。当有三个时间点的时候需要均分为三部分,然后在各自的部分计算对应的坐标,完成绘制。所以得到不论时间点的个数有多少绘制的方法不会改变,需要改变的是绘制时候用到的点的坐标。其实已经可以看出,当多个点的时候需要循环一下,代码如下:
// 得到多个点时,其中每个部分的宽,itevW 也就等同与上面只有一个时间点时控件的宽float itemW = mViewWidth / mDataList.size();for (int i = 0; i < mDataList.size(); i++) { // 完成相关计算、绘制}
看完上述内容,你们对Android中怎么通过自定义View实现横行时间轴效果有进一步的了解吗?如果还想了解更多知识或者相关内容,请关注创新互联行业资讯频道,感谢大家的支持。
当前题目:Android中怎么通过自定义View实现横行时间轴效果-创新互联
当前URL:http://scyanting.com/article/dipjei.html