欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

安卓MPAndroidChart--LineChart实现动态曲线(传感器通信)

程序员文章站 2022-03-19 16:59:20
目录一、前言二、效果图三、代码实现3.1 定义变量3.2 初始化表格3.3 开启线程,开始与传感器通信三、总结一、前言本次记录的是一年前做的项目,与烟雾、火焰传感器模块通信,记录数据,并显示实时动态曲线。对于参加比赛来说,很多时候单靠软件是很不现实的。因此软件与硬件的通信显得十分重要,软硬件联动往往能在一些比赛中获得更好好的成绩。本次功能基于蓝牙模块实现与传感器通信,获取数据之后利用MPAndroidChart–LineChart实现各指数的实时动态曲线图。二、效果图以上是我实现的效果图,红色曲线...

一、前言

本次记录的是一年前做的项目,与烟雾、火焰传感器模块通信,记录数据,并显示实时动态曲线。对于参加比赛来说,很多时候单靠软件是很不现实的。因此软件与硬件的通信显得十分重要,软硬件联动往往能在一些比赛中获得更好好的成绩。本次功能基于蓝牙模块实现与传感器通信,获取数据之后利用MPAndroidChart–LineChart实现各指数的实时动态曲线图。

二、效果图

安卓MPAndroidChart--LineChart实现动态曲线(传感器通信)
以上是我实现的效果图,红色曲线表示火焰指数变化,黄色曲线表示烟雾指数的实时变化。

三、代码实现

3.1 定义变量

  private boolean isodd = true; //控制数据读取
    private boolean isopen = true; //控制警报

    public BluetoothSocket msocket = null;
    private LineChart lineChart_sensor;

    private XAxis xAxis;
    private YAxis yAxis_left, yAxis_right;


    Legend legend;
    LineData lineData;
    //点与数据集合
    List<Float> flamelists = new ArrayList<> ();
    List<Float> smoglists = new ArrayList<> ();

    List<Entry> entries_flame = new ArrayList<> ();
    List<Entry> entries_smog = new ArrayList<> ();

    LineDataSet lineDataSet_flame = new LineDataSet (entries_flame, "火焰指数");
    LineDataSet lineDataSet_smog = new LineDataSet (entries_smog, "烟雾指数");

    //创建随机数
    private Random random = new Random ();
    private DecimalFormat decimalFormat = new DecimalFormat ("#.000");


   
    private String string_smog = "正常", string_flame = "正常", string_isnormal = "正常";

    private  boolean isadd=false;//判断奇偶,控制数据传输

3.2 初始化表格

   /**
     * 初始化表格
     */
    private void initChart() {
        lineChart_sensor = findViewById (R.id.lc_sensor);
        lineChart_sensor.setDrawBorders (true);
        xAxis = lineChart_sensor.getXAxis ();
        yAxis_left = lineChart_sensor.getAxisLeft ();
         yAxis_right = lineChart_sensor.getAxisRight ();
        legend = lineChart_sensor.getLegend ();
        lineData = new LineData ();
        lineChart_sensor.setData (lineData);
        //设置图表基本属性
        setChartBasicAttr (lineChart_sensor);
        //设置xy轴
        setXYAxis (lineChart_sensor, xAxis, yAxis_left, yAxis_right);
        //添加线条
        initLine ();
        //设置图例
        createLegend (legend);
    }
     /**
     * 设置图表基本属性
     */

    void setChartBasicAttr(LineChart mlineChart) {
        mlineChart.setDrawGridBackground (false);//是否展示网格线
        mlineChart.setDrawBorders (true);//显示边界

        mlineChart.setDragEnabled (true);//可拖动
        mlineChart.setScaleEnabled (true);//可缩放
        mlineChart.setTouchEnabled (true);//可触摸
        //设置动画效果
        mlineChart.animateX (1500);

    }

    /**
     * 设置X、Y轴
     */
    private void setXYAxis(LineChart mlineChart_sensor, XAxis mxAxis, YAxis myAxis_left, YAxis myAxis_right) {
        mxAxis.setPosition (XAxis.XAxisPosition.BOTTOM);//x轴设置f显示在底部
        mxAxis.setAxisMinimum (0f); // 设置X轴的最小值
        mxAxis.setAxisMaximum (20); // 设置X轴的最大值
        mxAxis.setLabelCount (30, false); // 设置X轴的刻度数量,第二个参数表示是否平均分配
        mxAxis.setGranularity (1f); // 设置X轴坐标之间的最小间隔
        mlineChart_sensor.setVisibleXRangeMaximum (5);//最多在x轴上显示的总量
        myAxis_left.setAxisMinimum (0f);
        myAxis_right.setAxisMinimum (0f);
        myAxis_left.setAxisMaximum (1f);
        myAxis_right.setAxisMaximum (1f);
        myAxis_left.setLabelCount (1000);
        myAxis_left.setGranularity (0.001f);//设置x轴坐标之间的最小间隔
        myAxis_right.setLabelCount (1000);
        myAxis_right.setGranularity (0.001f);
        mlineChart_sensor.setVisibleYRangeMaximum (30, YAxis.AxisDependency.LEFT);
        mlineChart_sensor.setVisibleYRangeMaximum (30, YAxis.AxisDependency.RIGHT);
        myAxis_right.setEnabled (false);

    }


    /**
     * 设置图例
     */
    private void createLegend(Legend mlegend) {

        mlegend.setForm (Legend.LegendForm.LINE);
        mlegend.setTextSize (12f);
        //显示位置
        mlegend.setVerticalAlignment (Legend.LegendVerticalAlignment.BOTTOM);
        mlegend.setHorizontalAlignment (Legend.LegendHorizontalAlignment.LEFT);
        mlegend.setOrientation (Legend.LegendOrientation.HORIZONTAL);
        //是否绘制在图表里
        mlegend.setDrawInside (false);
        mlegend.setEnabled (true);

    }

    
  /**
   *初始化线条
   */
    void initLine() {
        createLine (flamelists, entries_flame, lineDataSet_flame, getResources ().getColor (R.color.red_700), lineData, lineChart_sensor);
        createLine (smoglists, entries_smog, lineDataSet_smog, getResources ().getColor (R.color.yellow_700), lineData, lineChart_sensor);
        for (int i = 0; i < lineData.getDataSetCount (); i++) {
            lineChart_sensor.getLineData ().getDataSets ().get (i).setVisible (true); //
        }
    }
    
   /**
     * 功能:动态创建一条曲线
     */

    private void createLine(List<Float> datalist, List<Entry> entries, LineDataSet mlineDataSet, int color, LineData mlineData, LineChart mlineChart) {
        for (int i = 0; i < datalist.size (); i++) {
            Entry entry = new Entry (i, datalist.get (i));
            entries.add (entry);
        }
        //初始化线条
        initLineDataSet (mlineDataSet, color, LineDataSet.Mode.CUBIC_BEZIER);

        if (mlineData == null) {
            mlineData = new LineData ();
            mlineData.addDataSet (mlineDataSet);
            mlineChart.setData (mlineData);

        } else {
            mlineChart.getLineData ().addDataSet (mlineDataSet);
        }
        mlineChart.invalidate ();
    }


3.3 开启线程,开始与传感器通信

这里在handler我没使用实际数据,使用的是随机数模拟数据。

      //对话框打开蓝牙
        if (!bluetoothAdapter.isEnabled ()) {
            Intent intent = new Intent (BluetoothAdapter.ACTION_REQUEST_ENABLE);
            startActivityForResult (intent, RESULT_OK);
        }
        //作为客户端连接
        try {
            new ClientThread (BtMac).start ();
        } catch (IOException e) {
            e.printStackTrace ();
        }

开启线程,进行通信。

 private class ClientThread extends Thread {
        private BluetoothDevice mdevice;
        
        private InputStream is;

        private Boolean isflame = true;


        Method method;

        public ClientThread(String adress) throws IOException {
            mdevice = bluetoothAdapter.getRemoteDevice (adress);


            Log.e ("ConnectThread: ", "连接线程");
        }

        @Override
        public void run() {
            // 关闭发现设备
            Log.e ("run: ", "开启线程");
            bluetoothAdapter.cancelDiscovery ();


            try {
                method = mdevice.getClass ().getMethod ("createRfcommSocket", new Class[]{int.class});
                msocket = (BluetoothSocket) method.invoke (mdevice, 1);


            } catch (Exception e) {
            }
            try {
                msocket.connect ();
                Log.e ("run: ", "连接成功");
                is = msocket.getInputStream ();
                if (is != null) {
                    //long currentTime = System.currentTimeMillis ();

                    byte[] bufferflame, buffersmog;
                    int count1, count2;
                    int ch;
                    while (true) {
                        count1 = 0;
                        count2 = 0;
                        bufferflame = new byte[1024];
                        buffersmog = new byte[1024];
                        Message msgflame = new Message ();
                        Message msgsmog = new Message ();
                        while ((ch = is.read ()) != '\n') {
                            if (ch == ',') {
                                isflame = false;
                                continue;
                            }
                            if (ch != -1 && isflame) {
                                bufferflame[count1] = (byte) ch;
                                count1++;
                            }
                            if (ch != -1 && !isflame) {
                                buffersmog[count2] = (byte) ch;
                                count2++;
                            }
                        }
                        isflame = true;

                        bufferflame[count1] = (byte) '\n';
                        count1++;
                        buffersmog[count2] = (byte) '\n';
                        count2++;
                        msgflame.obj = new String (bufferflame, 0, count1);
                        handler.sendMessage (msgflame);
                        sleep (100);
                        msgsmog.obj = new String (buffersmog, 0, count2);
                        handler.sendMessage (msgsmog);
                    }
                }


            } catch (IOException e) {
                e.printStackTrace ();
            } catch (InterruptedException e) {
                e.printStackTrace ();
            }

            {
                try {
                    msocket.close ();
                    Log.e ("run: ", "连接失败");
                } catch (IOException e1) {
                    e1.printStackTrace ();
                }
            }

        }
        public void cancle() {
            try {
                msocket.close ();
            } catch (IOException closeException) {

            }

        }

        Handler handler = new Handler () {
            @Override
            public void handleMessage(Message msg) {
                super.handleMessage (msg);


                if (isodd) {
                     string_flame= (String) msg.obj;
                    if (isadd){
                    addLine1Data (getRandom (0.5f));
                    addLine2Data (getRandom (0.5f));}

                    isodd = false;
                } else {
                    string_smog=(String) msg.obj;

                    if (isadd){

                    addLine1Data (getRandom (0.5f));
                    addLine2Data (getRandom (0.5f));}
                    isodd = true;

                }

                Log.e ("handleMessage: ", (String) msg.obj);
            }
        };
    }

三、总结

现在来看我的这个代码确实是冗余了,虽然实现了效果。但是由于当初的知识还比较浅薄,由此写出的代码是十分凌乱的,今后需要跟进一步学习,不能光做UI,得学学Java或者安卓更加底层的原理才会有进步空间。

本文地址:https://blog.csdn.net/qq_44706002/article/details/110502782

相关标签: Java Android