加入星計劃,您可以享受以下權益:

  • 創(chuàng)作內(nèi)容快速變現(xiàn)
  • 行業(yè)影響力擴散
  • 作品版權保護
  • 300W+ 專業(yè)用戶
  • 1.5W+ 優(yōu)質(zhì)創(chuàng)作者
  • 5000+ 長期合作伙伴
立即加入

串口通訊以及MPAndroidchart畫圖的使用(kotlin)

04/24 08:54
2238
服務支持:
技術交流群

完成交易后在“購買成功”頁面掃碼入群,即可與技術大咖們分享疑惑和經(jīng)驗、收獲成長和認同、領取優(yōu)惠和紅包等。

虛擬商品不可退

當前內(nèi)容為數(shù)字版權作品,購買后不支持退換且無法轉(zhuǎn)移使用。

加入交流群
掃碼加入
獲取工程師必備禮包
參與熱點資訊討論
放大
實物圖
  • 方案介紹
    • 一.Kotlin串口通訊實現(xiàn)
    • 二.MPAndroidChart圖表使用
    • 三.單個房間溫度圖表顯示功能實現(xiàn)
    • 四.多個房間溫度圖表顯示功能實現(xiàn)
    • 五.歷史數(shù)據(jù)分析圖顯示功能實現(xiàn)
  • 相關文件
  • 推薦器件
  • 相關推薦
  • 電子產(chǎn)業(yè)圖譜
申請入駐 產(chǎn)業(yè)圖譜

一.Kotlin串口通訊實現(xiàn)

1.1導入基礎庫

1.為了方便大家。我把所有關于串口的資源打包成aar 文件,大家直接使用即可。

谷歌android串口開發(fā) aar文件,地址如下所示:

使用過程

aar文件導入lib文件夾。

gradle文件

repositories {

??????? flatDir {

??????????? dirs 'libs'

??????? }

??? }
dependencies {

??? implementation(name: 'serialport-1.0.1', ext: 'aar')

}

1.2?效果展示

1.3布局界面

12.1?代碼

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

??? xmlns:app="http://schemas.android.com/apk/res-auto"

??? android:layout_width="match_parent"

??? android:layout_height="match_parent"

??? android:orientation="vertical">



??? <androidx.appcompat.widget.Toolbar

??????? android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"

??????? android:background="@color/shape3"

??????? android:id="@+id/toolbar"

??????? android:layout_width="match_parent"

??????? android:layout_height="?actionBarSize"

??????? app:title="History Data"

??????? app:titleTextColor="@android:color/white"

??????? >



??? </androidx.appcompat.widget.Toolbar>



??? <FrameLayout

??????? android:id="@+id/main_layout"

??????? android:layout_width="match_parent"

??????? android:layout_height="match_parent"

??????? >

??????? <LinearLayout

??????????? android:layout_width="match_parent"

??????????? android:layout_height="match_parent"

??????????? android:orientation="vertical">

??????????? <androidx.recyclerview.widget.RecyclerView

??????????????? android:id="@+id/recycler_view"

??????????????? style="@style/RecyclerViewStyle"

??????????????? android:layout_weight="1"/>

??????????? <RadioGroup

??????????????? android:id="@+id/radioGroup"

??????????????? android:layout_width="wrap_content"

??????????????? android:layout_height="wrap_content"

??????????????? android:layout_marginBottom="8dp"

??????????????? android:layout_marginStart="8dp"

??????????????? android:orientation="horizontal"

??????????????? app:layout_constraintBottom_toTopOf="@+id/sp_bote"

??????????????? app:layout_constraintStart_toStartOf="parent">

??????????????? <RadioButton

??????????????????? android:id="@+id/radioButton1"

??????????????????? android:layout_width="wrap_content"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_weight="1"

??????????????????? android:text="發(fā)送Text" />



??????????????? <RadioButton

??????????????????? android:id="@+id/radioButton2"

??????????????????? android:layout_width="wrap_content"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginLeft="10dp"

??????????????????? android:layout_weight="1"

??????????????????? android:checked="true"

??????????????????? android:text="發(fā)送Hex" />

??????????? </RadioGroup>

??????????? <androidx.cardview.widget.CardView

??????????????? style="@style/CardViews"

??????????????? app:cardCornerRadius="22dp">

?? ?????????????<LinearLayout

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:gravity="center_vertical"

??????????????????? android:layout_marginLeft="20dp">

??????? ????????????<TextView

??????????????????????? android:layout_width="66dp"

??????????????????????? android:layout_height="wrap_content"

??????????????????????? android:layout_marginTop="12dp"

??????????????????????? android:layout_marginBottom="12dp"

????? ??????????????????android:alpha="0.4"

??????????????????????? android:text="串口號"

??????????????????????? android:gravity="center"

??????????????????????? android:textColor="@color/black"

??????????????????????? android:textSize="14sp" />

??????????????????? <EditText

??????????????????????? android:layout_weight="1"

??????????????????????? android:id="@+id/EditText1"

??????????????????????? android:layout_width="match_parent"

??????????????????????? android:layout_height="match_parent"

?? ?????????????????????android:background="@null"

??????????????????????? android:hint="無"

??????????????????????? android:inputType="number"

??????????????????????? android:textColor="@color/shape1"

??????????????????????? android:textSize="14sp"

????????? ??????????????android:layout_marginLeft="14dp" />

??????????????????? <Spinner

??????????????????????? android:id="@+id/sp_serial"

??????????????????????? android:layout_width="100dp"

??????????????????????? android:layout_height="wrap_content"

????????? ??????????????android:layout_marginStart="8dp"

??????????????????????? android:layout_marginEnd="15dp">

??????????????????? </Spinner>

??????????????? </LinearLayout>

??????????? </androidx.cardview.widget.CardView>

??????????? <androidx.cardview.widget.CardView

??????????????? style="@style/CardViews"

??????????????? app:cardCornerRadius="22dp">

??????????????? <LinearLayout

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:gravity="center_vertical"

??????????????????? android:layout_marginLeft="20dp">

??????????????????? <TextView

??????????????????????? android:layout_width="66dp"

??????????????????????? android:layout_height="wrap_content"

??? ????????????????????android:layout_marginTop="12dp"

??????????????????????? android:layout_marginBottom="12dp"

??????????????????????? android:alpha="0.4"

??????????????????????? android:gravity="center"

??????????????????????? android:text="波特率"

???????? ???????????????android:textColor="@color/black"

??????????????????????? android:textSize="14sp" />



??????????????????? <EditText

??????????????????????? android:id="@+id/EditText2"

??????????????????????? android:layout_weight="1"

??????????????????????? android:layout_width="match_parent"

??????????????????????? android:layout_height="match_parent"

??????????????????????? android:background="@null"

??????????????????????? android:hint="無"

??????????????????????? android:inputType="number"

??????????????? ????????android:textColor="@color/shape1"

??????????????????????? android:textSize="14sp"

??????????????????????? android:layout_marginLeft="14dp" />

??????????????????? <Spinner

??????????????????????? android:id="@+id/sp_bote"

??????????????????????? android:layout_width="100dp"

??????????????????????? android:layout_height="wrap_content"

??????????????????????? android:layout_marginStart="8dp"

??????????????????????? android:layout_marginEnd="15dp">

??????????????????? </Spinner>



??????????????? </LinearLayout>

??????????? </androidx.cardview.widget.CardView>

??????????? <androidx.cardview.widget.CardView

??????????????? style="@style/CardViews"

??????????????? app:cardCornerRadius="22dp">

??????????????? <LinearLayout

??????? ????????????android:layout_width="match_parent"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:gravity="center_vertical"

??????????????????? android:layout_marginLeft="20dp">

??????????????????? <TextView

???????????? ???????????android:layout_width="66dp"

??????????????????????? android:layout_height="wrap_content"

??????????????????????? android:layout_marginTop="12dp"

??????????????????????? android:layout_marginBottom="12dp"

??????????????????????? android:alpha="0.4"

??????????????????????? android:text="發(fā)送消息"

??????????????????????? android:gravity="center"

??????????????????????? android:textColor="@color/black"

??????????????????????? android:textSize="14sp" />



??????????????????? <EditText

???????????????????? ???android:id="@+id/SendText"

??????????????????????? android:layout_width="match_parent"

??????????????????????? android:layout_height="match_parent"

??????????????????????? android:layout_marginLeft="14dp"

??????????????????????? android:layout_weight="1"

??????????????????????? android:background="@null"

??????????????????????? android:hint="請輸入"

??????????????????????? android:textColor="@color/teal_200"

??????????????????????? android:textSize="14sp" />



??????????????? </LinearLayout>

??????????? </androidx.cardview.widget.CardView>





??????????? <LinearLayout

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="wrap_content"

??????????????? android:gravity="center"

??????????????? android:layout_marginTop="20dp"

??????????????? android:layout_marginBottom="25dp"



??????????????? android:orientation="horizontal">

??????????????? <Button

??????????????????? android:id="@+id/open"

??????????????????? android:layout_width="wrap_content"

??????????????????? android:layout_height="44dp"

??????????????????? android:background="@drawable/shape_bt"

??????????????????? android:gravity="center"

??????????????????? android:text="打開串口"

??????????????????? android:textColor="@android:color/white"

??????????????????? android:textSize="@dimen/sp_14" />

??????????????? <View

??????????????????? android:layout_width="100dp"

??????????????????? android:layout_height="match_parent"

??????????????????? >

??????????????? </View>

??????????????? <Button

??????????????????? android:id="@+id/send"

??????????????????? android:layout_width="wrap_content"

??????????????????? android:layout_height="44dp"

??????????????????? android:background="@drawable/shape_bt"

??????????????????? android:gravity="center"

??????????????????? android:text="發(fā)送"

??????????????????? android:textColor="@android:color/white"

??????????????????? android:textSize="@dimen/sp_14" />

??????????? </LinearLayout>

??????? </LinearLayout>

??? </FrameLayout>

</LinearLayout>

1.4 Activity實現(xiàn)代碼

13.1?實列化

private var serialPortFinder: SerialPortFinder? = null

? ??? private var serialHelper: SerialHelper? = null

?????? //局部變量

private val list = ArrayList<Map<String, Any>>()

??? ???var map: Map<String, Any>? = null

1.3.2?適配波特率以及獲取本機串口號,進行串口監(jiān)聽

(1)適配器的編寫

?????? 名字:SpAdapter

public class SpAdapter extends BaseAdapter {



??? String[] datas;

??? Context mContext;



??? public SpAdapter(Context context) {

??????? this.mContext = context;

??? }



??? public void setDatas(String[] datas) {

??????? this.datas = datas;

??????? notifyDataSetChanged();

??? }



??? @Override

??? public int getCount() {

??????? return datas == null ? 0 : datas.length;

??? }



??? @Override

??? public Object getItem(int position) {

??????? return datas == null ? null : datas[position];

??? }



??? @Override

??? public long getItemId(int position) {

??????? return position;

??? }



??? @Override

??? public View getView(int position, View convertView, ViewGroup parent) {

??????? ViewHodler hodler = null;

??????? if (convertView == null) {

??????????? hodler = new ViewHodler();

??????????? convertView = LayoutInflater.from(mContext).inflate(R.layout.item_layout, null);

??????????? hodler.mTextView = (TextView) convertView;

??????????? convertView.setTag(hodler);

??????? } else {

??????????? hodler = (ViewHodler) convertView.getTag();

??????? }



??????? hodler.mTextView.setText(datas[position]);



??? ????return convertView;

??? }



??? private static class ViewHodler {

??????? TextView mTextView;

??? }

}

(2)適配代碼


serialPortFinder = SerialPortFinder()

??????? //獲取串口地址

??????? val ports = serialPortFinder!!.allDevicesPath

??????? //設置波特率地址

??????? val botes = arrayOf(

??????????? "0",

??????????? "50",

??????????? "75",

??????????? "110",

??????????? "134",

??????????? "150",

??????????? "200",

??????????? "300",

??????????? "600",

??????????? "1200",

??????????? "1800",

??????????? "2400",

??????????? "4800",

??????????? "9600",

??????????? "19200",

??????????? "38400",

??????????? "57600",

??????????? "115200",

??????????? "230400",

??????????? "460800",

??????????? "500000",

??????????? "576000",

??????????? "921600",

??????????? "1000000",

??????????? "1152000",

??????????? "1500000",

??????????? "2000000",

?????????? ?"2500000",

??????????? "3000000",

??????????? "3500000",

??????????? "4000000"

??????? )

??????? val spAdapter = SpAdapter(this)

??????? /*

???????? * TODO 適配下拉列表(串口地址)

??????? * */

??????? spAdapter.setDatas(ports)

??????? binding.spSerial.adapter = spAdapter

??????? binding.spSerial.onItemSelectedListener = object : OnItemSelectedListener {

??????????? override fun onItemSelected(

??????????????? parent: AdapterView<*>?,

??????????????? view: View,

??????????????? position: Int,

??????????????? id: Long

??????????? ) {

??????????????? serialHelper?.close()



??????????????? serialHelper?.port = ports[position]



??????????????? binding.EditText1.setText(ports[position])

??????????????? binding.open.text = "關閉串口"



???? ???????}



??????????? override fun onNothingSelected(parent: AdapterView<*>?) {}

??????? }

??????? /*

???????? * TODO 適配下拉列表(波特率地址)

??????? * */

??????? val spAdapter2 = SpAdapter(this)

??????? spAdapter2.setDatas(botes)

??????? binding.spBote.adapter = spAdapter2

??????? binding.spBote.onItemSelectedListener = object : OnItemSelectedListener {

??????????? override fun onItemSelected(

??????????????? parent: AdapterView<*>?,

??????????????? view: View,

??????????????? position: Int,

??????????????? id: Long

??????????? ) {

??????????????? serialHelper?.close()

??????????????? serialHelper?.setBaudRate(botes[position])

??????????????? binding.EditText2.setText(botes[position])

??????????????? binding.open.text = "關閉串口"



??? ????????}



??????????? override fun onNothingSelected(parent: AdapterView<*>?) {}

??????? }

(3)開啟串口監(jiān)視



?? serialHelper = object : SerialHelper() {

??????????? override fun onDataReceived(comBean: ComBean) {

??????????????? runOnUiThread {

//??????????????????? Toast.makeText(

//??????????????????????? baseContext,

//??????????????????????? FuncUtil.ByteArrToHex(comBean.bRec),

//????????????????????? ??Toast.LENGTH_SHORT

//??????????????????? ).show()

??????????????????? /*

??????????????????? * TODO 將獲取的數(shù)據(jù)進行列表適配

??????????????????? * */

??????????????????? map = HashMap()

??????????????????? (map as HashMap<String, Any>)["Value"] =comBean.sRecTime + ":?? " +

??????????????????????????? ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec))

??????????????????? list.add(map as HashMap<String, Any>)

??????????????????? Handler(Looper.getMainLooper()).postDelayed({

??????????????????????? /**

???????????????????????? * 列表數(shù)據(jù)的溢處理已經(jīng)適配

???????????????????????? * */

??????????????????????? if (list.size>12){

??????????????????????????? map = list[0]

??????????????????????????? list.remove(map)

??????????????????????? }

??????????????????????? initAdapter()

??????????????????? }, 300)

??????????????? }

??????????? }

??????? }???

二.MPAndroidChart圖表使用

2.1導入基礎庫

2.1.1.引入開源

在項目根目錄的build.gradle文件中加入如下代碼

allprojects {

??? repositories {

??????? maven { url "https://jitpack.io" }

??? }

2.1.2在app根目錄的buil.gradle文件中加入依賴

根據(jù)自己的需求添加對應的庫文件

主要運用到的為下列兩個開源庫

/*安卓項目實戰(zhàn)之:開源框架BaseRecyclerViewAdapterHelper的使用*/

api 'com.github.CymChad:BaseRecyclerViewAdapterHelper:3.0.4'

//MPAndroidChart畫圖

??? implementation 'com.github.PhilJay:MPAndroidChart:v3.0.3'

dependencies {

//api表示對所有的module可見,如果沒有在其他地方使用到版本號,則不用進行版本號的統(tǒng)一控制

/*??? *//*一個非常好用的開源庫,調(diào)試Android數(shù)據(jù)庫有救了*//*

??? debugImplementation 'com.glance.guolindev:glance:1.0.0-alpha01'*/

??? //使用開源的org.greenrobot.EventBus可以更好地維護事件處理

??? api 'org.greenrobot:eventbus:3.0.0'

??? //MultiDex,解決方法數(shù)超過65535限制

??? api 'androidx.multidex:multidex:2.0.1'

??? //leakcanary檢測內(nèi)存泄漏

??? debugImplementation 'com.squareup.leakcanary:leakcanary-android:2.4'

??? //Kotlin

??? implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"

??? //RxJava

??? api 'io.reactivex.rxjava2:rxandroid:2.1.0'

??? api 'io.reactivex.rxjava2:rxjava:2.2.4'

??? //側(cè)滑返回框架

??? api 'com.billy.android:smart-swipe:1.1.2'

??? /*android4.4以上沉浸式狀態(tài)欄和導航欄實現(xiàn)以及Bar的其他管理*/

??? api 'com.gyf.immersionbar:immersionbar:3.0.0'

??? /*安卓項目實戰(zhàn)之:開源框架BaseRecyclerViewAdapterHelper的使用*/

??? api 'com.github.CymChad:BaseRecyclerViewAdapterHelper:3.0.4'

??? //下拉刷新框架

??? api 'com.scwang.smartrefresh:SmartRefreshLayout:1.1.2'

??? //特殊Header

??? api 'com.scwang.smartrefresh:SmartRefreshHeader:1.1.2'

??? //MPAndroidChart畫圖

??? implementation 'com.github.PhilJay:MPAndroidChart:v3.0.3'

??? //底部選擇器

??? api 'com.contrarywind:Android-PickerView:4.1.8'

}

2.2 LineChart曲線圖

2.2.1布局代碼

<com.github.mikephil.charting.charts.LineChart

??????????? android:id="@+id/dynamic_chart1"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="380dp"/>

2.2.2 Activity實現(xiàn)代碼

1.寫一個工具類以便我們使用

文件名:DynamicLineChartManager

public class DynamicLineChartManager {



??? private LineChart lineChart;

??? private YAxis leftAxis;

??? private YAxis rightAxis;

??? private XAxis xAxis;

??? private LineData lineData;

??? private LineDataSet lineDataSet;

??? private List<ILineDataSet> lineDataSets = new ArrayList<>();

??? private SimpleDateFormat df = new SimpleDateFormat("HH:mm:ss");//設置日期格式

??? private List<String> timeList = new ArrayList<>(); //存儲x軸的時間



??? //一條曲線

??? public DynamicLineChartManager(LineChart mLineChart, String name, int color) {

??????? this.lineChart = mLineChart;

??????? leftAxis = lineChart.getAxisLeft();

??????? rightAxis = lineChart.getAxisRight();

??????? xAxis = lineChart.getXAxis();

??????? initLineChart();

??????? initLineDataSet(name, color);

??? }

??? //警告曲線

??? public DynamicLineChartManager(LineChart mLineChart, String name, int color,float High, String warn,int warn_color) {

??????? this.lineChart = mLineChart;

??????? leftAxis = lineChart.getAxisLeft();

??????? rightAxis = lineChart.getAxisRight();

?????? ?xAxis = lineChart.getXAxis();

??????? initLineChart();

??????? initLineDataWarn(name, color,High,warn,warn_color);

??? }

??? //多條曲線

??? public DynamicLineChartManager(LineChart mLineChart, List<String> names, List<Integer> colors) {

??????? this.lineChart = mLineChart;

??????? leftAxis = lineChart.getAxisLeft();

??????? rightAxis = lineChart.getAxisRight();

??????? xAxis = lineChart.getXAxis();

??????? initLineChart();

??????? initLineDataSet(names, colors);



??? }



??? /**

???? * 初始化LineChar

???? */

??? private void initLineChart() {



??????? lineChart.setDrawGridBackground(false);

??????? //顯示邊界

??????? lineChart.setDrawBorders(true);

??????? //折線圖例 標簽 設置

??????? Legend legend = lineChart.getLegend();

??????? legend.setForm(Legend.LegendForm.LINE);

??????? legend.setTextSize(11f);

??????? //顯示位置

??????? legend.setVerticalAlignment(Legend.LegendVerticalAlignment.BOTTOM);

??????? legend.setHorizontalAlignment(Legend.LegendHorizontalAlignment.LEFT);

????? ??legend.setOrientation(Legend.LegendOrientation.HORIZONTAL);

??????? legend.setDrawInside(false);



??????? //X軸設置顯示位置在底部

??????? xAxis.setPosition(XAxis.XAxisPosition.BOTTOM);

??????? xAxis.setGranularity(1f);

??????? xAxis.setLabelCount(10);



??????? xAxis.setValueFormatter(new IAxisValueFormatter() {

??????????? @Override

??????????? public String getFormattedValue(float value, AxisBase axis) {

??????????????? return timeList.get((int) value % timeList.size());

??????????? }

??????? });



??????? //保證Y軸從0開始,不然會上移一點

??????? leftAxis.setAxisMinimum(0f);

??????? rightAxis.setAxisMinimum(0f);

??? }



??? /**

???? * 初始警告線化折線(一條線)

???? *

???? * @param name

???? * @param color

???? */

??? private void initLineDataWarn(String name, int color,float High, String warn,int warn_color) {



??????? lineDataSet = new LineDataSet(null, name);

??????? lineDataSet.setLineWidth(1.5f);

??????? lineDataSet.setCircleRadius(1.5f);

??????? lineDataSet.setColor(color);

??????? lineDataSet.setCircleColor(color);

??????? lineDataSet.setHighLightColor(color);

??????? //設置曲線填充

??????? lineDataSet.setDrawFilled(true);

??????? lineDataSet.setAxisDependency(YAxis.AxisDependency.LEFT);

??????? lineDataSet.setValueTextSize(10f);

??????? lineDataSet.setMode(LineDataSet.Mode.CUBIC_BEZIER);

??????? //添加一個空的 LineData

??????? lineData = new LineData();

??????? lineChart.setData(lineData);

??????? lineChart.invalidate();

??????? setHightLimitLine(High,warn, warn_color);

??? }

??? /**

???? * 初始化折線(一條線)

???? *

???? * @param name

???? * @param color

???? */

??? private void initLineDataSet(String name, int color) {



??????? lineDataSet = new LineDataSet(null, name);

??????? lineDataSet.setLineWidth(1.5f);

??????? lineDataSet.setCircleRadius(1.5f);

??????? lineDataSet.setColor(color);

??????? lineDataSet.setCircleColor(color);

??????? lineDataSet.setHighLightColor(color);

??????? //設置曲線填充

??????? lineDataSet.setDrawFilled(true);

??????? lineDataSet.setAxisDependency(YAxis.AxisDependency.LEFT);

??????? lineDataSet.setValueTextSize(10f);

??????? lineDataSet.setMode(LineDataSet.Mode.CUBIC_BEZIER);

??????? //添加一個空的 LineData

??????? lineData = new LineData();

??????? lineChart.setData(lineData);

??????? lineChart.invalidate();



??? }



??? /**

???? * 初始化折線(多條線)

???? *

???? * @param names

???? * @param colors

???? */

??? private void initLineDataSet(List<String> names, List<Integer> colors) {



??????? for (int i = 0; i < names.size(); i++) {

??????????? lineDataSet = new LineDataSet(null, names.get(i));

??????????? lineDataSet.setColor(colors.get(i));

??????????? lineDataSet.setLineWidth(1.5f);

??????????? lineDataSet.setCircleRadius(1.5f);

??????????? lineDataSet.setColor(colors.get(i));



??????????? lineDataSet.setDrawFilled(true);

??????????? lineDataSet.setCircleColor(colors.get(i));

??????????? lineDataSet.setHighLightColor(colors.get(i));

??????????? lineDataSet.setMode(LineDataSet.Mode.CUBIC_BEZIER);

??????????? lineDataSet.setAxisDependency(YAxis.AxisDependency.LEFT);

??????????? lineDataSet.setValueTextSize(10f);

??????????? lineDataSets.add(lineDataSet);



??????? }

??????? //添加一個空的 LineData

??????? lineData = new LineData();

??????? lineChart.setData(lineData);

??????? lineChart.invalidate();

??? }



??? /**

???? * 動態(tài)添加數(shù)據(jù)(一條折線圖)

???? *

???? * @param number

???? */

??? public void addEntry(Float number) {



??????? //最開始的時候才添加 lineDataSet(一個lineDataSet 代表一條線)

??????? if (lineDataSet.getEntryCount() == 0) {

??????????? lineData.addDataSet(lineDataSet);

??????? }

??????? lineChart.setData(lineData);

??????? //避免集合數(shù)據(jù)過多,及時清空(做這樣的處理,并不知道有沒有用,但還是這樣做了)

??????? if (timeList.size() > 11) {

??????????? timeList.clear();

??????? }



??????? timeList.add(df.format(System.currentTimeMillis()));



??????? Entry entry = new Entry(lineDataSet.getEntryCount(), number);

??????? lineData.addEntry(entry, 0);

??????? //通知數(shù)據(jù)已經(jīng)改變

??????? lineData.notifyDataChanged();

??????? lineChart.notifyDataSetChanged();

??????? //設置在曲線圖中顯示的最大數(shù)量

??????? lineChart.setVisibleXRangeMaximum(10);

??????? //移到某個位置

??????? lineChart.moveViewToX(lineData.getEntryCount() - 5);



??? }

??? /**

???? * 動態(tài)添加數(shù)據(jù)(一條折線圖)

???? *

???? * @param number

???? * @param time

???? * @param str

???? */

??? public void HistoryEntry(Float number,String time,String str) {



??????? //最開始的時候才添加 lineDataSet(一個lineDataSet 代表一條線)

??????? if (lineDataSet.getEntryCount() == 0) {

??????????? lineData.addDataSet(lineDataSet);

??????? }

??????? lineChart.setData(lineData);

??????? //避免集合數(shù)據(jù)過多,及時清空(做這樣的處理,并不知道有沒有用,但還是這樣做了)

??????? if (timeList.size() > 100) {

??????????? timeList.clear();

??????? }



??????? timeList.add(time);



??????? Entry entry = new Entry(lineDataSet.getEntryCount(), number);

??????? lineData.addEntry(entry, 0);

??????? //通知數(shù)據(jù)已經(jīng)改變

??????? lineData.notifyDataChanged();

??????? lineChart.notifyDataSetChanged();

??????? //設置在曲線圖中顯示的最大數(shù)量

??????? lineChart.setVisibleXRangeMaximum(10);

??????? //移到某個位置

??????? lineChart.moveViewToX(lineData.getEntryCount() - 5);

??????? setDescription(str);

??? }

??? /**

???? * 動態(tài)添加數(shù)據(jù)(多條折線圖)

???? *

???? * @param numbers

???? */

??? public void addEntry(List<Float> numbers) {



??????? if (lineDataSets.get(0).getEntryCount() == 0) {

??????????? lineData = new LineData(lineDataSets);

??????????? lineChart.setData(lineData);

??????? }

??????? if (timeList.size() > 11) {

??????????? timeList.clear();

??????? }

??????? timeList.add(df.format(System.currentTimeMillis()));

??????? for (int i = 0; i < numbers.size(); i++) {

??????????? Entry entry = new Entry(lineDataSet.getEntryCount(), numbers.get(i));

??????????? lineData.addEntry(entry, i);

??????????? lineData.notifyDataChanged();

??????????? lineChart.notifyDataSetChanged();

??????????? lineChart.setVisibleXRangeMaximum(6);

??????????? lineChart.moveViewToX(lineData.getEntryCount() - 5);

??????? }

??? }



??? /**

???? * 設置Y軸值

???? *

???? * @param max

???? * @param min

???? * @param labelCount

???? */

??? public void setYAxis(float max, float min, int labelCount) {

??????? if (max < min) {

??????????? return;

??????? }

??????? leftAxis.setAxisMaximum(max);

??????? leftAxis.setAxisMinimum(min);

??????? leftAxis.setLabelCount(labelCount, false);



??????? rightAxis.setAxisMaximum(max);

??????? rightAxis.setAxisMinimum(min);

??????? rightAxis.setLabelCount(labelCount, false);

??????? lineChart.invalidate();

??? }

??? /**

???? * 設置高限制線

???? *

???? * @param high

???? * @param name

???? */

??? public void setHightLimitLine(float high, String name, int color) {

??????? if (name == null) {

??????????? name = "高限制線";

??????? }

??????? LimitLine hightLimit = new LimitLine(high, name);

??????? hightLimit.setLineWidth(4f);

??????? hightLimit.setTextSize(10f);

??????? hightLimit.setLineColor(color);

??????? hightLimit.setTextColor(color);

??????? leftAxis.addLimitLine(hightLimit);

??????? lineChart.invalidate();

??? }



??? /**

???? * 設置低限制線

???? *

???? * @param low

???? * @param name

???? */

??? public void setLowLimitLine(int low, String name) {

??????? if (name == null) {

??????????? name = "低限制線";

??????? }

??????? LimitLine hightLimit = new LimitLine(low, name);

??????? hightLimit.setLineWidth(4f);

??????? hightLimit.setTextSize(10f);

??? ????leftAxis.addLimitLine(hightLimit);

??????? lineChart.invalidate();

??? }



??? /**

???? * 設置描述信息

???? *

???? * @param str

???? */

??? public void setDescription(String str) {

??????? Description description = new Description();

??????? description.setText(str);

??????? description.setTextColor(Color.MAGENTA);

??????? description.setTextSize(15);



??????? lineChart.setDescription(description);

??????? lineChart.invalidate();

??? }

}

2.在activity里面使用

(1)實列化工具類

private var dynamicLineChartManager1: DynamicLineChartManager? = null

局部數(shù)據(jù)

/*

??? * 1.關于List在kotlin里面沒有add(),clear() 方法解決辦法

??? *?? 將List改變成MutableList,MutableList源碼可以發(fā)現(xiàn),常用的clear、addAll等方法都有定義

??? *?? 解決的辦法就是將變量類型使用"MutableList"代替"List"就可以了,完整的定義如下代碼:

??? * */

??? private val list: MutableList<Float> = ArrayList() //數(shù)據(jù)集合



??? private val names: MutableList<String> = ArrayList() //折線名字集合



??? private val colour: MutableList<Int> = ArrayList() //折線顏色集合

(2)添加局部數(shù)據(jù)以及實現(xiàn)曲線

//折線名字

??????? names.add("溫度")

??????? names.add("壓強")

??????? names.add("其他")

??????? //折線顏色

??????? colour.add(Color.CYAN)

??????? colour.add(Color.GREEN)

??????? colour.add(Color.BLUE)

//實現(xiàn)一條曲線

dynamicLineChartManager1 = DynamicLineChartManager(binding.dynamicChart1, names[0], colour[0])

????? //實現(xiàn)多條曲線

??????? dynamicLineChartManager2 = DynamicLineChartManager(binding.dynamicChart2, names, colour)

(3)添加數(shù)據(jù)到曲線內(nèi)

//添加一條曲線的數(shù)據(jù)

??????????? dynamicLineChartManager1?.addEntry((Math.random() * 100).toFloat())

//添加多條曲線的數(shù)據(jù)

??????????????????? list.add((Math.random() * 50).toFloat() + 10)

??????????????????? list.add((Math.random() * 80).toFloat() + 10)

????????????????? ??list.add((Math.random() * 100).toFloat())

??????????????????? dynamicLineChartManager2!!.addEntry(list)

??????????????????? list.clear()

2.3 BarChart柱狀圖

2.3.1布局代碼

<com.github.mikephil.charting.charts.CombinedChart

???? ???????android:id="@+id/chart1"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="360dp"/>

2.3.2 Activity實現(xiàn)代碼

1.寫一個工具類以便我們使用

類名字為:CombinedChartManager

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() {

??????? //不顯示描述內(nèi)容

??????? 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); // 立即執(zhí)行的動畫,x軸

??? }



??? /**

???? * 設置X軸坐標值

???? *

???? * @param xAxisValues x軸坐標集合

???? */

??? public void setXAxis(final List<String> xAxisValues) {



??????? //設置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<Float> lineChartY, String lineName, int lineColor) {

??????? LineData lineData = new LineData();



??????? ArrayList<Entry> 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<List<Float>> lineChartYs, List<String> lineNames, List<Integer> lineColors) {

??????? LineData lineData = new LineData();



??????? for (int i = 0; i < lineChartYs.size(); i++) {

??????????? ArrayList<Entry> 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<Float> barChartY, String barName, int barColor) {

??????? BarData barData = new BarData();

??????? ArrayList<BarEntry> 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);



??????? //以下是為了解決 柱狀圖 左右兩邊只顯示了一半的問題 根據(jù)實際情況 而定

??????? 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<List<Float>> barChartYs, List<String> barNames, List<Integer> barColors) {

??????? List<IBarDataSet> lists = new ArrayList<>();

??????? for (int i = 0; i < barChartYs.size(); i++) {

??????????? ArrayList<BarEntry> 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(); //需要顯示柱狀圖的類別 數(shù)量

??????? 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<String> xAxisValues, List<Float> barChartY, List<Float> 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 barChartY?? 柱狀圖Y軸值

???? * @param lineChartY? 折線圖Y軸值

???? * @param barName???? 柱狀圖名字

???? * @param lineName??? 折線圖名字

???? * @param barColor??? 柱狀圖顏色

???? * @param lineColor?? 折線圖顏色

???? */



??? public void showbinedChart(

??????????? List<String> xAxisValues, List<Float> barChartY

??????????? , String barName, int barColor) {

??????? initChart();

??????? setXAxis(xAxisValues);



??????? CombinedData combinedData = new CombinedData();



??????? combinedData.setData(getBarData(barChartY, barName, barColor));



??????? 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<String> xAxisValues, List<List<Float>> barChartYs, List<List<Float>> lineChartYs,

??????????? List<String> barNames, List<String> lineNames, List<Integer> barColors, List<Integer> 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();

??? }

}

2在Activity里面使用



(1)添加局部數(shù)據(jù)以及實現(xiàn)曲線

???? ??private fun intDate(){

??????? //x軸數(shù)據(jù)

??????? val xData: MutableList<String> = ArrayList()

??????? for (i in 0..20) {

??????????? xData.add(i.toString())

??????? }

??????? //y軸數(shù)據(jù)集合

??????? val yBarDatas: MutableList<List<Float>> = ArrayList()

??????? //4種直方圖

??????? for (i in 0..3) {

??????????? //y軸數(shù)

??????????? val yData: MutableList<Float> = ArrayList()

??????????? for (j in 0..20) {

??????????????? yData.add((Math.random() * 100).toFloat())

??????????? }

??????????? yBarDatas.add(yData)

??????? }

??????? //顏色集合

??????? val colors: MutableList<Int> = ArrayList()

??????? colors.add(Color.BLUE)

??????? colors.add(Color.RED)

??????? colors.add(Color.YELLOW)

??????? colors.add(Color.CYAN)



??????? //管理類

?????? ?val combineChartManager1 = CombinedChartManager(binding.chart1)



??????? combineChartManager1.showbinedChart(

??????????? xData, yBarDatas.get(0),

??????????? "直方圖", colors.get(0)

??????? )

??? }

2.4?曲線混合柱狀圖

2.4.1布局代碼

? <com.github.mikephil.charting.charts.CombinedChart

??????????? android:id="@+id/chart1"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="360dp"/>

2.4.2 Activity實現(xiàn)代碼

1..實現(xiàn)混合顯示(工具類已經(jīng)提供)

private fun intDate(){

??????? //x軸數(shù)據(jù)

??????? val xData: MutableList<String> = ArrayList()

??????? for (i in 0..20) {

??????????? xData.add(i.toString())

??????? }

??????? //y軸數(shù)據(jù)集合

??????? val yBarDatas: MutableList<List<Float>> = ArrayList()

??????? //4種直方圖

??????? for (i in 0..3) {

??????????? //y軸數(shù)

??????????? val yData: MutableList<Float> = ArrayList()

??????????? for (j in 0..20) {

??????????????? yData.add((Math.random() * 100).toFloat())

??????????? }

??????????? yBarDatas.add(yData)

??????? }

????? ??//y軸數(shù)據(jù)集合

??????? val yLineDatas: MutableList<List<Float>> = ArrayList()

??????? //4種直方圖

??????? for (i in 0..3) {

??????????? //y軸數(shù)

??????????? val yData: MutableList<Float> = ArrayList()

??????????? for (j in 0..20) {

??????????????? yData.add((Math.random() * 100).toFloat())

??????????? }

??????????? yLineDatas.add(yData)

??????? }

??????? //名字集合

??????? val barNames: MutableList<String> = ArrayList()

??????? barNames.add("直方圖一")

??????? barNames.add("直方圖二")

??????? barNames.add("直方圖三")

??????? barNames.add("直方圖四")

??????? //顏色集合

??????? val colors: MutableList<Int> = ArrayList()

??????? colors.add(Color.BLUE)

??????? colors.add(Color.RED)

??????? colors.add(Color.YELLOW)

??????? colors.add(Color.CYAN)

?????? ?//豎狀圖管理類

??????? val lineNames: MutableList<String> = ArrayList()

??????? lineNames.add("折線圖一")

??????? lineNames.add("折線圖二")

??????? lineNames.add("折線圖三")

??????? lineNames.add("折線圖四")





??????? //管理類

??????? val combineChartManager1 = CombinedChartManager(binding.chart1)

??????? combineChartManager1.showCombinedChart(xData, yBarDatas.get(0), yLineDatas.get(0),

??????????????? "直方圖", "線性圖", colors.get(0), colors.get(1));



??????? val combineChartManager2 = CombinedChartManager(binding.chart2)

??????? combineChartManager2.showCombinedChart(

??????????? xData, yBarDatas, yLineDatas, barNames, lineNames,

??????????? colors, colors

??????? )



??? }

2.5 RadarChart雷達圖

2.5.1布局代碼‘

<com.github.mikephil.charting.charts.RadarChart

??????????? android:id="@+id/radar"

??????????? android:layout_marginTop="20dp"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="300dp">

2.5.2 Activity實現(xiàn)代碼

1.實現(xiàn)代碼

?? fun radar(){

??????? val radar: RadarChart? = binding.radar

??????? var list: MutableList<RadarEntry>? = null

??????? var list2: MutableList<RadarEntry>? = null

??????? list = ArrayList()

??????? list2 = ArrayList()

??????? list.add(RadarEntry(30F))

??????? list.add(RadarEntry(35F))

??????? list.add(RadarEntry(40F))

??????? list.add(RadarEntry(35F))

??????? list.add(RadarEntry(20F))

??????? list2.add(RadarEntry(50F))

??????? list2.add(RadarEntry(45F))

??????? list2.add(RadarEntry(55F))

??????? list2.add(RadarEntry(40F))

??????? list2.add(RadarEntry(60F))

??????? val radarDataSet = RadarDataSet(list, "男性")

??????? radarDataSet.color = Color.RED

??????? val radarDataSet1 = RadarDataSet(list2, "女性")

??????? radarDataSet1.color = Color.BLUE

??????? val radarData = RadarData(radarDataSet)

??????? radarData.addDataSet(radarDataSet1)

??????? radar!!.data = radarData



??????? //Y軸最小值不設置會導致數(shù)據(jù)中最小值默認成為Y軸最小值

??????? radar.yAxis.axisMinimum = 0f



??????? //大字的顏色(中心點和各頂點的連線)

??????? radar.webColor = Color.CYAN

??????? //所有五邊形的顏色

??????? radar.webColorInner = Color.CYAN

??????? //整個控件的背景顏色

??????? radar.setBackgroundColor(Color.LTGRAY)

??????? val xAxis = radar.xAxis

??????? xAxis.textColor = Color.RED //X軸字體顏色

??????? xAxis.textSize = 16f //X軸字體大小

??????? //自定義X軸坐標描述(也就是五個頂點上的文字,默認是0、1、2、3、4)

??????? xAxis.valueFormatter =

??????????? IAxisValueFormatter { v, axisBase ->

??????????????? if (v == 0f) {

??????????????????? return@IAxisValueFormatter "語文"

??????????????? }

??????????????? if (v == 1f) {

??????????????????? return@IAxisValueFormatter "數(shù)學"

??????????????? }

???? ???????????if (v == 2f) {

??????????????????? return@IAxisValueFormatter "英語"

??????????????? }

??????????????? if (v == 3f) {

??????????????????? return@IAxisValueFormatter "生物"

??????????????? }

??????????????? if (v == 4f) {

??????????????????? "地理"

?? ?????????????} else ""

??????????? }





??????? //是否繪制雷達框上對每個點的數(shù)據(jù)的標注??? 和Y軸坐標點一般不同時存在 否則顯得很擠? 默認為true

??????? radarDataSet.setDrawValues(false)

??????? radarDataSet1.setDrawValues(false)

??????? radarDataSet.valueTextSize = 12f //數(shù)據(jù)值得字體大?。ㄟ@里只是寫在這)

??????? radarDataSet.valueTextColor = Color.CYAN //數(shù)據(jù)值得字體顏色(這里只是寫在這)

??????? val yAxis = radar!!.yAxis

??????? //是否繪制Y軸坐標點? 和雷達框數(shù)據(jù)一般不同時存在 否則顯得很擠 默認為true

??????? yAxis.setDrawLabels(true)

??????? yAxis.textColor = Color.GRAY //Y軸坐標數(shù)據(jù)的顏色

??????? yAxis.axisMaximum = 80f //Y軸最大數(shù)值

??????? yAxis.axisMinimum = 0f //Y軸最小數(shù)值

??????? //Y軸坐標的個數(shù)??? 第二個參數(shù)一般填false???? true表示強制設置標簽數(shù) 可能會導致X軸坐標顯示不全等問題

??????? yAxis.setLabelCount(10, false)





??????? //對于右下角一串字母的操作

??????? radar.description.isEnabled = false //是否顯示右下角描述

??????? radar.description.text = "這是修改那串英文的方法" //修改右下角字母的顯示

??????? radar.description.textSize = 20f //字體大小

??????? radar.description.textColor = Color.CYAN //字體顏色



??????? //圖例

??????? val legend = radar.legend

??????? legend.isEnabled = true //是否顯示圖例

??????? legend.position = Legend.LegendPosition.BELOW_CHART_CENTER //圖例的位置

??? }

2.6 PieChart餅狀圖

2.6.1布局代碼

<com.github.mikephil.charting.charts.PieChart

??????????? android:id="@+id/pie"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="300dp">

??????? </com.github.mikephil.charting.charts.PieChart>

2.6.2 Activity實現(xiàn)代碼

1.實現(xiàn)代碼


fun pie(){

??????? val pie: PieChart = binding.pie

??????? list = ArrayList()

??????? (list as ArrayList<PieEntry>).add(PieEntry(56F, "男性"))

??????? (list as ArrayList<PieEntry>).add(PieEntry(44F, "女性"))

??????? val pieDataSet = PieDataSet(list, "")

??????? val pieData = PieData(pieDataSet)

??????? pie.data = pieData

??????? pie.setBackgroundColor(Color.GRAY)



??????? //設置各個數(shù)據(jù)的顏色

??????? pieDataSet.setColors(Color.RED, Color.BLUE)

??????? //實體扇形的空心圓的半徑?? 設置成0時就是一個圓 而不是一個環(huán)

??????? pie.holeRadius = 30f

??????? //中間半透明白色圓的半徑??? 設置成0時就是隱藏

??????? pie.transparentCircleRadius = 30f

??????? //設置中心圓的顏色

??????? pie.setHoleColor(Color.CYAN)

??????? //設置中心部分的字? (一般中間白色圓不隱藏的情況下才設置)

??????? pie.centerText = "男女比例"

??????? //設置中心字的字體顏色

??????? pie.setCenterTextColor(Color.RED)

??????? //設置中心字的字體大小

??????? pie.setCenterTextSize(16f)

??????? //設置描述的字體大?。▓D中的? 男性? 女性)

??????? pie.setEntryLabelTextSize(20f)

??????? //設置數(shù)據(jù)的字體大小? (圖中的? 44???? 56)

??????? pieDataSet.valueTextSize = 20f

??????? //設置描述的位置

??????? pieDataSet.xValuePosition = PieDataSet.ValuePosition.OUTSIDE_SLICE

??????? pieDataSet.valueLinePart1Length = 0.6f //設置描述連接線長度

??????? //設置數(shù)據(jù)的位置

??????? pieDataSet.yValuePosition = PieDataSet.ValuePosition.OUTSIDE_SLICE

??????? pieDataSet.valueLinePart2Length = 0.6f //設置數(shù)據(jù)連接線長度

??????? //設置兩根連接線的顏色

??????? pieDataSet.valueLineColor = Color.WHITE



??????? //對于右下角一串字母的操作

??????? pie.description.isEnabled = false //是否顯示右下角描述

??????? pie.description.text = "這是修改那串英文的方法" //修改右下角字母的顯示

??????? pie.description.textSize = 20f //字體大小

??????? pie.description.textColor = Color.RED //字體顏色



??????? //圖例

??????? val legend = pie.legend

??????? legend.isEnabled = true //是否顯示圖例

??????? legend.position = Legend.LegendPosition.BELOW_CHART_CENTER //圖例的位置





??????? //數(shù)據(jù)更新

??????? pie.notifyDataSetChanged()

??????? pie.invalidate()



??????? //動畫(如果使用了動畫可以則省去更新數(shù)據(jù)的那一步)

??????? pie.animateY(3000) //在Y軸的動畫? 參數(shù)是動畫執(zhí)行時間 毫秒為單位

??????? //???? ???line.animateX(2000); //X軸動畫

??? //??????? line.animateXY(2000,2000);//XY兩軸混合動畫

??? }

三.單個房間溫度圖表顯示功能實現(xiàn)

3.1?效果展示

3.2?數(shù)據(jù)庫實現(xiàn)

1. 創(chuàng)建數(shù)據(jù)庫

類名:(MyDatabaseHelper)

class MyDatabaseHelper(

??? private val mContext: Context, name: String?,

??? factory: CursorFactory?, version: Int

) :

??? SQLiteOpenHelper(mContext, name, factory, version) {

??? override fun onCreate(db: SQLiteDatabase) {

??????? db.execSQL(CREATE)

??????? //Toast.makeText(mContext, "Create succeeded", Toast.LENGTH_SHORT).show()

??? }



??? override fun onUpgrade(db: SQLiteDatabase, oldVersion: Int, newVersion: Int) {}

??? // TODO 創(chuàng)建數(shù)據(jù)庫后,對數(shù)據(jù)庫的操作

??? // sql中Constant是用來存放一些關于數(shù)據(jù)庫的常量的類

??? // 類型有:Integer、text文本、varchar(n)、real浮點型、blob二進制類型

??? companion object {

??????? const val CREATE =? "create table temp(_id integer primary key autoincrement,Home text,Date text,time text,temperatures real,hum real)"

??? }





??? fun deleteDatabase(context: Context, databaseName: String?): Boolean {

??????? return context.deleteDatabase(databaseName)

??? }

}

2. 數(shù)據(jù)庫的使用

(1)實例化

private var dbHelper: MyDatabaseHelper? = null



dbHelper = MyDatabaseHelper(this, "temperature.db", null, 1)(放到開始運行部分)

(2)創(chuàng)建數(shù)據(jù)庫

private fun sql() {

??????? dbHelper?.writableDatabase;

}

(3)刪除數(shù)據(jù)庫

????? private fun Detele(){

??????? dbHelper?.deleteDatabase(applicationContext, "temperature.db");

}

(4)插入數(shù)據(jù)

fun add(){



??????? val formatter = SimpleDateFormat("yyyy-MM-dd")

??????? val date: String = formatter.format(Date())

??????? /*

??????? * HH-mm-ss(24時制)

??????? * hh-mm-ss(12時制)

? ??????* */

??????? val formatte = SimpleDateFormat("HH:mm:ss")

??????? val time = formatte.format(Date())



??????? val db: SQLiteDatabase = dbHelper!!.writableDatabase

??????? val values = ContentValues()

??????? // 開始組裝第一條數(shù)據(jù)

??????? values.put("Home", (Math.random() * 100).toString())

??????? values.put("Date", date)

??????? values.put("time", time)

??????? values.put("temperatures", (Math.random() * 100).toFloat())

??????? values.put("hum", (Math.random() * 100).toFloat())

??????? db.insert("temp", null, values) // 插入第一條數(shù)據(jù)



??????? values.clear()



}

??(5)查詢數(shù)據(jù)

fun find(){

var sql : String = "select * from `temp` where `Date` = '2021-11-02';"

??????? val cursor: Cursor = db.rawQuery(sql,null)



??????? if (cursor.moveToFirst()) {

??????????? do {

??????????????? val name: String = cursor.getString(

??????????????????? cursor.getColumnIndex("Date")

??????????????? )

??????????????? val author: String = cursor.getString(

??????????? ????????cursor.getColumnIndex("time")

??????????????? )

??????????????? val pages: Float = cursor.getFloat(

??????????????????? cursor.getColumnIndex("temperatures")

??????????????? )

??????????????? Log.d("MainActivity", "book name is $name")

??????????? ????Log.d("MainActivity", "book author is $author")

??????????????? Log.d("MainActivity", "book pages is $pages")

??????????? } while (cursor.moveToNext())

??????? }

??????? cursor.close()

}

3.3布局代碼

<?xml version="1.0" encoding="utf-8"?>

<ScrollView

??? xmlns:android="http://schemas.android.com/apk/res/android"

??? xmlns:app="http://schemas.android.com/apk/res-auto"

??? android:layout_width="match_parent"

??? android:layout_height="match_parent"

??? >



??? <LinearLayout

??????? android:layout_width="match_parent"

??????? android:layout_height="match_parent"

??????? android:orientation="vertical">



??????? <androidx.appcompat.widget.Toolbar

??????????? android:background="@color/shape3"

??????????? android:id="@+id/toolbar"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="?actionBarSize"

??????????? android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"

??????????? app:title="SeriaPortHome"

??????????? app:titleTextColor="@android:color/white"

??????????? >



??????? </androidx.appcompat.widget.Toolbar>



??????? <androidx.cardview.widget.CardView

??????????? style="@style/CardViews"

??????????? app:cardCornerRadius="22dp">

??????????? <LinearLayout

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="wrap_content"

??????????????? android:gravity="center_vertical"

??????????????? android:layout_marginLeft="20dp">

??????????????? <TextView

??????????????????? android:layout_width="66dp"

?????????????? ?????android:layout_height="wrap_content"

??????????????????? android:layout_marginTop="12dp"

??????????????????? android:layout_marginBottom="12dp"

??????????????????? android:alpha="0.4"

??????????????????? android:text="串口號"

??????????????????? android:gravity="center"

??????????????????? android:textColor="@color/black"

??????????????????? android:textSize="14sp" />



??????????????? <EditText

??????????????????? android:layout_weight="1"

??????????????????? android:id="@+id/EditText1"

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="match_parent"

??????????????????? android:background="@null"

??????????????????? android:hint="無"

????????? ??????????android:inputType="number"

??????????????????? android:textColor="@color/shape1"

??????????????????? android:textSize="14sp"

??????????????????? android:layout_marginLeft="14dp" />



??????????????? <Spinner

??????????????????? android:id="@+id/sp_serial"

??????????????????? android:layout_width="100dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginStart="8dp"

??????????????????? android:layout_marginEnd="15dp">

??????????????? </Spinner>



?????? ?????</LinearLayout>

??????? </androidx.cardview.widget.CardView>

??????? <androidx.cardview.widget.CardView

??????????? style="@style/CardViews"

??????????? app:cardCornerRadius="22dp">

??????????? <LinearLayout

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="wrap_content"

??????????????? android:gravity="center_vertical"

??????????????? android:layout_marginLeft="20dp">



??????????????? <TextView

??????????????????? android:layout_width="66dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginTop="12dp"

??????????????????? android:layout_marginBottom="12dp"

??????????????????? android:alpha="0.4"

??????????????????? android:gravity="center"

??????????????????? android:text="波特率"

??????????????????? android:textColor="@color/black"

??????????????????? android:textSize="14sp" />



??????????????? <EditText

??????????????????? android:id="@+id/EditText2"

??????????????????? android:layout_weight="1"

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="match_parent"

??????????????????? android:background="@null"

??????????????????? android:hint="無"

??????????????????? android:inputType="number"

??????????????????? android:textColor="@color/shape1"

??????????????????? android:textSize="14sp"

??????????????????? android:layout_marginLeft="14dp" />





??????????????? <Spinner

??????????????????? android:id="@+id/sp_bote"

??????????????????? android:layout_width="100dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginStart="8dp"

??????????????????? android:layout_marginEnd="15dp">

??????????????? </Spinner>



??????????? </LinearLayout>

??????? </androidx.cardview.widget.CardView>



??????? <LinearLayout

??????????? android:layout_width="match_parent"

??????????? android:layout_height="wrap_content"

??????????? android:gravity="center"

??????????? android:layout_marginTop="20dp"

??????????? android:layout_marginBottom="25dp"



??????????? android:orientation="horizontal">

??????????? <Button

??????????????? android:id="@+id/open"

??????????????? android:layout_width="wrap_content"

?? ?????????????android:layout_height="44dp"

??????????????? android:background="@drawable/shape_bt"

??????????????? android:gravity="center"

??????????????? android:text="打開串口"



??????????????? android:textColor="@android:color/white"

??????????????? android:textSize="@dimen/sp_14" />

??????????? <View

??????????????? android:layout_width="100dp"

??????????????? android:layout_height="match_parent"

??????????????? >

??????????? </View>

??????????? <Button

??????????????? android:id="@+id/SimulateData"

??????????????? android:layout_width="wrap_content"

??????????????? android:layout_height="44dp"

??????????????? android:background="@drawable/shape_bt"

??????????????? android:gravity="center"

??????????????? android:text="模擬數(shù)據(jù)"

??????????????? android:textColor="@android:color/white"

??????????????? android:textSize="@dimen/sp_14" />

??????? </LinearLayout>

??????? <com.github.mikephil.charting.charts.LineChart

??????????? android:id="@+id/dynamic_chart1"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="380dp"/>



??????? <Button

??????????? android:layout_width="match_parent"

??????????? android:layout_height="wrap_content"

??????????? android:id="@+id/addEntry"



??????????? android:text="隨機數(shù)據(jù)"

??????????? />

??? </LinearLayout>

</ScrollView>

3.4 Activity實現(xiàn)代碼

1.實列化以及局部數(shù)據(jù)

//串口

??? private var serialPortFinder: SerialPortFinder? = null

??? private var serialHelper: SerialHelper? = null

??? //曲線

??? private var dynamicLineChartManager1: DynamicLineChartManager? = null

??? private val list: MutableList<Float> = ArrayList() //數(shù)據(jù)集合

??? private val names: MutableList<String> = ArrayList() //折線名字集合

private val colour: MutableList<Int> = ArrayList() //折線顏色集合

//線程使用

private val mHandler = Handler()

2.串口實現(xiàn)函數(shù)以及數(shù)據(jù)跟新

/*

??? * TODO 串口使用初始化

??? * */

?private fun openSerialPort(){



??????? serialPortFinder = SerialPortFinder()

??????? serialHelper = object : SerialHelper() {

??????????? override fun onDataReceived(comBean: ComBean) {

??????????????? runOnUiThread {

??????????????????? /*

??????????????????? * TODO 獲取串口數(shù)據(jù)已經(jīng)保存數(shù)據(jù)

??????????????????? *? */

??????????????????? val home =

??????????????????????? ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec)).toString().substring(0, 2)

??????????????????? val tem =

??????????????????????? ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec)).toString().substring(5, 9)

??????????????????? val hum =

? ??????????????????????ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec)).toString().substring(12, 16)



??????????????????? when(home.toInt()) {

??????????????????????? 1 -> {

??????????????????????????? list.add(tem.toFloat())

??????????? ????????????????list.add(hum.toFloat())

??????????????????????????? dynamicLineChartManager1!!.addEntry(list)

??????????????????????????? list.clear()

??????????????????????? }

??????????????????????? 2 -> LogUtil.d("home","2")

??????????????????????? 3 -> LogUtil.d("home","3")

??????????????????????? 4 -> LogUtil.d("home","4")

??????????????????????? else -> {

??????????????????????? }

??????????????????? }

??????????????? }

??????????? }

??????? }

??????? //獲取串口地址

??????? val ports = serialPortFinder!!.allDevicesPath

??????? //設置波特率地址

??????? val botes = arrayOf(

??????????? "0",

??????????? "50",

??????????? "75",

??????????? "110",

??????????? "134",

??????????? "150",

??????????? "200",

??????????? "300",

?????? ?????"600",

??????????? "1200",

??????????? "1800",

??????????? "2400",

??????????? "4800",

??????????? "9600",

??????????? "19200",

??????????? "38400",

??????????? "57600",

??????????? "115200",

??????????? "230400",

??????????? "460800",

??????????? "500000",

??????????? "576000",

??????????? "921600",

??????????? "1000000",

??????????? "1152000",

??????????? "1500000",

??????????? "2000000",

??????????? "2500000",

??????????? "3000000",

??????????? "3500000",

??????????? "4000000"

??????? )

??????? val spAdapter = SpAdapter(this)

??????? /*

???????? * TODO 適配下拉列表(串口地址)

??????? * */

??????? spAdapter.setDatas(ports)

??????? binding.spSerial.adapter = spAdapter

??????? binding.spSerial.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {

??????????? override fun onItemSelected(

??????????????? parent: AdapterView<*>?,

??????????????? view: View,

??????????????? position: Int,

??????????????? id: Long

??????????? ) {

??????????????? serialHelper?.close()

??????????????? serialHelper?.port = ports[position]

??????????????? binding.EditText1.setText(ports[position])

??????????????? binding.open.text = "關閉串口"

??????????????? //btOpen.setEnabled(true)

??????????? }



??????????? override fun onNothingSelected(parent: AdapterView<*>?) {}

??????? }

??????? /*

???????? * TODO 適配下拉列表(波特率地址)

??????? * */

??????? val spAdapter2 = SpAdapter(this)

??????? spAdapter2.setDatas(botes)

??????? binding.spBote.adapter = spAdapter2



??????? binding.spBote.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {

??????????? override fun onItemSelected(

??????????????? parent: AdapterView<*>?,

??????????????? view: View,

??????????????? position: Int,

??????????????? id: Long

??????????? ) {

??????????????? serialHelper?.close()

??????????????? serialHelper?.setBaudRate(botes[position])

??????????????? binding.EditText2.setText(botes[position])

??????????????? binding.open.text = "關閉串口"

??????????????? // btOpen.setEnabled(true)

??????????? }



??????????? override fun onNothingSelected(parent: AdapterView<*>?) {}

??????? }

??? }

3.模擬數(shù)據(jù)跟新

/*

??? * TODO 線程更新處理

??? * */

??? private val mRunnable: Runnable = object : Runnable {

??????? override fun run() {

??????????? dynamicLineChartManager1?.addEntry((Math.random() * 100).toFloat())

??????????? // 每3秒執(zhí)行一次

??????????? mHandler.postDelayed(this, 3000) //給自己發(fā)送消息,自運行

??????? }

}

4.開啟該線程

//模擬數(shù)據(jù)(simulated data)

??????? binding.SimulateData.setOnClickListener{

??????????? //啟動線程

??????????? mHandler.post(mRunnable);

??????????? //設置模擬數(shù)據(jù)不能被點擊

??????????? binding.SimulateData.isEnabled = false

??????? }

5.退出時關閉模擬線程

override fun onDestroy() {

??????? //將線程銷毀掉

??????? mHandler.removeCallbacks(mRunnable)

??????? super.onDestroy()

??? }

四.多個房間溫度圖表顯示功能實現(xiàn)

4.1?效果展示

4.2布局代碼

<?xml version="1.0" encoding="utf-8"?>

<ScrollView

??? xmlns:android="http://schemas.android.com/apk/res/android"

??? xmlns:app="http://schemas.android.com/apk/res-auto"

??? android:layout_width="match_parent"

??? android:layout_height="match_parent"

??? >



??? <LinearLayout

??????? android:layout_width="match_parent"

??????? android:layout_height="match_parent"

??????? android:orientation="vertical">



??????? <androidx.appcompat.widget.Toolbar

??????????? android:background="@color/shape3"

??????????? android:id="@+id/toolbar"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="?actionBarSize"

??????????? android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"

??????????? app:title="SeriaPortHome"

??????????? app:titleTextColor="@android:color/white"

??????????? >



??????? </androidx.appcompat.widget.Toolbar>



??????? <androidx.cardview.widget.CardView

??????????? style="@style/CardViews"

??????????? app:cardCornerRadius="22dp">

??????????? <LinearLayout

??????????????? android:layout_width="match_parent"

?????????? ?????android:layout_height="wrap_content"

??????????????? android:gravity="center_vertical"

??????????????? android:layout_marginLeft="20dp">

??????????????? <TextView

??????????????????? android:layout_width="66dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginTop="12dp"

??????????????????? android:layout_marginBottom="12dp"

??????????????????? android:alpha="0.4"

??????????????????? android:text="串口號"

??????????????????? android:gravity="center"

??????? ????????????android:textColor="@color/black"

??????????????????? android:textSize="14sp" />



??????????????? <EditText

??????????????????? android:layout_weight="1"

??????????????????? android:id="@+id/EditText1"

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="match_parent"

??????????????????? android:background="@null"

??????????????????? android:hint="無"

??????????????????? android:inputType="number"

??????????????????? android:textColor="@color/shape1"

??????????????????? android:textSize="14sp"

??????????????????? android:layout_marginLeft="14dp" />



??????????????? <Spinner

??????????????????? android:id="@+id/sp_serial"

??????????????????? android:layout_width="100dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginStart="8dp"

??????????????????? android:layout_marginEnd="15dp">

??????????????? </Spinner>



??????????? </LinearLayout>

??????? </androidx.cardview.widget.CardView>

??????? <androidx.cardview.widget.CardView

??????????? style="@style/CardViews"

??????????? app:cardCornerRadius="22dp">

??????????? <LinearLayout

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="wrap_content"

??????????????? android:gravity="center_vertical"

??????????????? android:layout_marginLeft="20dp">



??????????????? <TextView

??????????????????? android:layout_width="66dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginTop="12dp"

??????????????????? android:layout_marginBottom="12dp"

??????????????????? android:alpha="0.4"

??????????????????? android:gravity="center"

??????????????????? android:text="波特率"

??????????????????? android:textColor="@color/black"

??????????????????? android:textSize="14sp" />



??????????????? <EditText

??????????????????? android:id="@+id/EditText2"

??????????????????? android:layout_weight="1"

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="match_parent"

??????????????????? android:background="@null"

??????????????????? android:hint="無"

??????????????????? android:inputType="number"

??????? ????????????android:textColor="@color/shape1"

??????????????????? android:textSize="14sp"

??????????????????? android:layout_marginLeft="14dp" />





??????????????? <Spinner

??????????????????? android:id="@+id/sp_bote"

??????????????????? android:layout_width="100dp"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginStart="8dp"

??????????????????? android:layout_marginEnd="15dp">

??????????????? </Spinner>



??????????? </LinearLayout>

??????? </androidx.cardview.widget.CardView>



??????? <LinearLayout

??????????? android:layout_width="match_parent"

??????????? android:layout_height="wrap_content"

??????????? android:gravity="center"

??????????? android:layout_marginTop="20dp"

??????????? android:layout_marginBottom="25dp"



??????????? android:orientation="horizontal">

??????????? <Button

??????????????? android:id="@+id/open"

??????????????? android:layout_width="wrap_content"

??????????????? android:layout_height="44dp"

??????????????? android:background="@drawable/shape_bt"

??????????????? android:gravity="center"

??????????????? android:text="打開串口"



??????????????? android:textColor="@android:color/white"

??????????????? android:textSize="@dimen/sp_14" />

? ??????????<View

??????????????? android:layout_width="100dp"

??????????????? android:layout_height="match_parent"

??????????????? >

??????????? </View>

??????????? <Button

??????????????? android:id="@+id/SimulateData"

??????????????? android:layout_width="wrap_content"

??????????????? android:layout_height="44dp"

??????????????? android:background="@drawable/shape_bt"

??????????????? android:gravity="center"

??????????????? android:text="模擬數(shù)據(jù)"

??????????????? android:textColor="@android:color/white"

??????????????? android:textSize="@dimen/sp_14" />

??????? </LinearLayout>



??????? <com.github.mikephil.charting.charts.LineChart

??????????? android:id="@+id/dynamic_chart1"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="380dp"/>



??????? <com.github.mikephil.charting.charts.LineChart

??????????? android:id="@+id/dynamic_chart2"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="380dp"/>



??????? <com.github.mikephil.charting.charts.LineChart

??????????? android:id="@+id/dynamic_chart3"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="380dp"/>

???????

??????? <com.github.mikephil.charting.charts.LineChart

??????????? android:id="@+id/dynamic_chart4"

??????????? android:layout_width="match_parent"

??????????? android:layout_height="380dp"/>

??????? <Button

??????????? android:layout_width="match_parent"

??????????? android:layout_height="wrap_content"

??????????? android:id="@+id/addEntry"



??????????? android:text="隨機數(shù)據(jù)"

??????????? />



??? </LinearLayout>

</ScrollView>

4.3 Activity實現(xiàn)代碼

1.實列化以及局部數(shù)據(jù)

//串口

??? private var serialPortFinder: SerialPortFinder? = null

??? private var serialHelper: SerialHelper? = null

??? //曲線

??? private var dynamicLineChartManager1: DynamicLineChartManager? = null

??? private var dynamicLineChartManager2: DynamicLineChartManager? = null

??? private var dynamicLineChartManager3: DynamicLineChartManager? = null

??? private var dynamicLineChartManager4: DynamicLineChartManager? = null

??? //房間數(shù)據(jù)集

??? private val list: MutableList<Float> = ArrayList() //數(shù)據(jù)集合

??? private val list2: MutableList<Float> = ArrayList() //數(shù)據(jù)集合

??? private val list3: MutableList<Float> = ArrayList() //數(shù)據(jù)集合

??? private val list4: MutableList<Float> = ArrayList() //數(shù)據(jù)集合



??? private val names: MutableList<String> = ArrayList() //折線名字集合

??? private val colour: MutableList<Int> = ArrayList() //折線顏色集合

??? //數(shù)據(jù)庫

??? private var dbHelper: MyDatabaseHelper? = null

private val mHandler = Handler()



2.串口實現(xiàn)函數(shù)以及數(shù)據(jù)跟新

/*

??? * TODO 串口使用初始化

??? * */

??? private fun openSerialPort(){

??????? serialPortFinder = SerialPortFinder()

??????? serialHelper = object : SerialHelper() {

??????????? override fun onDataReceived(comBean: ComBean) {

??????? ????????runOnUiThread {

??????????????????? /*

??????????????????? * TODO 獲取串口數(shù)據(jù)已經(jīng)保存數(shù)據(jù)

??????????????????? *? */

??????????????????? val formatter = SimpleDateFormat("yyyy-MM-dd")

??????????????????? val date: String = formatter.format(Date())

??????????? ????????/*

??????????????????? * HH-mm-ss(24時制)

??????????????????? * hh-mm-ss(12時制)

??????????????????? * */

??????????????????? val formatte = SimpleDateFormat("HH:mm:ss")

??????????????????? val time = formatte.format(Date())



??????????????????? val db: SQLiteDatabase = dbHelper!!.writableDatabase



??????????????????? val home =

??????????????????????? ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec)).toString().substring(0, 2)

??????????????????? val tem =

??????????????????????? ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec)).toString().substring(5, 9)

??????????????????? val hum =

??????????????????????? ByteUtil.hexStringToString(ByteUtil.bytesToHexString(comBean.bRec)).toString().substring(12, 16)



??????????????????? when(home.toInt()) {

??????????????????????? 1 -> {

??????????????????????????? val values = ContentValues()

??????????????????????????? //保存到數(shù)據(jù)庫中

??????????????????????????? values.put("Home",home.toInt())

??????????????????????????? values.put("Date", date)

??????????????????????????? values.put("time", time)

??????????????????????????? values.put("temperatures", tem)

??????????????????????????? values.put("hum", hum)

?????????????????????? ?????db.insert("temp", null, values) // 插入第一條數(shù)據(jù)

??????????????????????????? values.clear()

??????????????????????????? //更新列表

??????????????????????????? list.add(tem.toFloat())

??????????????????????????? list.add(hum.toFloat())

????????????????????????? ??dynamicLineChartManager1!!.addEntry(list)

??????????????????????????? list.clear()

??????????????????????? }

??????????????????????? 2 -> {

??????????????????????????? val values = ContentValues()

??????????????????????????? //保存到數(shù)據(jù)庫中

?????????????????? ?????????values.put("Home",home.toInt())

??????????????????????????? values.put("Date", date)

??????????????????????????? values.put("time", time)

??????????????????????????? values.put("temperatures", tem)

??????????????????????????? values.put("hum", hum)

??????????????????????????? db.insert("temp", null, values) // 插入第一條數(shù)據(jù)

??????????????????????????? values.clear()



??????????????????????????? list2.add(tem.toFloat())

??????????????????????????? list2.add(hum.toFloat())

??????????????????????????? dynamicLineChartManager2!!.addEntry(list2)

??????????????????????????? list2.clear()

??????????????????????? }

??????????????????????? 3 -> {

??????????????????????????? val values = ContentValues()

???????????? ???????????????//保存到數(shù)據(jù)庫中

??????????????????????????? values.put("Home",home.toInt())

??????????????????????????? values.put("Date", date)

??????????????????????????? values.put("time", time)

??????????????????????????? values.put("temperatures", tem)

???? ???????????????????????values.put("hum", hum)

??????????????????????????? db.insert("temp", null, values) // 插入第一條數(shù)據(jù)

??????????????????????????? values.clear()



??????????????????????????? list3.add(tem.toFloat())

??????????????????????????? list3.add(hum.toFloat())

??????????????????????????? dynamicLineChartManager3!!.addEntry(list3)

??????????????????????????? list3.clear()

??????????????????????? }

??????????????????????? 4 -> {

??????????????????????????? val values = ContentValues()

????????????????? ??????????//保存到數(shù)據(jù)庫中

??????????????????????????? values.put("Home",home.toInt())

??????????????????????????? values.put("Date", date)

??????????????????????????? values.put("time", time)

??????????????????????????? values.put("temperatures", tem)

??????????????????????????? values.put("hum", hum)

??????????????????????????? db.insert("temp", null, values) // 插入第一條數(shù)據(jù)

??????????????????????????? values.clear()



??????????????????????????? list4.add(tem.toFloat())

??????????????????????????? list4.add(hum.toFloat())

??????????????????????????? dynamicLineChartManager4!!.addEntry(list4)

??????????????????????????? list4.clear()

??????????????????????? }

??????????????????????? else -> {

?????? ?????????????????}

??????????????????? }



??????????????? }

??????????? }

??????? }

??????? //獲取串口地址

??????? val ports = serialPortFinder!!.allDevicesPath

??????? //設置波特率地址

??????? val botes = arrayOf(

??????????? "0",

??????????? "50",

??????????? "75",

??????????? "110",

??????????? "134",

??????????? "150",

??????????? "200",

??????????? "300",

??????????? "600",

??????????? "1200",

??????????? "1800",

??????????? "2400",

??????????? "4800",

??????????? "9600",

??????????? "19200",

??????????? "38400",

??????????? "57600",

??????????? "115200",

??????????? "230400",

??????????? "460800",

??????????? "500000",

??????????? "576000",

??????????? "921600",

??????????? "1000000",

??????????? "1152000",

??????????? "1500000",

??????????? "2000000",

??????????? "2500000",

??????????? "3000000",

??????????? "3500000",

??????????? "4000000"

??????? )

??????? val spAdapter = SpAdapter(this)

??????? /*

???????? * TODO 適配下拉列表(串口地址)

??????? * */

??????? spAdapter.setDatas(ports)

??????? binding.spSerial.adapter = spAdapter

??????? binding.spSerial.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {

??????????? override fun onItemSelected(

??????????????? parent: AdapterView<*>?,

??????????????? view: View,

??????????????? position: Int,

??????????????? id: Long

??????????? ) {

??????????????? serialHelper?.close()

??????????????? serialHelper?.port = ports[position]

??????????????? binding.EditText1.setText(ports[position])

???? ???????????binding.open.text = "關閉串口"

??????????????? //btOpen.setEnabled(true)

??????????? }



??????????? override fun onNothingSelected(parent: AdapterView<*>?) {}

??????? }

??????? /*

???????? * TODO 適配下拉列表(波特率地址)

??????? * */

??????? val spAdapter2 = SpAdapter(this)

??????? spAdapter2.setDatas(botes)

??????? binding.spBote.adapter = spAdapter2



??????? binding.spBote.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {

??????????? override fun onItemSelected(

??????????????? parent: AdapterView<*>?,

??????????????? view: View,

??????????????? position: Int,

??????????????? id: Long

??????????? ) {

??????????????? serialHelper?.close()

??????????????? serialHelper?.setBaudRate(botes[position])

??????????????? binding.EditText2.setText(botes[position])

??????????????? binding.open.text = "關閉串口"

??????????????? // btOpen.setEnabled(true)

??????????? }



??????????? override fun onNothingSelected(parent: AdapterView<*>?) {}

??????? }

??? }

3.模擬數(shù)據(jù)跟新

/*

??? * TODO 線程更新處理

??? * */

??? private val mRunnable: Runnable = object : Runnable {

??????? override fun run() {

??????????? dynamicLineChartManager1?.addEntry((Math.random() * 100).toFloat())

??????????? dynamicLineChartManager2?.addEntry((Math.random() * 100).toFloat())

??????????? dynamicLineChartManager3?.addEntry((Math.random() * 100).toFloat())

??????????? dynamicLineChartManager4?.addEntry((Math.random() * 100).toFloat())

??????????? // 每3秒執(zhí)行一次

??????????? mHandler.postDelayed(this, 3000) //給自己發(fā)送消息,自運行

??????? }

??? }4.開啟該線程

//模擬數(shù)據(jù)(simulated data)

??????? binding.SimulateData.setOnClickListener{

??????????? //啟動線程

??????????? mHandler.post(mRunnable);

??????????? //設置模擬數(shù)據(jù)不能被點擊

??????????? binding.SimulateData.isEnabled = false

??????? }

5.退出時關閉模擬線程

override fun onDestroy() {

??????? //將線程銷毀掉

??????? mHandler.removeCallbacks(mRunnable)

??????? super.onDestroy()

??? }

五.歷史數(shù)據(jù)分析圖顯示功能實現(xiàn)

5.1?效果展示

5.2布局代碼

<?xml version="1.0" encoding="utf-8"?>

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

??? xmlns:app="http://schemas.android.com/apk/res-auto"

??? android:layout_width="match_parent"

??? android:layout_height="match_parent"

??? android:orientation="vertical">



??? <androidx.appcompat.widget.Toolbar

??????? android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"

??????? android:background="@color/shape3"

??????? android:id="@+id/toolbar"

??????? android:layout_width="match_parent"

??????? android:layout_height="?actionBarSize"

??????? app:title="History Data"

??????? app:titleTextColor="@android:color/white"

??????? >



??? </androidx.appcompat.widget.Toolbar>



??? <FrameLayout

??????? xmlns:android="http://schemas.android.com/apk/res/android"

??????? xmlns:tools="http://schemas.android.com/tools"

??????? xmlns:fab="http://schemas.android.com/apk/res-auto"

??????? android:id="@+id/main_layout"

??????? android:layout_width="match_parent"

??????? android:layout_height="match_parent"

??????? >

??????? <LinearLayout

??????????? android:layout_width="match_parent"

??????????? android:layout_height="match_parent"

??????????? android:orientation="vertical">

??????????? <androidx.cardview.widget.CardView

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="wrap_content"

??????????????? android:layout_marginStart="30dp"

??????????????? android:layout_marginTop="16dp"

??????????????? android:layout_marginEnd="30dp"

??????????????? android:background="@android:color/white"

??????????????? app:cardCornerRadius="22dp">



??????????????? <LinearLayout

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="wrap_content"

??????????????????? android:layout_marginStart="20dp"

??????????????????? android:layout_marginEnd="20dp"

??????????????????? android:gravity="center_vertical">



??????????????????? <TextView

??????????????????????? android:layout_width="66dp"

??????????????????????? android:layout_height="wrap_content"

??????????????????????? android:layout_marginTop="12dp"

??????????????????????? android:layout_marginBottom="12dp"

??????????????????????? android:alpha="0.4"

??????????????????????? android:text="開始日期"

??????????????????????? android:textColor="@color/black"

??????????????????????? android:textSize="14sp" />



??????????????????? <TextView

??????????????????????? android:id="@+id/start_text"

??? ????????????????????android:layout_width="match_parent"

??????????????????????? android:layout_height="match_parent"

??????????????????????? android:gravity="center"



??????????????????????? android:background="@null"

??????????????????????? android:hint="yyyy-MM-ddHH:mm:ss"

??????????????????????? android:inputType="number"

??????????????????????? android:textColor="@color/colorPrimary"

??????????????????????? android:textSize="14sp"

??????????????????????? android:layout_marginLeft="14dp" />

???????????? ???</LinearLayout>

??????????? </androidx.cardview.widget.CardView>

??????????? <androidx.cardview.widget.CardView

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="wrap_content"

??????????????? android:layout_marginStart="30dp"

??????????????? android:layout_marginTop="16dp"

??????????????? android:layout_marginEnd="30dp"

??????????????? android:layout_marginBottom="16dp"

??????????????? android:background="@android:color/white"

??????????????? app:cardCornerRadius="22dp">



??????????????? <LinearLayout

??????????????????? android:layout_width="match_parent"

??????????????????? android:layout_height="wrap_content"

???????? ???????????android:layout_marginStart="20dp"

??????????????????? android:layout_marginEnd="20dp"

??????????????????? android:gravity="center_vertical">



??????????????????? <TextView

??????????????????????? android:layout_width="66dp"

???????????????????? ???android:layout_height="wrap_content"

??????????????????????? android:layout_marginTop="12dp"

??????????????????????? android:layout_marginBottom="12dp"

??????????????????????? android:alpha="0.4"

??????????????????????? android:text="結(jié)束日期"

???????????? ???????????android:textColor="@color/black"

??????????????????????? android:textSize="14sp" />



??????????????????? <TextView

??????????????????????? android:id="@+id/end_text"

??????????????????????? android:layout_width="match_parent"

?????????????????? ?????android:layout_height="match_parent"



??????????????????????? android:background="@null"

??????????????????????? android:gravity="center"

??????????????????????? android:hint="yyyy-MM-ddHH:mm:ss"

??????????????????????? android:inputType="number"

??????????????????????? android:textColor="@color/colorPrimary"

??????????????????????? android:textSize="14sp"

??????????????????????? android:layout_marginLeft="14dp" />

??????????????? </LinearLayout>

??????????? </androidx.cardview.widget.CardView>



??????????? <com.github.mikephil.charting.charts.LineChart

??????????????? android:id="@+id/dynamic_chart1"

??????????????? android:layout_marginTop="20dp"

??????????????? android:layout_width="match_parent"

??????????????? android:layout_height="400dp"/>

??????????? <TextView

??????????????? android:id="@+id/time"

??????????????? android:layout_width="wrap_content"

??????????????? android:layout_height="wrap_content"

??????????????? android:layout_marginTop="12dp"

??????????????? android:layout_marginBottom="12dp"

??????????????? android:alpha="0.4"

??????????????? android:layout_gravity="center"

??????????????? android:text="等待"

??????????????? android:textColor="@color/black"

??????????????? android:textSize="14sp" />

??????? </LinearLayout>

??? </FrameLayout>

</LinearLayout>

5.3 Activity實現(xiàn)代碼

1.實列化以及局部數(shù)據(jù)

private var dynamicLineChartManager1: DynamicLineChartManager? = null



??? private val names: MutableList<String> = ArrayList() //折線名字集合

??? private var dbHelper: MyDatabaseHelper? = null

??? private val colour: MutableList<Int> = ArrayList() //折線顏色集合

??? private val list: MutableList<Float> = ArrayList() //數(shù)據(jù)集合

??? private var endData: String? = null

??? private var startData: String? = null

2. 開始時間選擇

//開始時間選擇

??????? binding.startText.setOnClickListener {

??????????? val startTime = "1990-01-01 00:00:00"

??????????? val endTime = "2100-01-01 12:00:00"

??????????? val formatStr = DateUtil.Y_M_D_H_M_S

??????????? val type = booleanArrayOf(true, true, true, true, true, true)

??????????? val currentTime = DateUtil.convertOtherFormat(DateUtil.getCurrentDateTime(), DateUtil.Y_M_D, DateUtil.Y_M_D_H_M_S)

????? ??????PickerViewUtil.selectDateTime(

??????????????? this, { date: Date?, v1: View? ->

??????????????????? startData = DateUtil.dateToString(date, "yyyy-MM-ddHH:mm:ss")

??????????????????? val sb: StringBuilder = StringBuilder(startData)

????????????????? ??Log.d("字符串:", "" + sb.toString() + " 字符長度:" + sb.length)

??????????????????? val string =sb.toString().substring(0, 10)

??????????????????? startData = string

??????????????????? Log.d("字符串:", "" + startData)

??????????????????? binding.startText.text = DateUtil.date2String(date!!, formatStr)

??????????????? }, currentTime, startTime, endTime, formatStr,

??????????????? "選擇日期時間", "取消", "確定", type

??????????? )



??????????? //accessUrlRxJava(UrlConstant.ONE_NET_URL)

??????? }

3. 結(jié)束時間選擇

? //結(jié)束時間選擇

??????? binding.endText.setOnClickListener {

??????????? val startTime = "1990-01-01 00:00:00"

??????????? var endTime = "2100-01-01 12:00:00"

??????????? val formatStr = DateUtil.Y_M_D_H_M_S

??????????? val type = booleanArrayOf(true, true, true, true, true, true)

??????????? val currentsTime = DateUtil.convertOtherFormat(DateUtil.getCurrentDateTime(), DateUtil.Y_M_D, DateUtil.Y_M_D_H_M_S)

???? ???????PickerViewUtil.selectDateTime(

??????????????? this, OnTimeSelectListener { date: Date?, v1: View? ->

??????????????????? endData = DateUtil.dateToString(date, "yyyy-MM-ddHH:mm:ss")

??????????????????? val sb: StringBuilder = StringBuilder(endData)

??????????????????? Log.d("字符串:", "" + sb.toString() + " 字符長度:" + sb.length)

??????????????????? val string = sb.substring(0, 10)

??????????????????? endData = string.toString()

??????????????????? Log.d("字符串:", "" + endData)

??????????????????? binding.endText.text = DateUtil.date2String(date!!, formatStr)

??????????????????? binding.time.text = "等待中....!"

??????????????????? Handler(Looper.getMainLooper()).postDelayed({

??????????????????????? /**

???????????????????????? * 數(shù)據(jù)初始化(200毫秒)AddDeviceActivity

???????????????????????? * */

??????????????????????? findHistoryData()

??????????????????? }, 300)



??????????????? }, currentsTime, startTime, endTime, formatStr,

??????????????? "選擇日期時間", "取消", "確定", type

??????????? )



??????????? //accessUrlRxJava(UrlConstant.ONE_NET_URL)

??????? }

4.數(shù)據(jù)庫查找數(shù)據(jù)顯示

private fun findHistoryData(){

??????? val db: SQLiteDatabase = dbHelper!!.writableDatabase

??????? val sql : String = "select * from `temp` where `Date` Between '$startData' and '$endData';"

??????? val cursor: Cursor = db.rawQuery(sql,null)

??????? if (cursor.moveToFirst()) {

??????? ????do {

??????????????? val Datas: String = cursor.getString(

??????????????????? cursor.getColumnIndex("Date")

??????????????? )

??????????????? val times: String = cursor.getString(

??????????????????? cursor.getColumnIndex("time")

??????????????? )

?? ?????????????val temp: Float = cursor.getFloat(

??????????????????? cursor.getColumnIndex("temperatures")

??????????????? )

??????????????? val hum: Float = cursor.getFloat(

??????????????????? cursor.getColumnIndex("hum")

??????????????? )

?????????????? ?list.add(temp.toFloat())

??????????????? list.add(hum.toFloat())

??????????????? dynamicLineChartManager1!!.HistoryAddEntry(list)

??????????????? list.clear()

??????????? } while (cursor.moveToNext())

??????? }

??????? cursor.close()

??????? Handler(Looper.getMainLooper()).postDelayed({

??????????? /**

???????????? * 數(shù)據(jù)初始化(200毫秒)AddDeviceActivity

???????????? * */

??????????? binding.time.text = "數(shù)據(jù)加載完成!"

??????? }, 200)

??? }

End

聯(lián)系方式 微信號:13648103287

  • 聯(lián)系方式.docx

推薦器件

更多器件
器件型號 數(shù)量 器件廠商 器件描述 數(shù)據(jù)手冊 ECAD模型 風險等級 參考價格 更多信息
TJA1051T,118 1 NXP Semiconductors TJA1051 - High-speed CAN transceiver SOIC 8-Pin

ECAD模型

下載ECAD模型
$1.08 查看
TJA1051T/3/1J 1 NXP Semiconductors TJA1051 - High-speed CAN transceiver SOIC 8-Pin

ECAD模型

下載ECAD模型
$1.11 查看
KSZ9897RTXI 1 Microchip Technology Inc IC ETHERNET SWITCH 7PORT 128TQFP

ECAD模型

下載ECAD模型
$13.89 查看

相關推薦

電子產(chǎn)業(yè)圖譜

方案定制,程序設計方案、單片機程序設計與講解、APP定制開發(fā)。本公眾號致力于向讀者傳遞關于程序設計和開發(fā)的相關知識,并分享一些關于軟件開發(fā)的最佳實踐。如果您有什么問題或建議,請隨時聯(lián)系我們。我們將竭誠為您服務