基于React Native与鸿蒙ArkUI的跨平台提醒应用开发实践
项目概述
本文介绍了一个使用React Native构建的健康提醒应用,该应用具备定时提醒功能、状态管理及用户交互界面。应用采用模块化设计,实现了灵活的提醒管理机制,在鸿蒙OS平台上通过ArkUI/Ability的WorkScheduler和Notification能力实现了跨平台适配。
数据模型设计
提醒应用的核心数据结构如下:
interface TaskNotification {
uuid: string;
name: string;
scheduledTime: string;
isActive: boolean;
symbol: string;
details: string;
recurrence: string;
}
该数据模型具有以下特点:
- 使用唯一标识符确保数据操作精确性
- 状态开关实现灵活控制
- 符号字段支持视觉区分
- 重复模式支持多样化提醒场景
在鸿蒙平台上的数据适配:
interface TaskNotification {
uuid: string;
name: string;
scheduledTime: string;
isActive: boolean;
symbol: string;
details: string;
recurrence: string;
}
enum RecurrencePattern {
DAILY = '每天',
WEEKDAYS = '周一至周五',
CUSTOM = '自定义'
}
提醒卡片组件实现
提醒卡片是应用的核心UI组件,实现如下:
const NotificationCard = ({ item, onStatusChange, onRemove }) => {
return (
<View style={styles.cardContainer}>
<View style={styles.cardHeader}>
<View style={styles.iconContainer}>
<Text style={styles.iconSymbol}>{item.symbol}</Text>
</View>
<View style={styles.infoContainer}>
<Text style={styles.titleText}>{item.name}</Text>
<Text style={styles.timeText}>{item.scheduledTime}</Text>
<Text style={styles.descriptionText}>{item.details}</Text>
</View>
<View style={styles.controlContainer}>
<Switch
value={item.isActive}
onValueChange={() => onStatusChange(item.uuid)}
/>
<TouchableOpacity onPress={() => onRemove(item.uuid)}>
<Text style={styles.removeText}>删除</Text>
</TouchableOpacity>
</View>
</View>
<View style={styles.recurrenceContainer}>
<Text style={styles.recurrenceText}>{item.recurrence}</Text>
</View>
</View>
);
};
鸿蒙平台上的组件实现:
@Component
struct NotificationCard {
@Prop item: TaskNotification;
@Prop onStatusChange: (uuid: string) => void;
@Prop onRemove: (uuid: string) => void;
build() {
Column() {
Row() {
// 图标区域
Column() {
Text(this.item.symbol)
}
.width(48)
.height(48)
.backgroundColor('#f1f5f9')
.borderRadius(24)
// 信息区域
Column() {
Text(this.item.name)
Text(this.item.scheduledTime)
Text(this.item.details)
}
// 控制区域
Column() {
Toggle({ type: ToggleType.Switch, isOn: this.item.isActive })
.onChange(() => this.onStatusChange(this.item.uuid))
Button('删除', { type: ButtonType.Normal })
.onClick(() => this.onRemove(this.item.uuid))
}
}
// 重复信息
Text(this.item.recurrence)
}
.backgroundColor(Color.White)
.borderRadius(12)
.padding(16)
}
}
状态管理系统
应用采用React的状态管理机制:
const changeNotificationStatus = (uuid: string) => {
setNotifications(prevState =>
prevState.map(item =>
item.uuid === uuid ? { ...item, isActive: !item.isActive } : item
)
);
};
const removeNotification = (uuid: string) => {
setNotifications(prevState => prevState.filter(item => item.uuid !== uuid));
};
鸿蒙平台的状态管理实现:
@State notifications: TaskNotification[] = [];
changeNotificationStatus(uuid: string) {
this.notifications = this.notifications.map(item =>
item.uuid === uuid ? { ...item, isActive: !item.isActive } : item
);
}
removeNotification(uuid: string) {
this.notifications = this.notifications.filter(item => item.uuid !== uuid);
}
用户交互设计
删除提醒时的用户确认机制:
const removeNotification = (uuid: string) => {
Alert.alert(
'删除提醒',
'确定要删除这个提醒吗?',
[
{ text: '取消', style: 'cancel' },
{ text: '删除', onPress: () => setNotifications(prev => prev.filter(item => item.uuid !== uuid)) }
]
);
};
鸿蒙平台的对话框实现:
async removeNotification(uuid: string) {
const result = await prompt.showDialog({
title: '删除提醒',
message: '确定要删除这个提醒吗?',
buttons: [
{ text: '取消', color: '#666666' },
{ text: '删除', color: '#FF0000' }
]
});
if (result.index === 1) {
this.notifications = this.notifications.filter(item => item.uuid !== uuid);
}
}
界面布局设计
统计卡片组件实现:
const StatsDisplay = ({ symbol, value, label }) => {
return (
<View style={styles.statsItem}>
<Text style={styles.statsSymbol}>{symbol}</Text>
<Text style={styles.statsValue}>{value}</Text>
<Text style={styles.statsLabel}>{label}</Text>
</View>
);
};
鸿蒙平台的统计卡片实现:
@Component
struct StatsDisplay {
@Prop symbol: string;
@Prop value: string;
@Prop label: string;
build() {
Column() {
Text(this.symbol)
Text(this.value)
Text(this.label)
}
.alignItems(HorizontalAlign.Center)
}
}
导航系统实现
标签导航系统:
const [currentTab, setCurrentTab] = useState('notifications');
<TouchableOpacity
style={[styles.tabItem, currentTab === 'notifications' && styles.activeTabItem]}
onPress={() => setCurrentTab('notifications')}
>
<Text style={[styles.tabText, currentTab === 'notifications' && styles.activeTabText]}>
我的提醒
</Text>
</TouchableOpacity>
鸿蒙平台的导航实现:
@State currentTab: string = 'notifications';
Tabs({ index: this.currentTab === 'notifications' ? 0 : 1 }) {
TabContent() {
// 我的提醒
}
TabContent() {
// 快捷提醒
}
}
.onChange((index: number) => {
this.currentTab = index === 0 ? 'notifications' : 'quick';
})
跨平台适配策略
组件映射关系表:
| React Native组件 | 鸿蒙ArkUI组件 | 关键适配点 |
|---|---|---|
| Switch | Toggle | 样式和事件处理差异 |
| Alert.alert | prompt.showDialog | 配置格式不同 |
| TouchableOpacity | Button | 交互反馈机制差异 |
| ScrollView | Scroll | 滚动行为基本一致 |
鸿蒙平台的核心实现
在鸿蒙平台上,提醒功能的核心实现依赖于以下几个系统能力:
- WorkScheduler:用于定时任务的调度和管理
- Notification:负责通知的显示和管理
- Ability:提供应用的生命周期管理
统一的接口设计:
interface NotificationBridge {
scheduleNotification(task: TaskNotification): Promise<void>;
cancelNotification(uuid: string): Promise<void>;
requestNotificationPermission(): Promise<boolean>;
checkNotificationPermission(): Promise<boolean>;
}
权限处理机制
在鸿蒙平台上,提醒功能需要处理以下权限:
- 通知权限:用于显示提醒通知
- 振动权限:控制提醒时的振动反馈
- 后台运行权限:确保应用在后台时仍能触发提醒
权限检查与请求的统一接口:
async function ensurePermissions() {
const hasNotificationPermission = await NotificationBridge.checkNotificationPermission();
if (!hasNotificationPermission) {
const granted = await NotificationBridge.requestNotificationPermission();
if (!granted) {
// 引导用户到设置页面
return false;
}
}
return true;
}
时间处理与本地化
提醒时间的处理需要考虑时区和本地化:
function formatTimeForPlatform(timeString: string, timezone: string): string {
// 将时间字符串转换为平台特定格式
const [hours, minutes] = timeString.split(':').map(Number);
const date = new Date();
date.setHours(hours, minutes, 0, 0);
// 根据时区调整时间
return date.toLocaleTimeString('zh-CN', {
hour: '2-digit',
minute: '2-digit',
timeZone: timezone
});
}
应用打包与部署
将React Native应用打包为鸿蒙平台可用的bundle:
# 打包命令
npm run harmony
打包完成后,将生成的鸿蒙文件复制到DevEco-Studio工程目录中,即可在鸿蒙设备上运行和测试应用。
通过以上实现,我们成功地将React Native应用适配到鸿蒙平台,实现了跨平台的提醒功能,为用户提供了统一的体验。
