发现最新的MPAndroidChart和以前版本的使用有一些差距,就写下了现在新版的使用方法
Android图表控件MPAndroidChart的简单介绍(MPAndroidChart3.0)
Android图表控件MPAndroidChart——曲线图LineChart的使用(多条曲线)
Android图表控件MPAndroidChart——曲线图LineChart(多条曲线)动态添加数据
Android图表控件MPAndroidChart——柱状图BarChart的使用(多条柱状图)
Android图表控件MPAndroidChart——曲线图+柱状图 CombinedChart的使用
Android图表控件MPAndroidChart——源码修改实现曲线图X轴直尺刻度样式
本文相关代码
MPAndroidChart在github上的地址:https://github.com/PhilJay/MPAndroidChart
组合图CombinedChart可以将MPAndroidChart支持的所有类别的图表组合在一起,在此只是展示曲线图+柱状图
一.效果图
1.一条柱状图加一条线性图
2.多条柱状图加多条线性图
因为柱状图宽度太小,柱状图值的无法显示,放大即会显示柱状图值
二.实现效果图
主要代码如下
public class CombinedChartManager { private CombinedChart mCombinedChart; private YAxis leftAxis; private YAxis rightAxis; private XAxis xAxis; public CombinedChartManager(CombinedChart combinedChart) { this.mCombinedChart = combinedChart; leftAxis = mCombinedChart.getAxisLeft(); rightAxis = mCombinedChart.getAxisRight(); xAxis = mCombinedChart.getXAxis(); } /** * 初始化Chart */ private void initChart() { //不显示描述内容 mCombinedChart.getDescription().setEnabled(false); mCombinedChart.setDrawOrder(new CombinedChart.DrawOrder[]{ CombinedChart.DrawOrder.BAR, CombinedChart.DrawOrder.LINE }); mCombinedChart.setBackgroundColor(Color.WHITE); mCombinedChart.setDrawGridBackground(false); mCombinedChart.setDrawBarShadow(false); mCombinedChart.setHighlightFullBarEnabled(false); //显示边界 mCombinedChart.setDrawBorders(true); //图例说明 Legend legend = mCombinedChart.getLegend(); legend.setWordWrapEnabled(true); legend.setVerticalAlignment(Legend.LegendVerticalAlignment.BOTTOM); legend.setHorizontalAlignment(Legend.LegendHorizontalAlignment.CENTER); legend.setOrientation(Legend.LegendOrientation.HORIZONTAL); legend.setDrawInside(false); //Y轴设置 rightAxis.setDrawGridLines(false); rightAxis.setAxisMinimum(0f); leftAxis.setDrawGridLines(false); leftAxis.setAxisMinimum(0f); mCombinedChart.animateX(2000); // 立即执行的动画,x轴 } /** * 设置X轴坐标值 * * @param xAxisValues x轴坐标集合 */ public void setXAxis(final ListxAxisValues) { //设置X轴在底部 XAxis xAxis = mCombinedChart.getXAxis(); xAxis.setPosition(XAxis.XAxisPosition.BOTTOM); xAxis.setGranularity(1f); xAxis.setLabelCount(xAxisValues.size() - 1,false); xAxis.setValueFormatter(new IAxisValueFormatter() { @Override public String getFormattedValue(float value, AxisBase axis) { return xAxisValues.get((int) value % xAxisValues.size()); } }); mCombinedChart.invalidate(); } /** * 得到折线图(一条) * * @param lineChartY 折线Y轴值 * @param lineName 折线图名字 * @param lineColor 折线颜色 * @return */ private LineData getLineData(List lineChartY, String lineName, int lineColor) { LineData lineData = new LineData(); ArrayList yValue = new ArrayList<>(); for (int i = 0; i < lineChartY.size(); i++) { yValue.add(new Entry(i, lineChartY.get(i))); } LineDataSet dataSet = new LineDataSet(yValue, lineName); dataSet.setColor(lineColor); dataSet.setCircleColor(lineColor); dataSet.setValueTextColor(lineColor); dataSet.setCircleSize(1); //显示值 dataSet.setDrawValues(true); dataSet.setValueTextSize(10f); dataSet.setMode(LineDataSet.Mode.CUBIC_BEZIER); dataSet.setAxisDependency(YAxis.AxisDependency.LEFT); lineData.addDataSet(dataSet); return lineData; } /** * 得到折线图(多条) * * @param lineChartYs 折线Y轴值 * @param lineNames 折线图名字 * @param lineColors 折线颜色 * @return */ private LineData getLineData(List > lineChartYs, List
lineNames, List lineColors) { LineData lineData = new LineData(); for (int i = 0; i < lineChartYs.size(); i++) { ArrayList yValues = new ArrayList<>(); for (int j = 0; j < lineChartYs.get(i).size(); j++) { yValues.add(new Entry(j, lineChartYs.get(i).get(j))); } LineDataSet dataSet = new LineDataSet(yValues, lineNames.get(i)); dataSet.setColor(lineColors.get(i)); dataSet.setCircleColor(lineColors.get(i)); dataSet.setValueTextColor(lineColors.get(i)); dataSet.setCircleSize(1); dataSet.setDrawValues(true); dataSet.setValueTextSize(10f); dataSet.setMode(LineDataSet.Mode.CUBIC_BEZIER); dataSet.setAxisDependency(YAxis.AxisDependency.LEFT); lineData.addDataSet(dataSet); } return lineData; } /** * 得到柱状图 * * @param barChartY Y轴值 * @param barName 柱状图名字 * @param barColor 柱状图颜色 * @return */ private BarData getBarData(List barChartY, String barName, int barColor) { BarData barData = new BarData(); ArrayList yValues = new ArrayList<>(); for (int i = 0; i < barChartY.size(); i++) { yValues.add(new BarEntry(i, barChartY.get(i))); } BarDataSet barDataSet = new BarDataSet(yValues, barName); barDataSet.setColor(barColor); barDataSet.setValueTextSize(10f); barDataSet.setValueTextColor(barColor); barDataSet.setAxisDependency(YAxis.AxisDependency.LEFT); barData.addDataSet(barDataSet); //以下是为了解决 柱状图 左右两边只显示了一半的问题 根据实际情况 而定 xAxis.setAxisMinimum(-0.5f); xAxis.setAxisMaximum((float) (barChartY.size()- 0.5)); return barData; } /** * 得到柱状图(多条) * * @param barChartYs Y轴值 * @param barNames 柱状图名字 * @param barColors 柱状图颜色 * @return */ private BarData getBarData(List > barChartYs, List
barNames, List barColors) { List lists = new ArrayList<>(); for (int i = 0; i < barChartYs.size(); i++) { ArrayList entries = new ArrayList<>(); for (int j = 0; j < barChartYs.get(i).size(); j++) { entries.add(new BarEntry(j, barChartYs.get(i).get(j))); } BarDataSet barDataSet = new BarDataSet(entries, barNames.get(i)); barDataSet.setColor(barColors.get(i)); barDataSet.setValueTextColor(barColors.get(i)); barDataSet.setValueTextSize(10f); barDataSet.setAxisDependency(YAxis.AxisDependency.LEFT); lists.add(barDataSet); } BarData barData = new BarData(lists); int amount = barChartYs.size(); //需要显示柱状图的类别 数量 float groupSpace = 0.12f; //柱状图组之间的间距 float barSpace = (float) ((1 - 0.12) / amount / 10); // x4 DataSet float barWidth = (float) ((1 - 0.12) / amount / 10 * 9); // x4 DataSet // (0.2 + 0.02) * 4 + 0.12 = 1.00 即100% 按照百分百布局 //柱状图宽度 barData.setBarWidth(barWidth); //(起始点、柱状图组间距、柱状图之间间距) barData.groupBars(0, groupSpace, barSpace); return barData; } /** * 显示混合图(柱状图+折线图) * * @param xAxisValues X轴坐标 * @param barChartY 柱状图Y轴值 * @param lineChartY 折线图Y轴值 * @param barName 柱状图名字 * @param lineName 折线图名字 * @param barColor 柱状图颜色 * @param lineColor 折线图颜色 */ public void showCombinedChart( List xAxisValues, List barChartY, List lineChartY , String barName, String lineName, int barColor, int lineColor) { initChart(); setXAxis(xAxisValues); CombinedData combinedData = new CombinedData(); combinedData.setData(getBarData(barChartY, barName, barColor)); combinedData.setData(getLineData(lineChartY, lineName, lineColor)); mCombinedChart.setData(combinedData); mCombinedChart.invalidate(); } /** * 显示混合图(柱状图+折线图) * * @param xAxisValues X轴坐标 * @param barChartYs 柱状图Y轴值 * @param lineChartYs 折线图Y轴值 * @param barNames 柱状图名字 * @param lineNames 折线图名字 * @param barColors 柱状图颜色 * @param lineColors 折线图颜色 */ public void showCombinedChart( List xAxisValues, List > barChartYs, List
> lineChartYs, List
barNames, List lineNames, List barColors, List lineColors) { initChart(); setXAxis(xAxisValues); CombinedData combinedData = new CombinedData(); combinedData.setData(getBarData(barChartYs, barNames, barColors)); combinedData.setData(getLineData(lineChartYs, lineNames, lineColors)); mCombinedChart.setData(combinedData); mCombinedChart.invalidate(); } }
XML中
xml version="1.0" encoding="utf-8"?>
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
android:id="@+id/chart1"
android:layout_width="match_parent"
android:layout_height="360dp"/>
android:id="@+id/chart2"
android:layout_width="match_parent"
android:layout_height="360dp"/>
Activity中
private CombinedChart mCombinedChart1; private CombinedChart mCombinedChart2; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_combinedchart); mCombinedChart1 = (CombinedChart) findViewById(R.id.chart1); mCombinedChart2 = (CombinedChart) findViewById(R.id.chart2); //x轴数据 ListxData = new ArrayList<>(); for (int i = 0; i <= 20; i++) { xData.add(String.valueOf(i)); } //y轴数据集合 List > yBarDatas = new ArrayList<>(); //4种直方图 for (int i = 0; i < 4; i++) { //y轴数 List
yData = new ArrayList<>(); for (int j = 0; j <= 20; j++) { yData.add((float) (Math.random() * 100)); } yBarDatas.add(yData); } //y轴数据集合 List > yLineDatas = new ArrayList<>(); //4种直方图 for (int i = 0; i < 4; i++) { //y轴数 List
yData = new ArrayList<>(); for (int j = 0; j <= 20; j++) { yData.add((float) (Math.random() * 100)); } yLineDatas.add(yData); } //名字集合 List barNames = new ArrayList<>(); barNames.add("直方图一"); barNames.add("直方图二"); barNames.add("直方图三"); barNames.add("直方图四"); //颜色集合 List colors = new ArrayList<>(); colors.add(Color.BLUE); colors.add(Color.RED); colors.add(Color.YELLOW); colors.add(Color.CYAN); //竖状图管理类 List lineNames = new ArrayList<>(); lineNames.add("折线图一"); lineNames.add("折线图二"); lineNames.add("折线图三"); lineNames.add("折线图四"); //管理类 CombinedChartManager combineChartManager1 = new CombinedChartManager(mCombinedChart1); combineChartManager1.showCombinedChart(xData, yBarDatas.get(0), yLineDatas.get(0), "直方图", "线性图", colors.get(0), colors.get(1)); CombinedChartManager combineChartManager2 = new CombinedChartManager(mCombinedChart2); combineChartManager2.showCombinedChart(xData, yBarDatas, yLineDatas, barNames, lineNames, colors, colors); }
三.使用中遇见的问题
1.和柱状图的显示一样,左右两边的柱状图显示只显示了一半
因为柱状图是从 X轴值中间开始显示的,为了显示左右两边的完整柱状图 设置X轴多显示0.5即可
//以下是为了解决 柱状图 左右两边只显示了一半的问题 根据实际情况 而定 xAxis.setAxisMinimum(-0.5f); xAxis.setAxisMaximum((float) (barChartY.size()- 0.5));
2.在显示多条柱状图时,并没有显示想要的内容,而是每个x轴刻度就一个柱状图,而不是一个X轴刻度显示多条柱状
解决问题
在getBarData()方法中 根据需要显示的柱状图条数,设置对应的宽度,间距,组间距
int amount = barChartYs.size(); //需要显示柱状图的类别 数量 float groupSpace = 0.12f; //柱状图组之间的间距 float barSpace = (float) ((1 - 0.12) / amount / 10); // x4 DataSet float barWidth = (float) ((1 - 0.12) / amount / 10 * 9); // x4 DataSet // (0.2 + 0.02) * 4 + 0.12 = 1.00 即100% 按照百分百布局 //柱状图宽度 barData.setBarWidth(barWidth); //(起始点、柱状图组间距、柱状图之间间距) barData.groupBars(0, groupSpace, barSpace);