Android 通过图片进行自定义View绘制
2016-06-30 18:50
537 查看
通过Android自定义图表:ChartView和自定义View实现渲染
我们已经了解了如何简单的去绘制一个自定义View-图表和在如何去对一个自定义View中起部分内容进行渲染。
这次我们来了解一下,在自定义View的过程中如何通过图片来绘制一个View。
首先还是先看效果图
这个View其实是2张图片组成的,其中一张是背景图,一张是指针,现在我们传给这个View一个0-10的值,让这个指针指向我们给的这个值,需要注意的是,背景图给的刻度是不规则的。
相信看了前面2篇的朋友在看这个代码,已经没多大压力了,这里多出了一个知识点是Matrix(),由于网上的内容已经讲解的很好了,这里就不重复了,推荐一个链接Android Matrix理论与应用详解,配合上面的注释,你可以下载源码体验一般,使用Bitmap进行View绘制,有时候会很省事。
我们已经了解了如何简单的去绘制一个自定义View-图表和在如何去对一个自定义View中起部分内容进行渲染。
这次我们来了解一下,在自定义View的过程中如何通过图片来绘制一个View。
首先还是先看效果图
Images:
这个View其实是2张图片组成的,其中一张是背景图,一张是指针,现在我们传给这个View一个0-10的值,让这个指针指向我们给的这个值,需要注意的是,背景图给的刻度是不规则的。
那么如何实现这个效果呢,看,直接上代码:
View Code:
** * Created by JackWaiting on 2016/6/30. */ public class RuleCircleView extends View { private float mLeftPadding,mRightPadding,mTopPadding,mBottomPadding; //上下左右边距 private float mRectFWidth,mRectFHeight; //控件高与宽 private float mRadius; //半径 private Bitmap mNum6VBitmap,mNumPointer; private Rect mSrcRect,mDstRect; private Matrix mPointMatrix; private float mNum6VData = 0; //数据 private float mDegrees = 0; //指针角度 private float mScale = 0.7f; //缩放比例 private float mFirstPoint = 0, mSecondPoint = 5.97f, mThirdPoint = 6.18f, mFourthPoint = 6.43f, mFifthPoint = 6.94f, mSixthPoint = 7.45f, mMaxPoint = 10; //每个区间的关键点 private int mFristMaxDegrees = 270,mSecondMaxDegrees = 300,mThirdMaxDegrees = 330,mFourthMaxDegrees = 30,mFifthMaxDegrees = 90,mSixthMaxDegrees = 135; //每个区间点的最大角度 private float mFristDegrees = 45,mSecondDegrees= 30,mThirdDegrees = 30,mFourthDegrees = 60,mFifthDegrees = 60,mSixthDegrees = 45; //每个区间的角度范围 public RuleCircleView(Context context) { super(context); init(); } public RuleCircleView(Context context, AttributeSet attrs) { super(context, attrs); init(); } public RuleCircleView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); init(); } //初始化 private void init() { mLeftPadding = PixelUtil.dp2px(10, getContext()); mTopPadding = PixelUtil.dp2px(10, getContext()); mRightPadding = PixelUtil.dp2px(10, getContext()); mBottomPadding = PixelUtil.dp2px(10, getContext()); mRadius = PixelUtil.dp2px(150, getContext()); mNum6VBitmap= BitmapFactory.decodeResource(getResources(), R.mipmap.img_num_6v); mNumPointer = BitmapFactory.decodeResource(getResources(), R.mipmap.img_num_pointer); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); drawBitMapBackGround(canvas); drawBitMapPointer(canvas); } //描绘指针 private void drawBitMapPointer(Canvas canvas) { canvas.drawBitmap(mNumPointer, mPointMatrix, null); } //拿到界面传给我们的值 public void getNum6VData(float data) { this.mNum6VData = data; } //描绘背景图 private void drawBitMapBackGround(Canvas canvas) { canvas.drawBitmap(mNum6VBitmap, mSrcRect,mDstRect, null); } //把用户给的值换算成角度 private float getDegrees(float mNum6VData) { if(mNum6VData>=mFirstPoint &&mNum6VData<=mSecondPoint){ return mFristMaxDegrees - ((mSecondPoint-mNum6VData)/mSecondPoint)*mFristDegrees; } else if(mNum6VData>mSecondPoint &&mNum6VData<=mThirdPoint){ return mSecondMaxDegrees - ((mThirdPoint-mNum6VData)/(mThirdPoint-mSecondPoint))*mSecondDegrees; } else if(mNum6VData>mThirdPoint &&mNum6VData<=mFourthPoint){ return mThirdMaxDegrees - ((mFourthPoint-mNum6VData)/(mFourthPoint-mThirdPoint))*mThirdDegrees; } else if(mNum6VData>mFourthPoint &&mNum6VData<=mFifthPoint){ float flagNum = mFourthMaxDegrees - ((mFifthPoint-mNum6VData)/(mFifthPoint-mFourthPoint))*mFourthDegrees; //如果是负数,换算成对应的正数 if(flagNum<0){ flagNum = 360+flagNum; } return flagNum; } else if(mNum6VData>mFifthPoint &&mNum6VData<=mSixthPoint){ return mFifthMaxDegrees - ((mSixthPoint-mNum6VData)/(mSixthPoint-mFifthPoint))*mFifthDegrees; } else if(mNum6VData>mSixthPoint &&mNum6VData<=mMaxPoint){ return mSixthMaxDegrees - ((mMaxPoint-mNum6VData)/(mMaxPoint-mSixthPoint))*mSixthDegrees; } return 0; } @Override protected void onSizeChanged(int w, int h, int oldw, int oldh) { super.onSizeChanged(w, h, oldw, oldh); mRectFWidth = w - mLeftPadding - mRightPadding; mRectFHeight = h - mTopPadding - mBottomPadding; mSrcRect = new Rect(0, 0,mNum6VBitmap.getWidth(), mNum6VBitmap.getHeight());// BitMap源区域 mDstRect = new Rect((int)(mRectFWidth/2-mRadius),(int) (mRectFHeight/2-mRadius),(int)(mRectFWidth/2+mRadius), (int)(mRectFHeight/2+mRadius));// BitMap目标区域 mPointMatrix = new Matrix(); mDegrees= getDegrees(mNum6VData); mPointMatrix.postRotate(mDegrees, mNumPointer.getWidth()/2,mNumPointer.getHeight()*12/13); mPointMatrix.postScale(mScale,mScale); mPointMatrix.postTranslate(mRectFWidth/2-mNumPointer.getWidth()/2*mScale,getHeight()/2 - mNumPointer.getHeight()*mScale); } }
相信看了前面2篇的朋友在看这个代码,已经没多大压力了,这里多出了一个知识点是Matrix(),由于网上的内容已经讲解的很好了,这里就不重复了,推荐一个链接Android Matrix理论与应用详解,配合上面的注释,你可以下载源码体验一般,使用Bitmap进行View绘制,有时候会很省事。
以下是代码下载地址:
Github下载地址:https://github.com/JackWaiting/ChartView相关文章推荐
- 自定义View,解决百分比布局适配时Textview的字体Textsize比例缩放问题
- Android 复习1 mvc设计模式
- Android 拍照以及一些常用的处理,例如将图片显示到相册(包含了安卓系统6.0以上调用相机的处理)
- Android 动态隐藏显示导航栏,状态栏
- Android获取手机的型号等
- android 5.0之后如何获取当前运行的应用包名
- Android APP代码混淆proguard和加固
- android studio运行编译速度慢的解决方法
- android 腾讯微博
- 使用DialogFragment实现底部弹窗布局
- 关于Android Studio项目的Gradle构建
- 【分享】兼容ie6-9和现代浏览器以及ios,android,pad等触屏设备的异步文件上传插件
- 基础总结篇之一:Activity生命周期
- Android 上自定义的复式折线图(三)
- 使用Socket处理跨进程的实时聊天
- Android开发之RecyclerView的使用全解
- 如何高效的学习Android动画
- android studio log打不全,主要是json太多
- Android中ListView分页加载数据
- Android Marshmallow实现文字选中