HarmonyOS APP开发---“数据眼“健康追踪App,需要用到这个库

HarmonyOS APP开发---"数据眼"健康追踪App,需要用到这个库

做一个健康追踪 App,每天的步数、心率、睡眠时长要用图表展示------自己用 Canvas 画图表?太累了。@ohos/mpchart 覆盖 7 大图表类型,手势缩放、数据高亮、自定义样式开箱即用。
📦 仓库地址:https://gitcode.com/CPF-ApplicationTPC/ohos_mpchart | 安装:ohpm install @ohos/mpchart


写在前面

"数据眼"是一个健康追踪 App,核心功能是把传感器采集的健康数据可视化:

  • 步数走势:最近 7 天每天的步数 → 柱状图
  • 心率曲线:今天 24 小时心率变化 → 折线图
  • 睡眠分布:深睡/浅睡/清醒占比 → 饼状图
  • 能力评估:心肺/力量/柔韧/平衡多维评分 → 雷达图

这些图表如果自己用 Canvas 画,每个都得写几百行:画轴、画网格、画数据点、处理手势缩放、处理点击高亮......4 种图表就是 2000+ 行代码。

@ohos/mpchart 提供了 7 大图表类型(线形/柱状/饼状/蜡烛/气泡/雷达/瀑布),自带手势交互和数据高亮,配置化使用,几十行就能出图。

这篇文章聊什么

  1. 步数柱状图------最近 7 天步数对比
  2. 心率折线图------24 小时心率曲线 + 缩放
  3. 睡眠饼状图------深睡/浅睡/清醒占比

#mermaid-svg-MpcXP7Oa32EVeK7c{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}@keyframes edge-animation-frame{from{stroke-dashoffset:0;}}@keyframes dash{to{stroke-dashoffset:0;}}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-animation-slow{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 50s linear infinite;stroke-linecap:round;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-animation-fast{stroke-dasharray:9,5!important;stroke-dashoffset:900;animation:dash 20s linear infinite;stroke-linecap:round;}#mermaid-svg-MpcXP7Oa32EVeK7c .error-icon{fill:#552222;}#mermaid-svg-MpcXP7Oa32EVeK7c .error-text{fill:#552222;stroke:#552222;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-thickness-normal{stroke-width:1px;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-thickness-thick{stroke-width:3.5px;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-pattern-solid{stroke-dasharray:0;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-thickness-invisible{stroke-width:0;fill:none;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-pattern-dashed{stroke-dasharray:3;}#mermaid-svg-MpcXP7Oa32EVeK7c .edge-pattern-dotted{stroke-dasharray:2;}#mermaid-svg-MpcXP7Oa32EVeK7c .marker{fill:#333333;stroke:#333333;}#mermaid-svg-MpcXP7Oa32EVeK7c .marker.cross{stroke:#333333;}#mermaid-svg-MpcXP7Oa32EVeK7c svg{font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;}#mermaid-svg-MpcXP7Oa32EVeK7c p{margin:0;}#mermaid-svg-MpcXP7Oa32EVeK7c .label{font-family:"trebuchet ms",verdana,arial,sans-serif;color:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c .cluster-label text{fill:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c .cluster-label span{color:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c .cluster-label span p{background-color:transparent;}#mermaid-svg-MpcXP7Oa32EVeK7c .label text,#mermaid-svg-MpcXP7Oa32EVeK7c span{fill:#333;color:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c .node rect,#mermaid-svg-MpcXP7Oa32EVeK7c .node circle,#mermaid-svg-MpcXP7Oa32EVeK7c .node ellipse,#mermaid-svg-MpcXP7Oa32EVeK7c .node polygon,#mermaid-svg-MpcXP7Oa32EVeK7c .node path{fill:#ECECFF;stroke:#9370DB;stroke-width:1px;}#mermaid-svg-MpcXP7Oa32EVeK7c .rough-node .label text,#mermaid-svg-MpcXP7Oa32EVeK7c .node .label text,#mermaid-svg-MpcXP7Oa32EVeK7c .image-shape .label,#mermaid-svg-MpcXP7Oa32EVeK7c .icon-shape .label{text-anchor:middle;}#mermaid-svg-MpcXP7Oa32EVeK7c .node .katex path{fill:#000;stroke:#000;stroke-width:1px;}#mermaid-svg-MpcXP7Oa32EVeK7c .rough-node .label,#mermaid-svg-MpcXP7Oa32EVeK7c .node .label,#mermaid-svg-MpcXP7Oa32EVeK7c .image-shape .label,#mermaid-svg-MpcXP7Oa32EVeK7c .icon-shape .label{text-align:center;}#mermaid-svg-MpcXP7Oa32EVeK7c .node.clickable{cursor:pointer;}#mermaid-svg-MpcXP7Oa32EVeK7c .root .anchor path{fill:#333333!important;stroke-width:0;stroke:#333333;}#mermaid-svg-MpcXP7Oa32EVeK7c .arrowheadPath{fill:#333333;}#mermaid-svg-MpcXP7Oa32EVeK7c .edgePath .path{stroke:#333333;stroke-width:2.0px;}#mermaid-svg-MpcXP7Oa32EVeK7c .flowchart-link{stroke:#333333;fill:none;}#mermaid-svg-MpcXP7Oa32EVeK7c .edgeLabel{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-MpcXP7Oa32EVeK7c .edgeLabel p{background-color:rgba(232,232,232, 0.8);}#mermaid-svg-MpcXP7Oa32EVeK7c .edgeLabel rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-MpcXP7Oa32EVeK7c .labelBkg{background-color:rgba(232, 232, 232, 0.5);}#mermaid-svg-MpcXP7Oa32EVeK7c .cluster rect{fill:#ffffde;stroke:#aaaa33;stroke-width:1px;}#mermaid-svg-MpcXP7Oa32EVeK7c .cluster text{fill:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c .cluster span{color:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c div.mermaidTooltip{position:absolute;text-align:center;max-width:200px;padding:2px;font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:12px;background:hsl(80, 100%, 96.2745098039%);border:1px solid #aaaa33;border-radius:2px;pointer-events:none;z-index:100;}#mermaid-svg-MpcXP7Oa32EVeK7c .flowchartTitleText{text-anchor:middle;font-size:18px;fill:#333;}#mermaid-svg-MpcXP7Oa32EVeK7c rect.text{fill:none;stroke-width:0;}#mermaid-svg-MpcXP7Oa32EVeK7c .icon-shape,#mermaid-svg-MpcXP7Oa32EVeK7c .image-shape{background-color:rgba(232,232,232, 0.8);text-align:center;}#mermaid-svg-MpcXP7Oa32EVeK7c .icon-shape p,#mermaid-svg-MpcXP7Oa32EVeK7c .image-shape p{background-color:rgba(232,232,232, 0.8);padding:2px;}#mermaid-svg-MpcXP7Oa32EVeK7c .icon-shape .label rect,#mermaid-svg-MpcXP7Oa32EVeK7c .image-shape .label rect{opacity:0.5;background-color:rgba(232,232,232, 0.8);fill:rgba(232,232,232, 0.8);}#mermaid-svg-MpcXP7Oa32EVeK7c .label-icon{display:inline-block;height:1em;overflow:visible;vertical-align:-0.125em;}#mermaid-svg-MpcXP7Oa32EVeK7c .node .label-icon path{fill:currentColor;stroke:revert;stroke-width:revert;}#mermaid-svg-MpcXP7Oa32EVeK7c :root{--mermaid-font-family:"trebuchet ms",verdana,arial,sans-serif;} 步数
心率
睡眠
能力
传感器数据
数据处理
图表类型
BarChart 柱状图
LineChart 折线图
PieChart 饼状图
RadarChart 雷达图
手势缩放+点击高亮
渲染到 UI


第一步:安装

bash 复制代码
ohpm install @ohos/mpchart

无需任何权限(纯渲染组件)。


第二步:步数柱状图------最近 7 天

typescript 复制代码
import {
  BarChart, BarChartModel, BarData, BarDataSet, BarEntry,
  JArrayList, XAxis, XAxisPosition, YAxis, Description,
  OnChartValueSelectedListener, Highlight, EntryOhos
} from '@ohos/mpchart'

@Entry
@Component
struct StepsChartPage {
  private barChart: BarChart = new BarChart()
  private model: BarChartModel = new BarChartModel()

  aboutToAppear() {
    // 模拟最近 7 天步数
    const steps = [8234, 10245, 6789, 9876, 12034, 5678, 8901]
    const days = ['周一', '周二', '周三', '周四', '周五', '周六', '周日']

    const entries = new JArrayList<BarEntry>()
    steps.forEach((val, i) => entries.add(new BarEntry(i, val)))

    const dataSet = new BarDataSet(entries, '每日步数')
    dataSet.setColorByColor(0xFF4ECDC4) // 青绿色

    const barData = new BarData(dataSet)
    barData.setBarWidth(0.5)

    this.model.setData(barData)
    this.model.getXAxis().setPosition(XAxisPosition.BOTTOM)
    this.model.getXAxis().setValueFormatter((value) => days[Math.floor(value)] || '')
    this.model.getAxisLeft().setAxisMinimum(0)
    this.model.getAxisRight().setEnabled(false) // 隐藏右侧 Y 轴
    this.model.setDescription(new Description().setText('单位:步'))

    // 点击柱子高亮
    this.barChart.setOnChartValueSelectedListener({
      onValueSelected: (e: EntryOhos, h: Highlight) => {
        promptAction.showToast({
          message: `${days[Math.floor(e.getX())]}: ${e.getY()} 步`,
        })
      },
      onNothingSelected: () => {},
    })

    this.barChart.setModel(this.model)
  }

  build() {
    Column() {
      Text('本周步数').fontSize(20).fontWeight(FontWeight.Bold).padding(12)
      this.barChart
    }
    .width('100%').height(400)
  }
}

第三步:心率折线图------24 小时曲线

typescript 复制代码
import {
  LineChart, LineChartModel, LineData, LineDataSet, LineEntry,
  JArrayList, XAxisPosition
} from '@ohos/mpchart'

// 24 小时心率数据(每小时一个点)
const heartRates = [62, 60, 58, 56, 55, 58, 64, 72, 80, 85, 78, 76,
                    74, 72, 70, 75, 82, 88, 92, 85, 76, 70, 66, 62]

const entries = new JArrayList<LineEntry>()
heartRates.forEach((hr, i) => entries.add(new LineEntry(i, hr)))

const dataSet = new LineDataSet(entries, '心率 (bpm)')
dataSet.setColorByColor(0xFFFF6B6B)  // 红色曲线
dataSet.setCircleColor(0xFFFF6B6B)
dataSet.setLineWidth(2)
dataSet.setDrawFilled(true) // 曲线下方填充
dataSet.setFillColor(0x33FF6B6B)

const model = new LineChartModel()
model.setData(new LineData(dataSet))
model.getXAxis().setPosition(XAxisPosition.BOTTOM)
model.getXAxis().setValueFormatter((v) => `${Math.floor(v)}:00`)
model.getAxisLeft().setAxisMinimum(40)
model.getAxisRight().setEnabled(false)
model.setDescription(new Description().setText('24h 心率'))

// 支持手势缩放(双指缩放看细节)
model.setPinchZoom(true)
model.setDoubleTapToZoomEnabled(true)

第四步:睡眠饼状图------占比分布

typescript 复制代码
import {
  PieChart, PieChartModel, PieData, PieDataSet, PieEntry,
  JArrayList
} from '@ohos/mpchart'

// 睡眠分布:深睡 2h、浅睡 5h、REM 1.5h、清醒 0.5h
const entries = new JArrayList<PieEntry>()
entries.add(new PieEntry(2, '深睡'))
entries.add(new PieEntry(5, '浅睡'))
entries.add(new PieEntry(1.5, 'REM'))
entries.add(new PieEntry(0.5, '清醒'))

const dataSet = new PieDataSet(entries, '睡眠分布')
dataSet.setColors([0xFF6C5CE7, 0xFF74B9FF, 0xFFFDCB6E, 0xFFFF7675])
dataSet.setSliceSpace(2) // 扇区间隙

const model = new PieChartModel()
model.setData(new PieData(dataSet))
model.setUsePercentValues(true) // 显示百分比
model.setDescription(new Description().setText(''))

为什么"数据眼"选了 mpchart?

需求 自研 Canvas @ohos/mpchart
柱状图 200+ 行 30 行
折线图 300+ 行 30 行
饼状图 250+ 行 20 行
手势缩放 手写 ✅ 内置
点击高亮 手写 ✅ 内置
雷达图 400+ 行 30 行

总结

"数据眼"这个场景里,@ohos/mpchart 解决了三件事:

  1. 多图表覆盖------柱状/折线/饼状/雷达,一个库搞定健康数据可视化全家桶
  2. 交互开箱即用------手势缩放、点击高亮、数据选中,不用手写
  3. 高度自定义------颜色、轴、网格、动画、格式化器,细节全可控

如果你也在做健康、金融、电商、IoT 监控等需要数据可视化的 App,@ohos/mpchart 让你的图表 UI 告别从零造轮子,几十行出图不是梦。


相关推荐
lilian2331 小时前
Harmony os 技术实战|拼豆制图49:五组分类视觉规则如何收口成一张配置表
华为·harmonyos
2501_919749032 小时前
华为鸿蒙免费决策APP—小羊挠头
华为·harmonyos·鸿蒙
m0_749690232 小时前
【寻迹校园 HarmonyOS NEXT 实战 37】一套 ArkUI 适配四档宽度:sm、md、lg、xl 响应式 Shell 实战
华为·harmonyos·arkui·navigation·响应式布局·多设备适配
RisunJan4 小时前
HarmonyOS 架构精读:从系统分层到应用模型
华为·架构·harmonyos
见山是山-见水是水4 小时前
从需求到页面:鸿蒙原生 Ability 与 ArkTS 交互的 ArkTS 原生实现
华为·harmonyos
见山是山-见水是水4 小时前
网络请求性能优化落地指南:让原生界面在模拟器里稳定运行
网络协议·华为·性能优化·harmonyos
2501_919749035 小时前
华为鸿蒙免费语音记录APP—小羊回响
华为·harmonyos·鸿蒙
less_121385 小时前
HarmonyOS WPS Open SDK:旧 HAR 迁移到统一接口联调指南
华为·sdk·harmonyos·wps·鸿蒙开发·文档编辑
yuhulkjv3355 小时前
告别复制粘贴式降级:纳米AI鸿蒙版导出word格式为何绕不开“AI 导出鸭”
人工智能·ai·word·harmonyos·ai导出鸭