前段时间公司要做图表,本来想用个三方库就完事的,然而有很多个性化的实现,那就自己动手吧。先上图
实现的效果感觉还行,再有什么特殊的需求,自己写的东西,改起来也方便。

接下来是把图表功能涉及到的类都先抽象出来。

ChartData包下是绘图时要用到的数据。
Xvalues:X轴下每个点要绘制的东西,如上面柱状图中绘制的月份数据
Yvalues:每个X轴坐标对应的Y轴数据点。
XaxisData: X坐标轴
YaxisData: Y坐标轴
ChartDataManager: 绘制图表可能需要以上数据的配合,所以,还要把上面的数据放到一个地方进行统一管理,这个类里包含了以上上面的所有数据。

ChartDrawUtil包下是每一中图的绘制工具
DrawUtil是绘制图表的基类和一些公用方法。绘制图表,我把它分割成了三个步骤
1.绘制X轴 ——-》2.绘制Y轴————-》3.绘制图表内容。
所以在基类里写了三个抽象方法

    abstract protected void startContent(Canvas canvas);abstract protected void drawXaxis(Canvas canvas);abstract protected void drawYaxis(Canvas canvas);

相应的子类实现对应的绘制就行了。

除了上面两个包里的类,剩下的就是实现好的图表类。

接下来就来看看图表的实现,上图中第一个,最简单的圆形进度控件CircleProgressChart

思路也很简单,先绘制一个底部的灰色圆环,再绘制上层的进度圆环,最后绘制中心文字。

@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);canvas.drawCircle(centerX,centerY,circirRudias,bottomCirclePaint);//底部圆环绘制float currentDegree=360*currentPercent;//通过进度百分比计算对应的弧度float left=centerX-circirRudias;float top=centerY-circirRudias;float right=centerX+circirRudias;float bottom=centerY+circirRudias;RectF rectF=new RectF(left,top,right,bottom);canvas.drawArc(rectF,-90,currentDegree,false,topCirclePaint);//绘制对应的进度弧度int percentText= (int) (currentPercent*100);String drawtext=percentText+"%";Paint.FontMetrics metrics=textPaint.getFontMetrics();float textwidth= textPaint.measureText(drawtext);float textX=(getMeasuredWidth()-textwidth)/2;               //文字X坐标点计算float textY=centerY-(metrics.ascent+metrics.descent)/2;     //文字Y坐标点计算canvas.drawText(drawtext,textX,textY,textPaint);}

这个实在太简单了,还没用上上面设计的数据结构,不过接下来的图表会用到。

第二个图是含有多个种类的圆环图

这个图的实现也是很简单,显然,它要有一个各个种类的数据集合,我是用Yvalues来表示一个种类。

public class MultiTypeCircleProgressChart extends View {private int centerX,centerY;private int circirRudias;Paint textPaint,bottomCirclePaint,topCirclePaint;int bottomCircleColor=Color.GRAY,topCirlceColor= Color.RED,textColor=Color.BLACK;float currentPercent=0.50f;float circleWidth=20;float textSize=30;List<Yvalues> allTypeValues;//图包含的种类集合List<Integer> allTypeDegree;//不同种类的对应的弧度集合public MultiTypeCircleProgressChart(Context context) {super(context);init(context);}public MultiTypeCircleProgressChart(Context context, @Nullable AttributeSet attrs) {super(context, attrs);init(context);}public MultiTypeCircleProgressChart(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);init(context);}private void init(Context context){textPaint=new Paint();textPaint.setAntiAlias(true);textPaint.setDither(true);textPaint.setColor(textColor);textPaint.setTextSize(textSize);bottomCirclePaint=new Paint();bottomCirclePaint.setAntiAlias(true);bottomCirclePaint.setDither(true);bottomCirclePaint.setColor(bottomCircleColor);bottomCirclePaint.setStrokeWidth(circleWidth);bottomCirclePaint.setStyle(Paint.Style.STROKE);topCirclePaint=new Paint();topCirclePaint.setAntiAlias(true);topCirclePaint.setDither(true);topCirclePaint.setColor(topCirlceColor);topCirclePaint.setStrokeWidth(circleWidth);topCirclePaint.setStyle(Paint.Style.STROKE);allTypeDegree=new ArrayList<>();allTypeValues=new ArrayList<>();}//这个方法是计算不同种类对应的弧度private   List<Integer> getRelativeDegree(List<Yvalues> yvaluesList){List<Integer> relativeDegree=new ArrayList<>();int size=yvaluesList.size();int totalValues=0;for(int i=0;i<size;i++){totalValues+=yvaluesList.get(i).getValue();}for(int i=0;i<size;i++){int degree= (int) (360*yvaluesList.get(i).getValue()*1.0f/totalValues);relativeDegree.add(degree);}return relativeDegree;}public void updateView(List<Yvalues> yvaluesList){this.allTypeValues=yvaluesList;this.allTypeDegree=getRelativeDegree(yvaluesList);invalidate();}@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {super.onMeasure(widthMeasureSpec, heightMeasureSpec);centerX=getMeasuredWidth()/2;centerY=getMeasuredHeight()/2;circirRudias=Math.min(centerX,centerY)-30;}@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);int startDegree=-90;//圆环绘制的起点从12点钟方向开始canvas.drawCircle(centerX,centerY,circirRudias,bottomCirclePaint);float left=centerX-circirRudias;float top=centerY-circirRudias;float right=centerX+circirRudias;float bottom=centerY+circirRudias;RectF rectF=new RectF(left,top,right,bottom);int size=allTypeValues.size();for(int i=0;i<size;i++){topCirclePaint.setColor(allTypeValues.get(i).getTextcolor());canvas.drawArc(rectF,startDegree,allTypeDegree.get(i),false,topCirclePaint);startDegree+=allTypeDegree.get(i);}}
}

小知识点提示:
1.绘制底部圆的时候,设置画笔描边属性: bottomCirclePaint.setStyle(Paint.Style.STROKE);
2.绘制弧度首尾两头半圆装的属性:topCirclePaint.setStrokeCap(Paint.Cap.ROUND);
3.绘制弧度起点设为0的话,起点对应的是3点钟方向,我这里写成-90是对应的就是12点方向。
4.让文字居中的坐标点计算原理参考 http://blog.csdn.net/doctorzhong/article/details/53079511。

android 图表控件的实现(一)相关推荐

  1. Android图表控件MPAndroidChart——曲线图LineChart的使用(财富收益图)

    目录 前言 本文涉及文章 其他相关文章 1.数据准备 1.1 数据来源 2.曲线展示 2.1 MPAndroidChart获取 2.2 数据对象获取 2.3 数据展示 3.曲线完善 3.1 图表背景. ...

  2. Android图表控件MPAndroidChart——BarChart实现多列柱状图以及堆积柱状图

    目录 前言 1. 数据准备 1.1 数据来源 2. 图表展示 2.1 MPAndroidChart获取 2.2 数据对象获取 2.3 数据展示 3. 柱状图外观完善 3.1 去掉图表外框,描述内容以及 ...

  3. Android图表控件MPAndroidChart的使用

    转载一篇Android图表控件MPAndroidChart的博客. 相关文章: Android图表控件MPAndroidChart的简单介绍(MPAndroidChart3.0) Android图表控 ...

  4. Android图表控件MPAndroidChart——LineChart实现 XY轴、原点线的直尺刻度样式

    接上文: Android图表控件MPAndroidChart--曲线图LineChart的使用(多条曲线) 其他相关文章: Android图表控件MPAndroidChart的简单介绍(MPAndro ...

  5. Android图表控件MPAndroidChart实现左右滑动以及联动

    前言 MPAndroidChart是一个功能强大的Android图表控件库,它实现了许多常见的图表效果.关于MPAndroidChart的使用文章已经很多了,这里不再详细介绍它的使用.当数据量过多时, ...

  6. android好用的曲线图控件,Android图表控件MPAndroidChart——曲线图LineChart的使用(多条曲线)...

    发现最新的MPAndroidChart和以前版本的使用有一些差距,就写下了现在新版的使用方法 相关文章: Android图表控件MPAndroidChart的简单介绍(MPAndroidChart3. ...

  7. android开发原点表框架,Android图表控件MPAndroidChart——LineChart实现 XY轴、原点线的直尺刻度样式...

    接上文: Android图表控件MPAndroidChart--曲线图LineChart的使用(多条曲线) 其他相关文章: Android图表控件MPAndroidChart的简单介绍(MPAndro ...

  8. android图表控件 坐标,android-charts 基于Java和Android开发的图形图表控件 | 李大仁博客...

    王晓龙 April 8th, 2014 at 09:44 | #1 我再github上看到了你写的控件,给了我很大启发,我现在在做K线图一类的图表,正好用到了您开发的这款控件,但是有些地方使用的不太舒 ...

  9. Android图表控件MPChart-柱状+折线组合图表基本使用

    一.效果图 双模式效果:柱形图加折线图,双y轴,从右向左滑动- 二.实现代码 1. 加入依赖 implementation 'com.github.PhilJay:MPAndroidChart:v3. ...

最新文章

  1. 我是如何在2年内逆袭成为BAT年薪40W的资深开发工程师的?
  2. 无敌了,不需要操作系统就能运行 Python 了!
  3. linux 判断网卡类型 有线 无线
  4. 系统进入低功耗的配置
  5. Redis 持久化之RDB和AOF
  6. Spring Bootstrap中带有配置元数据的高级配置
  7. springboot2——MyBatis入门
  8. 【zookeeper】zookeeper 的监听机制
  9. 协议protocol
  10. python创建文件的编码格式
  11. 2021 五一数学建模 赛题思路
  12. 电商ERP软件、订单管理系统、库存管理系统
  13. AI再造一个“李佳琦”,难嘛?
  14. html手机保存图片不显示,手机保存的图片在相册显示不了解决方法
  15. dlopen failed: empty/missing DT_HASH in quot;libx.soquot; (built with --hash-style=gnu?)
  16. 天津达内可靠么 老员工揭秘真实的达内教育
  17. 什么是软件需求?软件需求是什么意思?
  18. 单目视觉定位测距的两种方式
  19. 【学习笔记】群论基础
  20. Android开发者网址大全(不定期更新)

热门文章

  1. 2.4fxblue跟单ea如何实现多跟一,一跟多,或者多跟多
  2. Sublime3 设置Python快捷键
  3. js版微信测试号推送消息、生日、纪念日、网易云热评、舔狗日记【JavaScript版】保姆级教程 青龙面板做微信测试号推送生日、纪念日
  4. 计算机一级ms office应用题,计算机一级MSOffice考试练习题及答案
  5. JUC高并发编程从入门到精通(全)
  6. 计算机组成原理包健百度云,计算机组成原理包健版答案及解析.doc
  7. YII2使用Gii生成代码
  8. java-net-php-python-47ssm志愿者管理系统程序计算机毕业设计程序
  9. 强烈质疑第二届Android应用开发中国大学生挑战赛
  10. 小程序公共封装ajax,微信小程序HTTP请求从0到1封装