单位换算大师应用


欢迎加入开源鸿蒙跨平台社区:
https://openharmonycrossplatform.csdn.net

一、项目概述

运行效果图
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

1.1 应用简介

单位换算大师是一款功能全面的单位转换工具,旨在帮助用户快速、准确地进行各类单位之间的换算。在科学研究、工程设计、日常生活、国际贸易等场景中,单位换算是一项基础而重要的工作。本应用整合了长度、重量、面积、体积、温度、时间、速度、数据、压强、能量等十大类单位,支持公制、英制、中国传统单位等多种计量体系,让单位换算变得简单高效。

从纳米级的微观测量到光年级的宇宙尺度,从微克的精密称量到吨级的工业计量,本应用覆盖了广泛的换算需求。特别是温度换算,采用非线性转换算法,精确处理摄氏度、华氏度、开尔文三种温标之间的转换关系。

1.2 核心功能

功能模块 功能描述 实现方式
多类别换算 支持10大类别单位换算 枚举分类 + 因子转换
温度换算 摄氏/华氏/开尔文互转 非线性转换算法
历史记录 保存换算记录便于查阅 List集合 + 状态管理
收藏功能 收藏常用换算组合 Set集合 + 快捷访问
单位交换 快速交换源/目标单位 状态切换
结果复制 一键复制换算结果 剪贴板API

1.3 单位类别概览

类别 英文标识 图标 颜色 单位数量 代表单位
长度 length straighten 蓝色 16 米、千米、英尺、英寸
重量 weight scale 绿色 11 千克、克、磅、盎司
面积 area crop_square 橙色 13 平方米、公顷、亩
体积 volume water_drop 青色 13 升、毫升、加仑
温度 temperature thermostat 红色 3 摄氏度、华氏度、开尔文
时间 time access_time 紫色 10 秒、分、时、天
速度 speed speed 靛蓝色 6 米/秒、千米/时、马赫
数据 data storage 蓝绿色 7 字节、KB、MB、GB
压强 pressure compress 棕色 7 帕斯卡、大气压、psi
能量 energy bolt 琥珀色 9 焦耳、卡路里、千瓦时

1.4 技术栈

技术领域 技术选型 版本要求
开发框架 Flutter >= 3.0.0
编程语言 Dart >= 2.17.0
设计规范 Material Design 3 -
状态管理 setState -
目标平台 鸿蒙OS API 21+

1.5 项目结构

lib/
└── main_unit_converter.dart
    ├── UnitConverterApp        # 应用入口
    ├── UnitCategory            # 单位类别枚举
    ├── Unit                    # 单位模型
    ├── ConversionRecord        # 换算记录模型
    ├── HomePage                # 主页面
    │   ├── _buildHomePage()    # 首页
    │   ├── _buildCategoryPage() # 分类页
    │   ├── _buildHistoryPage() # 历史页
    │   └── _buildFavoritesPage() # 收藏页
    └── ConverterPage           # 换算页面

二、系统架构

2.1 整体架构图

Business Logic

Data Layer

Presentation Layer

首页
分类概览

换算页

历史页

收藏页

Unit
单位模型

ConversionRecord
换算记录

UnitCategory
类别枚举

单位换算
_calculate

温度转换
_convertTemperature

收藏管理
_favorites

历史管理
_history

2.2 类图设计

manages

uses

uses

references

belongs to

contains

UnitConverterApp

+Widget build()

HomePage

-int _currentIndex

-List<ConversionRecord> _history

-Set<String> _favorites

+Widget build()

-void _toggleFavorite()

-String _formatResult()

ConverterPage

-UnitCategory category

-int _fromIndex

-int _toIndex

-TextEditingController _inputController

-String _result

+Widget build()

-void _calculate()

-double _convertTemperature()

-void _swapUnits()

-void _saveRecord()

Unit

+String name

+String symbol

+double factor

+bool isTemperature

ConversionRecord

+String id

+UnitCategory category

+String fromUnit

+String toUnit

+double fromValue

+double toValue

+DateTime date

«enumeration»

UnitCategory

length

weight

area

volume

temperature

time

speed

data

pressure

energy

+String categoryName

+IconData categoryIcon

+Color categoryColor

+List<Unit> units

2.3 数据流程图

普通单位

温度

保存

收藏

复制

用户输入

单位类别

因子换算

非线性换算

baseValue = input × fromFactor

result = baseValue / toFactor

转换为摄氏度

转换为目标温标

格式化结果

显示结果

用户操作

添加历史记录

添加收藏

复制到剪贴板

2.4 换算流程时序图

换算算法 单位模型 换算页 用户 换算算法 单位模型 换算页 用户 alt [普通单位] [温度单位] 选择单位类别 获取单位列表 返回单位数据 选择源单位 选择目标单位 输入数值 执行换算 因子乘除法 非线性转换 返回结果 显示换算结果

三、核心模块设计

3.1 数据模型设计

3.1.1 单位模型 (Unit)
class Unit {
  final String name;           // 单位名称(中文)
  final String symbol;         // 单位符号
  final double factor;         // 转换因子(相对于基准单位)
  final bool isTemperature;    // 是否为温度单位
}

转换原理说明:

基准值=输入值×源单位因子 \text{基准值} = \text{输入值} \times \text{源单位因子} 基准值=输入值×源单位因子

结果值=基准值目标单位因子 \text{结果值} = \frac{\text{基准值}}{\text{目标单位因子}} 结果值=目标单位因子基准值

3.1.2 换算记录模型 (ConversionRecord)
class ConversionRecord {
  final String id;              // 唯一标识
  final UnitCategory category;  // 单位类别
  final String fromUnit;        // 源单位
  final String toUnit;          // 目标单位
  final double fromValue;       // 源值
  final double toValue;         // 目标值
  final DateTime date;          // 换算时间
}
3.1.3 单位类别枚举 (UnitCategory)
17% 14% 14% 12% 11% 9% 7% 7% 6% 3% 单位类别分布 长度 重量 面积 体积 温度 时间 速度 数据 压强 能量

3.2 单位换算算法

3.2.1 普通单位换算
void _calculate() {
  final input = double.tryParse(_inputController.text);
  if (input == null) return;
  
  final fromUnit = widget.category.units[_fromIndex];
  final toUnit = widget.category.units[_toIndex];
  
  // 转换为基准单位值
  final baseValue = input * fromUnit.factor;
  // 转换为目标单位值
  final result = baseValue / toUnit.factor;
}
3.2.2 温度换算(非线性)

温度换算采用特殊的非线性转换公式,因为温度刻度不是简单的比例关系:

double _convertTemperature(double value, String from, String to) {
  // 第一步:转换为摄氏度
  double celsius;
  switch (from) {
    case '°C':
      celsius = value;
      break;
    case '°F':
      celsius = (value - 32) * 5 / 9;
      break;
    case 'K':
      celsius = value - 273.15;
      break;
  }
  
  // 第二步:从摄氏度转换为目标温标
  switch (to) {
    case '°C':
      return celsius;
    case '°F':
      return celsius * 9 / 5 + 32;
    case 'K':
      return celsius + 273.15;
  }
}

温度转换公式:

转换方向 公式
°C → °F F=C×95+32F = C \times \frac{9}{5} + 32F=C×59+32
°F → °C C=(F−32)×59C = (F - 32) \times \frac{5}{9}C=(F32)×95
°C → K K=C+273.15K = C + 273.15K=C+273.15
K → °C C=K−273.15C = K - 273.15C=K273.15

3.3 页面结构设计

3.3.1 首页模块

首页 _buildHomePage

头部信息卡

分类网格

应用标题

统计数据

换算类别数

历史记录数

收藏单位数

长度卡片

重量卡片

面积卡片

体积卡片

温度卡片

时间卡片

速度卡片

数据卡片

压强卡片

能量卡片

3.3.2 换算页面

点击交换按钮

点击保存

点击复制

点击收藏

选择源单位

选择目标单位

输入数值

实时计算

显示结果

交换单位

保存记录

复制结果

收藏组合

3.3.3 历史记录页面

历史页

有记录?

记录列表

空状态提示

类别标签

源值/源单位

目标值/目标单位

换算时间

3.4 状态管理

3.4.1 核心状态变量
class _HomePageState extends State<HomePage> {
  // 导航状态
  int _currentIndex = 0;
  
  // 数据状态
  final List<ConversionRecord> _history = [];
  final Set<String> _favorites = {};
}

class _ConverterPageState extends State<ConverterPage> {
  // 换算状态
  late int _fromIndex;
  late int _toIndex;
  final TextEditingController _inputController = TextEditingController();
  String _result = '';
  bool _isReversed = false;
}
3.4.2 收藏功能实现
String get _favoriteKey {
  // 格式: 类别索引|源单位索引|目标单位索引
  return '${widget.category.index}|$_fromIndex|$_toIndex';
}

void _toggleFavorite(String key) {
  setState(() {
    if (_favorites.contains(key)) {
      _favorites.remove(key);
    } else {
      _favorites.add(key);
    }
  });
}

四、UI设计规范

4.1 配色方案

应用采用浅色主题设计,营造清爽专业的氛围:

颜色类型 色值 用途
主色 #1976D2 (Blue) AppBar、按钮、强调元素
背景色 #F5F5F5 页面背景
卡片背景 #FFFFFF 卡片、弹窗
文字主色 #000000 主要文字
文字次色 #757575 次要文字

类别专属颜色:

// 长度 - 蓝色
Colors.blue

// 重量 - 绿色
Colors.green

// 面积 - 橙色
Colors.orange

// 体积 - 青色
Colors.cyan

// 温度 - 红色
Colors.red

// 时间 - 紫色
Colors.purple

// 速度 - 靛蓝色
Colors.indigo

// 数据 - 蓝绿色
Colors.teal

// 压强 - 棕色
Colors.brown

// 能量 - 琥珀色
Colors.amber

4.2 字体规范

元素 字号 字重 颜色
输入数值 32px Bold #000000
换算结果 36px Bold 类别色
单位名称 16px Medium #000000
单位符号 12px Regular #757575
类别标签 14px Medium #000000

4.3 组件规范

4.3.1 分类卡片
┌─────────────────────────────┐
│         ┌────┐              │
│         │ 📏 │              │
│         └────┘              │
│          长度                │
│        16 单位               │
└─────────────────────────────┘
4.3.2 换算面板
┌─────────────────────────────────────────────────┐
│  从                    ⇄                    到  │
│ ┌─────────────┐          ┌─────────────┐       │
│ │    米  ▼    │          │  千米  ▼    │       │
│ └─────────────┘          └─────────────┘       │
│                                                 │
│              1000                               │
│              米                                 │
│                                                 │
│                =                                │
│                                                 │
│               1                                 │
│              千米                               │
│                                                 │
│     [复制结果]        [保存记录]               │
└─────────────────────────────────────────────────┘
4.3.3 历史记录卡片
┌─────────────────────────────────────────────────┐
│ [长度]                              1/25 14:30 │
│                                                 │
│  1000                      1                    │
│  米              →         千米                 │
└─────────────────────────────────────────────────┘

五、核心功能实现

5.1 单位数据定义

List<Unit> get units {
  switch (this) {
    case UnitCategory.length:
      return [
        Unit('千米', 'km', 1000),
        Unit('米', 'm', 1),
        Unit('分米', 'dm', 0.1),
        Unit('厘米', 'cm', 0.01),
        Unit('毫米', 'mm', 0.001),
        // ... 更多单位
      ];
    // ... 其他类别
  }
}

5.2 实时计算


void initState() {
  super.initState();
  _inputController.addListener(_calculate);
}

void _calculate() {
  final input = double.tryParse(_inputController.text);
  if (input == null) {
    setState(() => _result = '');
    return;
  }
  
  final fromUnit = widget.category.units[_fromIndex];
  final toUnit = widget.category.units[_toIndex];
  
  double result;
  if (widget.category == UnitCategory.temperature) {
    result = _convertTemperature(input, fromUnit.symbol, toUnit.symbol);
  } else {
    final baseValue = input * fromUnit.factor;
    result = baseValue / toUnit.factor;
  }
  
  setState(() => _result = _formatResult(result));
}

5.3 结果格式化

String _formatResult(double value) {
  if (value == value.toInt()) {
    return value.toInt().toString();
  } else if (value.abs() < 0.001 || value.abs() > 1000000) {
    return value.toStringAsExponential(6);
  } else {
    return value
        .toStringAsFixed(10)
        .replaceAll(RegExp(r'0+$'), '')
        .replaceAll(RegExp(r'\.$'), '');
  }
}

5.4 单位交换

void _swapUnits() {
  setState(() {
    final temp = _fromIndex;
    _fromIndex = _toIndex;
    _toIndex = temp;
    _isReversed = !_isReversed;
    _calculate();
  });
}

5.5 保存记录

void _saveRecord() {
  final input = double.tryParse(_inputController.text);
  if (input == null || _result.isEmpty) return;
  
  final record = ConversionRecord(
    id: DateTime.now().millisecondsSinceEpoch.toString(),
    category: widget.category,
    fromUnit: widget.category.units[_fromIndex].name,
    toUnit: widget.category.units[_toIndex].name,
    fromValue: input,
    toValue: double.tryParse(_result) ?? 0,
    date: DateTime.now(),
  );
  
  widget.onConvert(record);
}

六、单位数据详解

6.1 长度单位

单位名称 符号 转换因子 说明
千米 km 1000 公制
m 1 基准单位
分米 dm 0.1 公制
厘米 cm 0.01 公制
毫米 mm 0.001 公制
微米 μm 0.000001 公制
纳米 nm 0.000000001 公制
英里 mi 1609.344 英制
yd 0.9144 英制
英尺 ft 0.3048 英制
英寸 in 0.0254 英制
海里 nmi 1852 航海
500 中国传统
3.33333333 中国传统
0.33333333 中国传统
0.03333333 中国传统

6.2 重量单位

单位名称 符号 转换因子 说明
t 1000 公制
千克 kg 1 基准单位
g 0.001 公制
毫克 mg 0.000001 公制
微克 μg 0.000000001 公制
lb 0.45359237 英制
盎司 oz 0.028349523 英制
0.5 中国传统
0.05 中国传统
0.005 中国传统
克拉 ct 0.0002 珠宝

6.3 面积单位

单位名称 符号 转换因子 说明
平方千米 km² 1000000 公制
公顷 ha 10000 公制
公亩 a 100 公制
平方米 1 基准单位
平方分米 dm² 0.01 公制
平方厘米 cm² 0.0001 公制
平方毫米 mm² 0.000001 公制
平方英里 mi² 2589988.11 英制
英亩 ac 4046.8564224 英制
平方英尺 ft² 0.09290304 英制
平方英寸 in² 0.00064516 英制
666.6666667 中国传统
66666.666667 中国传统

6.4 体积单位

单位名称 符号 转换因子 说明
立方米 1 基准单位
立方分米 dm³ 0.001 公制
立方厘米 cm³ 0.000001 公制
L 0.001 公制
毫升 mL 0.000001 公制
加仑(美) gal 0.00378541 美制
夸脱(美) qt 0.00094635 美制
品脱(美) pt 0.00047318 美制
液量盎司(美) fl oz 0.00002957 美制
桶(石油) bbl 0.158987 石油工业

6.5 温度单位

温标转换

F = C × 9/5 + 32

C = (F-32) × 5/9

K = C + 273.15

C = K - 273.15

摄氏度 °C

华氏度 °F

开尔文 K

温标 冰点 沸点 绝对零度
摄氏度 (°C) 0 100 -273.15
华氏度 (°F) 32 212 -459.67
开尔文 (K) 273.15 373.15 0

6.6 时间单位

单位名称 符号 转换因子
y 31536000
mo 2592000
wk 604800
d 86400
小时 h 3600
分钟 min 60
s 1
毫秒 ms 0.001
微秒 μs 0.000001
纳秒 ns 0.000000001

6.7 速度单位

单位名称 符号 转换因子 说明
米/秒 m/s 1 基准单位
千米/时 km/h 0.277778 常用
英里/时 mph 0.44704 英制
kn 0.514444 航海
马赫 Ma 340.29 音速
光速 c 299792458 物理常数

6.8 数据单位

单位名称 符号 转换因子
比特 bit 0.125
字节 B 1
千字节 KB 1024
兆字节 MB 1048576
吉字节 GB 1073741824
太字节 TB 1099511627776
拍字节 PB 1125899906842624

6.9 压强单位

单位名称 符号 转换因子 说明
帕斯卡 Pa 1 基准单位
千帕 kPa 1000 公制
兆帕 MPa 1000000 工程常用
bar 100000 气象
标准大气压 atm 101325 物理
毫米汞柱 mmHg 133.322 医学
磅/平方英寸 psi 6894.76 英制

6.10 能量单位

单位名称 符号 转换因子 说明
焦耳 J 1 基准单位
千焦 kJ 1000 公制
兆焦 MJ 1000000 公制
卡路里 cal 4.184 热学
千卡 kcal 4184 营养学
瓦时 Wh 3600 电力
千瓦时 kWh 3600000 电表单位
电子伏特 eV 1.602e-16 物理
英热单位 BTU 1055.06 英制

七、换算知识

7.1 单位制简介

计量单位制

国际单位制 SI

英制单位

中国传统单位

米 m

千克 kg

秒 s

开尔文 K

英尺 ft

磅 lb

加仑 gal

7.2 换算原理

线性换算:大多数单位采用线性换算关系

Vtarget=Vsource×FsourceFtarget V_{target} = V_{source} \times \frac{F_{source}}{F_{target}} Vtarget=Vsource×FtargetFsource

非线性换算:温度等特殊单位需要特殊处理

T°F=T°C×95+32 T_{°F} = T_{°C} \times \frac{9}{5} + 32 T°F=T°C×59+32

7.3 精度处理

整数

极小或极大

普通小数

换算结果

判断数值范围

直接显示整数

科学计数法

去除尾部零

toStringAsExponential 6位

toStringAsFixed 10位

正则去除尾部0


八、扩展功能规划

8.1 后续版本规划

2024-01-07 2024-01-14 2024-01-21 2024-01-28 2024-02-04 2024-02-11 2024-02-18 2024-02-25 2024-03-03 2024-03-10 2024-03-17 2024-03-24 单位数据 换算算法 历史收藏 汇率换算 自定义单位 离线使用 换算公式展示 语音输入 小组件支持 V1.0 基础版本 V1.1 增强版本 V1.2 进阶版本 单位换算大师开发计划

8.2 功能扩展建议

8.2.1 汇率换算

接入实时汇率数据:

  • 支持全球主要货币
  • 实时汇率更新
  • 历史汇率查询
8.2.2 自定义单位

允许用户添加自定义单位:

  • 定义单位名称和符号
  • 设置转换因子
  • 分享自定义单位库
8.2.3 换算公式展示

显示详细换算过程:

  • 展示换算公式
  • 分步骤计算过程
  • 教育学习用途

九、注意事项

9.1 开发注意事项

  1. 温度换算:温度采用非线性换算,不能使用因子乘除法

  2. 精度处理:大数和小数需要科学计数法显示

  3. 因子精度:转换因子使用高精度数值,避免累积误差

  4. 单位符号:特殊符号如 μ 需要正确编码

9.2 常见问题

问题 原因 解决方案
温度换算错误 使用了因子法 使用专门的温度转换函数
精度丢失 因子精度不足 使用更高精度的因子值
显示异常 数值过大或过小 使用科学计数法格式化

9.3 精度说明

⚠️ 精度提示 ⚠️

本应用的换算因子采用标准值,部分单位换算可能存在微小误差。
对于高精度要求的科学计算,建议使用专业工具验证结果。


十、运行说明

10.1 环境要求

环境 版本要求
Flutter SDK >= 3.0.0
Dart SDK >= 2.17.0
鸿蒙OS API 21+

10.2 运行命令

# 查看可用设备
flutter devices

# 运行到鸿蒙设备
flutter run -d 127.0.0.1:5555 lib/main_unit_converter.dart

# 运行到Windows
flutter run -d windows -t lib/main_unit_converter.dart

# 代码分析
flutter analyze lib/main_unit_converter.dart

十一、总结

单位换算大师通过直观的界面设计和精准的换算算法,为用户提供了一个便捷的单位转换工具。应用采用浅色主题设计,符合清爽专业的定位;代码结构清晰,遵循Flutter最佳实践;数据模型设计合理,便于后续扩展更多单位类别。

核心功能涵盖十大类别单位换算,从长度、重量到能量、压强,从公制到英制再到中国传统单位,满足用户在科学研究、工程设计、日常生活等多场景的换算需求。实时计算功能让用户输入即得结果,历史记录和收藏功能便于快速访问常用换算。

特别值得一提的是温度换算功能,采用非线性转换算法精确处理摄氏度、华氏度、开尔文三种温标之间的转换,确保结果的准确性。通过本应用,希望能够帮助用户轻松应对各类单位换算需求,提升工作和学习效率。

精准换算,一触即达

Logo

作为“人工智能6S店”的官方数字引擎,为AI开发者与企业提供一个覆盖软硬件全栈、一站式门户。

更多推荐