- 一、概述
- 二、Chart 组件体系总览
- 三、快速上手:第一个折线图
- 四、实时数据绘图(动态折线图)
- 五、多数据系列(多条折线)
- 六、曲线图(平滑折线)
- 七、样式自定义
- 八、数据导入
- 九、趋势线(最佳拟合线)
- 十、数据交互与查询
- 十一、完整实战案例:温度监测应用
- 十二、进阶:使用 ECharts 拓展实现更丰富的图表
- 十三、常见问题与解答
- 十四、ChartData2D 方法速查表
- 十五、总结
一、概述
数据可视化是 App 开发中的常见需求——温度监测、运动轨迹、成绩走势、股票行情……都需要将数据以图表形式呈现。App Inventor 2 从 nb186 版本(2020 年)开始内置了 Chart(图表)组件,支持折线图、面积图、散点图、条形图和饼图五种类型,无需任何拓展即可使用。
本文聚焦折线图/曲线图场景,从零开始讲解 Chart 组件的核心概念、基础用法、实时数据绘图、多数据系列、样式自定义、数据导入导出等内容。
前置知识: 了解 App Inventor 2 的基本操作(拖拽组件、拼接积木块)。如需回顾,请参阅 连接调试指南。
二、Chart 组件体系总览
App Inventor 2 的图表功能由以下三个核心组件协作完成:
| 组件 | 位置 | 作用 |
|---|---|---|
| Chart(图表) | 界面组件 → 图表 | 图表容器,决定图表类型、背景、网格等外观 |
| ChartData2D(二维图表数据) | 界面组件 → 图表 | 表示一条数据系列(如一条折线),管理数据点的增删改查 |
| Trendline(趋势线) | 界面组件 → 图表 | 基于数据系列自动计算并绘制最佳拟合线 |
关键理解: Chart 是”画布”,ChartData2D 是”画笔+颜料”。一个 Chart 可以挂载多个 ChartData2D(即多条折线),每个 ChartData2D 独立管理自己的数据和样式。
支持的图表类型
Chart 组件通过 类型 属性切换以下五种图表:
- 折线图(Line) —— 数据点用直线段连接(本文重点)
- 面积图(Area) —— 折线下方填充颜色
- 散点图(Scatter) —— 只显示数据点,不连线
- 条形图(Bar) —— 柱状图
- 饼图(Pie) —— 饼图
三、快速上手:第一个折线图
3.1 界面设计
- 打开 App Inventor 2 设计视图
- 从左侧组件面板 图表 分类中,将 Chart 组件拖入 Screen
- 将 ChartData2D 组件拖入 Chart 组件内部(注意:必须拖到 Chart 上,不是 Screen 上)
- 设置 Chart 组件的属性:
- 类型 →
折线图 - 描述 →
我的第一个折线图(作为图表标题) - 启用网格 →
勾选
- 类型 →
- 设置 ChartData2D 的属性:
- 颜色 → 选一个你喜欢的颜色(如蓝色)
- 标签 →
数据系列1
3.2 积木块:添加静态数据
使用 ChartData2D 的 添加数据点 方法,传入 x 和 y 值:
当 Screen1.初始化 时 执行:
调用 ChartData2D1.添加数据点(x: "1", y: "3")
调用 ChartData2D1.添加数据点(x: "2", y: "7")
调用 ChartData2D1.添加数据点(x: "3", y: "4")
调用 ChartData2D1.添加数据点(x: "4", y: "9")
调用 ChartData2D1.添加数据点(x: "5", y: "6")
运行后,你将看到一条由 5 个数据点组成的折线图。
3.3 用 CSV 方式一次性导入数据
除了逐点添加,ChartData2D 还提供了 元素来自键值对 属性,可以直接在设计视图输入 CSV 格式的数据:
x1,y1,x2,y2,x3,y3
例如:
1,23,2,28,3,35,4,30,5,42,6,38
这会一次性添加 6 个数据点:(1,23), (2,28), (3,35), (4,30), (5,42), (6,38)。
四、实时数据绘图(动态折线图)
实时数据绘图是最常见的应用场景之一——传感器数据、实时监测、动态更新等。
4.1 使用计时器定时添加数据
核心思路:用 Clock(计时器) 组件定时触发,每次触发时向 ChartData2D 添加一个新的数据点。
界面设计:
- 添加一个 Clock 组件,设置 计时间隔 为 1000(毫秒,即 1 秒)
- 添加一个按钮用于开始/停止
- Chart + ChartData2D(类型设为折线图)
积木块:
// 全局变量
全局 x计数 ← 0
当 按钮_开始.被点击 时 执行:
设置 Clock1.启用计时 为 true
调用 ChartData2D1.清除数据序列()
当 Clock1.计时器事件 时 执行:
x计数 ← x计数 + 1
随机值 ← 取随机整数(从 1 到 100)
调用 ChartData2D1.添加数据点(x: x计数, y: 随机值)
4.2 保持图表窗口滚动(只显示最近 N 个点)
如果数据持续增长,图表会越来越拥挤。常见做法是只保留最近的 N 个数据点:
当 Clock1.计时器事件 时 执行:
x计数 ← x计数 + 1
随机值 ← 取随机整数(从 1 到 100)
调用 ChartData2D1.添加数据点(x: x计数, y: 随机值)
所有数据 ← 调用 ChartData2D1.获取所有数据点()
如果 长度(列表:所有数据) > 20 那么:
第一个点 ← 列表中的第1项(所有数据)
x旧 ← 列表中的第1项(第一个点)
y旧 ← 列表中的第2项(第一个点)
调用 ChartData2D1.删除数据点(x: x旧, y: y旧)
说明:
获取所有数据点返回的列表中,每个元素是一个子列表[x, y]。
4.3 接入传感器数据实时绘图
Chart 组件支持直接绑定传感器作为数据源。以加速度传感器为例:
- 添加 AccelerometerSensor 组件
- 设置 ChartData2D 的属性:
- 数据源 → 选择
AccelerometerSensor1 - 数据源键标识符 →
X(表示 X 轴加速度)
- 数据源 → 选择
这样传感器每次产生新数据时,图表会自动更新。
支持的传感器数据源: 加速度传感器(X/Y/Z)、陀螺仪传感器(X/Y/Z)、位置传感器(纬度/经度/高度/速度)、方向传感器(俯仰角/方位角/横滚角)、计步器(行走步数/简单步数/距离)、距离传感器(距离)。
五、多数据系列(多条折线)
一个 Chart 容器可以挂载多个 ChartData2D 组件,实现多条折线同时显示。
5.1 界面设计
- 一个 Chart 组件(类型:折线图)
- 拖入两个(或更多) ChartData2D 到 Chart 内部
- 分别设置不同颜色和标签:
- ChartData2D1:颜色=蓝色,标签=最高温度
- ChartData2D2:颜色=红色,标签=最低温度
5.2 积木块
当 Screen1.初始化 时 执行:
// 最高温度数据
调用 ChartData2D1.添加数据点(x: "1月", y: "5")
调用 ChartData2D1.添加数据点(x: "2月", y: "8")
调用 ChartData2D1.添加数据点(x: "3月", y: "14")
调用 ChartData2D1.添加数据点(x: "4月", y: "22")
调用 ChartData2D1.添加数据点(x: "5月", y: "28")
// 最低温度数据
调用 ChartData2D2.添加数据点(x: "1月", y: "-3")
调用 ChartData2D2.添加数据点(x: "2月", y: "-1")
调用 ChartData2D2.添加数据点(x: "3月", y: "4")
调用 ChartData2D2.添加数据点(x: "4月", y: "10")
调用 ChartData2D2.添加数据点(x: "5月", y: "16")
Chart 会自动显示图例,区分两条折线。
六、曲线图(平滑折线)
ChartData2D 提供了 线型 属性,可以将折线图从直线变为平滑曲线:
- 折线(默认)—— 数据点之间用直线连接
- 曲线 —— 数据点之间用贝塞尔曲线平滑连接
- 阶梯 —— 数据点之间用阶梯线连接
在 设计视图 中设置 ChartData2D 的 线型 属性为 曲线,或在积木块中动态设置。
七、样式自定义
7.1 Chart 容器属性
| 属性 | 说明 |
|---|---|
| 背景颜色 | 图表背景色(RGBA) |
| 描述 | 图表标题文字 |
| 启用网格 | 是否显示网格线(适用于折线图、面积图、散点图、条形图) |
| 启用图例 | 是否显示图例(多数据系列时有用) |
| 标签列表 | 自定义 X 轴标签,如 ["周一","周二","周三","周四","周五"] |
| CSV字符串标签 | 以逗号分隔的字符串设置 X 轴标签,如 "周一,周二,周三,周四,周五" |
| 类型 | 切换图表类型 |
| 宽度/高度 | 尺寸设置 |
7.2 ChartData2D 数据系列属性
| 属性 | 说明 |
|---|---|
| 颜色 | 数据系列颜色 |
| 颜色列表 | 多色交替显示 |
| 标签 | 数据系列名称(图例文字) |
| 线型 | 折线/曲线/阶梯(适用于折线图和面积图) |
| 点型 | 圆形/方形/三角/十字/叉号(适用于散点图) |
| 元素来自键值对 | CSV 格式静态数据 |
7.3 自定义 X 轴标签示例
使用 标签列表 属性可以让 X 轴显示有意义的文字标签:
当 Screen1.初始化 时 执行:
设置 Chart1.标签列表 为 ["1月","2月","3月","4月","5月","6月"]
调用 ChartData2D1.从列表导入(list: [ [1,120],[2,200],[3,150],[4,280],[5,230],[6,310] ])
八、数据导入
除了逐点添加,ChartData2D 还支持从多种数据源批量导入数据。
8.1 从列表导入
调用 ChartData2D1.从列表导入(list: [[1,30],[2,45],[3,28],[4,60],[5,52]])
列表格式为 [[x1,y1],[x2,y2],...]。注意:此方法不会清除已有数据。
8.2 从微数据库导入
调用 ChartData2D1.从微数据库导入(tinyDB: TinyDB1, 标签: "temperature_data")
TinyDB 中存储的数据应该是列表格式:[[x1,y1],[x2,y2],...]
8.3 从云数据库导入
调用 ChartData2D1.从云数据库导入(云数据库: CloudDB1, 标签: "sensor_data")
8.4 从数据文件导入(CSV/JSON)
调用 ChartData2D1.从数据文件导入(数据文件: DataFile1, x值列: "time", y值列: "temperature")
数据文件示例(CSV 格式):
time,temperature
08:00,22.5
09:00,23.1
10:00,25.0
11:00,26.3
12:00,28.1
8.5 从 Web 客户端导入
// 先发起网络请求
调用 Web1.获取(url: "https://api.example.com/data.json")
// 在 Web1.收到内容 事件中
当 Web1.收到内容(响应代码: code, 响应内容: content) 时 执行:
调用 ChartData2D1.从Web客户端导入(web: Web1, xValueColumn: "time", yValueColumn: "value")
8.6 从电子表格导入
// 先读取电子表格数据
调用 Spreadsheet1.读取工作表()
// 然后导入到图表
调用 ChartData2D1.从电子表格导入(sheet: Spreadsheet1, xColumn: "A", yColumn: "B", useHeaders: true)
九、趋势线(最佳拟合线)
Chart 组件内置了 Trendline 子组件,可以自动计算并绘制趋势线,支持以下模型:
| 模型 | 公式 | 适用场景 |
|---|---|---|
| 线性 | y = m*x + b | 线性增长趋势 |
| 二次 | y = ax² + bx + c | 先升后降/先降后升 |
| 对数 | y = a + b*ln(x) | 递增趋缓 |
| 指数 | y = a*b^x | 加速增长/衰减 |
使用方法:
- 将 Trendline 组件拖入 Chart 内部
- 设置 图表数据 属性 → 选择要关联的 ChartData2D
- 设置 模型 → 如
线性 - 设置 颜色 和 线条宽度
Trendline 还提供了以下只读属性供程序使用:
- 拟合系数(RSquared) —— 拟合优度(越接近 1 越好)
- 线性系数 / 二次系数 / 对数系数 / 指数系数
- Y轴交点
- 预测 —— 基于模型进行预测
注意: Trendline 组件要求 AI 伴侣 v2.70 及以上版本。
十、数据交互与查询
10.1 数据点点击事件
Chart 和 ChartData2D 都提供了数据点点击事件:
当 ChartData2D1.数据点被点击(x坐标: x, y坐标: y) 时 执行:
调用 Label1.设置文本(文本: "点击了数据点:x=" + x + ", y=" + y)
10.2 查询数据
// 检查某个数据点是否存在
存在 ← 调用 ChartData2D1.数据点是否存在(x: "3", y: "45")
// 获取所有数据
所有数据 ← 调用 ChartData2D1.获取所有数据点()
// 按 X 值查找
匹配数据 ← 调用 ChartData2D1.获取X值数据点(x: "3")
// 按 Y 值查找
匹配数据 ← 调用 ChartData2D1.获取Y值数据点(y: "45")
10.3 清除与删除
// 删除单个数据点
调用 ChartData2D1.删除数据点(x: "3", y: "45")
// 清除所有数据
调用 ChartData2D1.清除数据序列()
十一、完整实战案例:温度监测应用
下面通过一个完整的温度监测案例,串联前面所学知识。
11.1 功能需求
- 模拟每秒采集一次温度数据(25°C ± 随机波动)
- 折线图实时显示最近 30 个数据点
- 显示当前温度值和最高/最低温度
- 支持暂停/继续
11.2 界面设计
Screen1 (标题: 温度监测)
├── 水平布局1
│ ├── Label_当前温度 (文本: "--°C")
│ ├── Label_最高温度 (文本: "最高: --°C")
│ └── Label_最低温度 (文本: "最低: --°C")
├── Chart1 (类型: 折线图, 描述: 实时温度, 启用网格: ✓, 宽度: 充满, 高度: 300px)
│ └── ChartData2D1 (颜色: 蓝色, 标签: 温度, 线型: 曲线)
├── 水平布局2
│ ├── Button_开始 (文本: "开始监测")
│ └── Button_停止 (文本: "停止监测")
└── Clock1 (计时间隔: 1000, 启用计时: false)
11.3 积木块
// ========== 全局变量 ==========
全局 x计数 ← 0
全局 最高温度 ← 0
全局 最低温度 ← 100
// ========== 开始监测 ==========
当 Button_开始.被点击 时 执行:
设置 Clock1.启用计时 为 true
设置 x计数 为 0
设置 最高温度 为 0
设置 最低温度 为 100
调用 ChartData2D1.清除数据序列()
// ========== 停止监测 ==========
当 Button_停止.被点击 时 执行:
设置 Clock1.启用计时 为 false
// ========== 定时采集数据 ==========
当 Clock1.计时器事件 时 执行:
x计数 ← x计数 + 1
当前温度 ← 25 + (取随机小数 × 10) - 5 // 20~30°C 之间随机
当前温度 ← 四舍五入(当前温度, 小数位数: 1)
// 更新图表
调用 ChartData2D1.添加数据点(x: x计数, y: 当前温度)
// 保持窗口大小为30个点
所有数据 ← 调用 ChartData2D1.获取所有数据点()
如果 长度(列表:所有数据) > 30 那么:
旧点 ← 列表中的第1项(所有数据)
调用 ChartData2D1.删除数据点(x: 列表中的第1项(旧点), y: 列表中的第2项(旧点))
// 更新统计
如果 当前温度 > 最高温度 那么:
最高温度 ← 当前温度
如果 当前温度 < 最低温度 那么:
最低温度 ← 当前温度
// 更新显示
设置 Label_当前温度.文本 为 (当前温度 + "°C")
设置 Label_最高温度.文本 为 ("最高: " + 最高温度 + "°C")
设置 Label_最低温度.文本 为 ("最低: " + 最低温度 + "°C")
十二、进阶:使用 ECharts 拓展实现更丰富的图表
App Inventor 2 内置 Chart 组件满足基础需求。如果需要更强大的图表效果(如 3D 图表、复杂交互、动画效果等),可以使用 ECharts 拓展。
详见 ECharts 拓展文档。
ECharts 折线图示例
ECharts 拓展的 Line 方法可以绘制平滑曲线折线图:
当 Screen1.初始化 时 执行:
调用 ECharts1.初始化(layout: 水平布局1)
调用 ECharts1.画折线图(
title: "月度销售数据",
legends: ["线上","线下"],
labels: ["1月","2月","3月","4月","5月","6月"],
datas: [[120,200,150,280,230,310],[80,150,120,200,180,250]],
smooth: true
)
ECharts 的优势:
- 支持 7 种主题风格
- 支持平滑曲线(smooth 参数)
- 支持图表点击事件回调
- 支持导出图片
- 支持 3D 曲面图等高级图表
十三、常见问题与解答
Q1:Chart 组件的最低版本要求?
Chart 组件从 nb186 版本开始内置。Trendline 组件要求 AI 伴侣 v2.70 及以上。建议始终使用最新版本的 AI 伴侣。
Q2:折线图可以显示多少个数据点?
Chart 组件本身没有硬性限制,但从性能角度,建议单个数据系列不超过 1000 个数据点。超过时建议只保留最近的数据。
Q3:如何实现折线图的 X 轴显示时间?
可以用字符串作为 X 值:
调用 ChartData2D1.添加数据点(x: "08:00", y: "22")
调用 ChartData2D1.添加数据点(x: "09:00", y: "23")
Q4:如何保存图表数据?
使用 获取所有数据点 获取数据列表,然后存入 TinyDB:
当 Button_保存.被点击 时 执行:
所有数据 ← 调用 ChartData2D1.获取所有数据点()
调用 TinyDB1.保存标签(标签: "chart_data", 值为: 所有数据)
下次启动时用 从列表导入 或 从微数据库导入 恢复。
Q5:折线图和面积图的区别?
面积图是折线图的填充版本——折线下方会填充颜色。两者使用相同的数据结构,只需将 Chart 类型从”折线图”切换为”面积图”即可。
Q6:如何实现动态切换图表类型?
当 Button_切换.被点击 时 执行:
设置 Chart1.类型 为 "条形图" // 或其他类型
十四、ChartData2D 方法速查表
| 方法 | 参数 | 说明 |
|---|---|---|
添加数据点 |
x, y | 添加一个数据点 |
删除数据点 |
x, y | 删除指定数据点 |
清除数据序列 |
无 | 清除所有数据 |
数据点是否存在 |
x, y | 返回布尔值 |
获取所有数据点 |
无 | 返回 [[x1,y1],[x2,y2],…] |
获取X值数据点 |
x | 返回匹配 x 值的所有数据点 |
获取Y值数据点 |
y | 返回匹配 y 值的所有数据点 |
从列表导入 |
list | 从列表批量导入 |
从微数据库导入 |
tinyDB, tag | 从 TinyDB 导入 |
从云数据库导入 |
cloudDB, tag | 从 CloudDB 导入 |
从数据文件导入 |
dataFile, xCol, yCol | 从 CSV/JSON 文件导入 |
从Web客户端导入 |
web, xCol, yCol | 从 Web 请求结果导入 |
从电子表格导入 |
sheet, xCol, yCol, useHeaders | 从电子表格导入 |
改变数据源 |
source, keyValue | 动态切换数据源 |
删除数据源 |
无 | 移除数据源绑定 |
十五、总结
App Inventor 2 内置的 Chart 组件已经能覆盖大部分数据可视化需求:
- 折线图 适合展示趋势变化
- 曲线图 通过设置线型为”曲线”即可实现平滑效果
- 实时数据 通过 Clock + 添加数据点 + 滚动窗口实现
- 多数据系列 通过多个 ChartData2D 组件实现
- 趋势线 内置支持线性/二次/对数/指数拟合
- 数据导入 支持 TinyDB、CloudDB、CSV、JSON、Web API、电子表格等
- ECharts 拓展 提供更高级的图表效果
完整组件属性和方法请参考 图表组件参考文档。
MIT App Inventor 官方文档采用 CC BY-SA 4.0 授权,本文档由 ai2claw 🐝 整理
扫码添加客服咨询