Android项目实战Android开发牛叉的demo

MPAndroidChart项目实战(五)——组合图实现趋势图

2017-07-14  本文已影响246人  天一方蓝
Paste_Image.png
本文出自:http://blog.csdn.net/dt235201314/article/details/75009573
MPAndroidChart常见设置属性(一)——应用层
MPAndroidChart项目实战(一)——实现对比性柱状图
MPAndroidChart项目实战(二)——双平滑曲线(双折线图)和MarkView实现
MPAndroidChart项目实战(三)——饼状图实现和文字重合问题解决
MPAndroidChart项目实战(四)——柱状图实现及X轴文字不显示问题和柱状图上显示文字 MPAndroidChart X轴文字斜着显示
MPAndroidChart项目实战(五)——组合图实现趋势图
一丶效果演示(源码链接见文末,欢迎Star)

二丶功能点技术点
1.MPAndroidChart组合图使用(平滑曲线,折线(效果图里的直线))
2.趋势图分析,趋势图的实现
3.markView不显示趋势线上的数据
4.MPAndroidChart数据精度问题解决
5.markView显示数据格式问题解决
三丶核心代码
1.趋势图,趋势线的形成,其实是计算好的数据,计算公式看图(也可以自行百度)

移动端就爽啦,后台直接算好了给我们。
第一步数据处理(这里就不再像前面那样转化成实体类再转回来了):
public void getData(){
    String data ="{\"exponentList\":[{\"dottedLineData\":\"0.0109\",\"exponentDate\":\"07-04\",\"solidLineData\":\"0.0099\"}," +
            "{\"dottedLineData\":\"0.0102\",\"exponentDate\":\"07-05\",\"solidLineData\":\"0.0039\"}," +
            "{\"dottedLineData\":\"0.0095\",\"exponentDate\":\"07-06\",\"solidLineData\":\"0.0084\"}," +
            "{\"dottedLineData\":\"0.0088\",\"exponentDate\":\"07-07\",\"solidLineData\":\"0.0195\"}," +
            "{\"dottedLineData\":\"0.0081\",\"exponentDate\":\"07-08\",\"solidLineData\":\"0.0148\"}," +
            "{\"dottedLineData\":\"0.0073\",\"exponentDate\":\"07-09\",\"solidLineData\":\"0.0035\"}," +
            "{\"dottedLineData\":\"0.0066\",\"exponentDate\":\"07-10\",\"solidLineData\":\"0.0013\"}],\"overviewName\":\"负面舆情指数\"}";
    try {
        JSONObject object = new JSONObject(data);
        JSONArray jsonArray = object.getJSONArray("exponentList");
        dottedLineData = new ArrayList<>();
        solidLineData = new ArrayList<>();
        dataList = new ArrayList<>();
        BigDecimal scale = new BigDecimal(100);
        for (int i = 0, count = jsonArray.length(); i < count; i++) {
            //改了这里
            JSONObject jsonObject = jsonArray.optJSONObject(i);
            String dottedData = jsonObject.optString("dottedLineData");
            String solidData = jsonObject.optString("solidLineData");
            String exponentDate = jsonObject.optString("exponentDate");
            BigDecimal solid = new BigDecimal(solidData);
            BigDecimal dotted = new BigDecimal(dottedData);
            dottedLineData.add(new Entry(i,scale.multiply(solid).floatValue()));
            solidLineData.add(new Entry(i,scale.multiply(dotted).floatValue()));
            if ( Float.valueOf(dottedData)> maxData) {
                maxData = Float.valueOf(dottedData);
            }
            if (Float.valueOf(solidData)>maxData){
                maxData=Float.valueOf(solidData);
            }
            dataList.add(exponentDate);
        }
    } catch (JSONException e) {
        e.printStackTrace();
    }
}

这里得到平滑曲线上要展示的两条线的数据private List<Entry> dottedLineData,solidLineData,以及X轴要显示的日期数据List<String> dataList;
第二步:图标属性设置及属性

private void updataLineharts(){
        lineCharts = (LineChartInViewPager) mView.findViewById(R.id.trend_lineChart);
        List<Entry>[] entries = new ArrayList[2];
        entries[1] = dottedLineData;
        entries[0] = solidLineData;
        int[] cahrtColors = {Color.parseColor("#F0C330"), Color.parseColor("#50C4D9")};

        String[] labels = {"TCL", "趋势线"};
        boolean[] hasDotted = {true, false};
        final LineChartEntity lineChartEntity = new LineChartEntity(lineCharts, entries, labels, hasDotted,
                cahrtColors, R.color.black99, 12f);

        lineCharts.getAxisLeft().setAxisMaximum(maxData*120f);
        lineCharts.getAxisLeft().setAxisMinimum(0f);
        lineCharts.getAxisLeft().setGranularity(0.1f);
        lineCharts.getLegend().setEnabled(false);
        /*设置横坐标的最小宽度*/
        lineCharts.getAxisLeft().setMinWidth(25);
        lineCharts.getAxisRight().setMinWidth(25);
        lineCharts.getXAxis().enableGridDashedLine(10f, 0f, 0f);
        lineCharts.getXAxis().setGridLineWidth(0.5f);
        lineCharts.getXAxis().setGridColor(Color.parseColor("#9E9E9E"));
        lineChartEntity.setAxisFormatter(
                new IAxisValueFormatter() {

                    @Override
                    public String getFormattedValue(float value, AxisBase axis) {

                        String xValueTemp = mFormat.format(value);
                        float transferValue = value;
                        int index;
                        {
                            if (xValueTemp.contains(".")) {
                                return "";
                            }
                            index = (int) value;
                            index = Math.abs(index);
                        }

                        if (index < 0) {
                            return "";
                        }

                        if (index >= dottedLineData.size()) {
                            return "";
                        }
                        String timeTemp = dataList.get(index);
                        return timeTemp;
                    }

                }, new IAxisValueFormatter() {
                    @Override
                    public String getFormattedValue(float value, AxisBase axis) {
                        return mFormat.format(value) + "%";
                    }
                }
        );
        lineChartEntity.setLineMode(LineDataSet.Mode.HORIZONTAL_BEZIER);
        lineChartEntity.initLegend(Legend.LegendForm.CIRCLE, 13f, Color.parseColor("#999999"));
        lineChartEntity.updateLegendOrientation(Legend.LegendVerticalAlignment.TOP, Legend.LegendHorizontalAlignment.RIGHT, Legend.LegendOrientation.HORIZONTAL);
        lineCharts.getData().setDrawValues(false);
        lineCharts.setLayerType(View.LAYER_TYPE_SOFTWARE, null);
        if(dataList.size()>1)
//        lineCharts.getXAxis().setLabelRotationAngle(-30);
            lineCharts.getViewTreeObserver().addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
                @Override
                public boolean onPreDraw() {
                    lineCharts.getViewTreeObserver().removeOnPreDrawListener(this);
                    int width = lineCharts.getWidth();
                    if(dataList.size()>0){
                        String xAxis = dataList.get(0);
                        int totalWidth = (int) (dataList.size() * lineCharts.getResources().getDisplayMetrics().density * xAxis.length()*9);
                        float scale = (float) totalWidth / width;
                        if (scale < 1) {
                            scale = 1;
                        }
                        lineChartEntity.setMinMaxScaleX(scale, scale);
                    }else{
                        lineChartEntity.setMinMaxScaleX(1.0f, 1.0f);
                    }
                    return false;
                }
            });
        
        final NewMarkerView markerView = new NewMarkerView(getActivity(), R.layout.custom_marker_view_layout,false);
        markerView.setCallBack(new NewMarkerView.CallBack() {
            @Override
            public void onCallBack(float x, String value) {
                int index = (int) x;
                if (index >= dataList.size()) {
                    return;
                }

                if(!TextUtils.isEmpty(value)){
                    float data = Float.parseFloat(value);
                    BigDecimal solid = new BigDecimal(dottedLineData.get(index).getY());
                    BigDecimal scale = new BigDecimal(100);
                    float solidInvert = solid.multiply(scale).floatValue();
                    if(solidInvert==data*100){
                        markerView.getTvContent().setVisibility(View.VISIBLE);
                        markerView.getTvContent().setText(dataList.get(index) + "\n" + mFormat.format(data)+ "%");
                    }
                    else{
                        markerView.getTvContent().setVisibility(View.INVISIBLE);
                    }
                }else{
                    markerView.getTvContent().setText( dataList.get(index)+ "\n" + "%");
                }
            }
        });
        lineChartEntity.setMarkView(markerView);
        LineDataSet.Mode[] modes = new LineDataSet.Mode[2];
        modes[0] =  LineDataSet.Mode.LINEAR;
        modes[1] = LineDataSet.Mode.HORIZONTAL_BEZIER;
        lineChartEntity.setLineMode(modes);
    }

这里基本的属性和前面的设置类似,也有几点改进
1.数据提升精确度,运用BigDecimal
2.不同modes的图形样式(这里是折线和平滑曲线)
这里在lineChartEntity设置

/**
 * 设置图表颜色值,组合图
 * @param modes LineDataSet.Mode
 */
public void setLineMode (LineDataSet.Mode[] modes) {
    List<ILineDataSet> sets = ((LineChart)mChart).getData().getDataSets();
    for (int index = 0, len = sets.size(); index < len; index ++) {
        LineDataSet set = (LineDataSet) sets.get(index);
        if (index < modes.length) {
            set.setMode(modes[index]);
        }
    }
    mChart.invalidate();
}

3.markView的显示设置
这里加判断,当点击获取的点在平滑曲线上也就是真实值时才会显示
markView显示格式控制代码

/*部分数据不需要格式化处理*/
public NewMarkerView(Context context, int layoutResource,boolean needFormat) {
    super(context, layoutResource);
    this.needFormat = needFormat;
    tvContent = (TextView) findViewById(R.id.tvContent);
}
@Override
public void refreshContent(Entry e, Highlight highlight) {

    String values;
    if (e instanceof CandleEntry) {
        CandleEntry ce = (CandleEntry) e;
        values = "" + Utils.formatNumber(ce.getHigh(), 0, true);
    } else {
        if(!needFormat){
            values=""+e.getY();
        }else{
            values = "" + Utils.formatNumber(e.getY(), 0, true);
        }
    }

    if (mCallBack != null) {
        mCallBack.onCallBack(e.getX(), values);
    }
    super.refreshContent(e, highlight);
}

4.让折线图看起来像直线(隐藏数据的点)

public LineChartEntity (LineChart lineChart, List<Entry> []entries, String[] labels,boolean[] hasDotted,
                        int []chartColor, int valueColor, float textSize) {
    super(lineChart, entries, labels, chartColor, valueColor, textSize,hasDotted);
    this.hasDotted = hasDotted;
}
if (hasDotted!=null&&hasDotted[index]) {
    lineDataSet[index].setDrawCircles(false);
    lineDataSet[index].setCircleColor(R.color.white);
    lineDataSet[index].enableDashedLine(10f, 15f, 0f);
    lineDataSet[index].enableDashedHighlightLine(10f, 15f, 0f);
}

好了,组合图实现趋势图就分享到这里。
如果文章对你有帮助,可以顺手顶一下,如果对博主感兴趣,欢迎关注
https://github.com/JinBoy23520/MPAndroidChartDemoByJin(源码链接,欢迎Star)

写在最后微信扫码提问

image
上一篇下一篇

猜你喜欢

热点阅读