【OpenHarmony】sensors_miscdevice小器件模块架构
sensors_miscdevice小器件模块架构
1. 模块概述
源码:https://gitee.com/openharmony/sensors_miscdevice
1.1 功能与目标
小器件模块(sensors_miscdevice)是OpenHarmony系统中用于控制小器件设备的核心模块,主要功能包括:
- 马达振动控制:提供马达振动功能,支持定时振动、预设效果振动、自定义振动等多种模式
- LED灯控制:提供LED灯的开关控制和动画效果控制
- 设备管理:管理多个小器件设备,支持设备插拔检测和状态监控
- 权限管理:提供基于权限的访问控制,确保系统安全性
- 优先级管理:实现振动优先级管理,支持免打扰模式、低电量模式等场景
使用场景:
- 系统通知和提醒
- 用户交互反馈
- 游戏和娱乐应用
- 系统状态指示
1.2 系统位置
小器件模块在OpenHarmony系统中的位置:
- 子系统:sensors(传感器子系统)
- 模块类型:核心服务模块
- 依赖关系:
- 依赖HDF(硬件抽象层)进行硬件控制
- 依赖系统服务框架(SAF)提供服务注册
- 依赖权限管理模块进行访问控制
- 依赖数据共享服务进行配置管理
1.3 设计思路与模式
设计思路:
- 分层架构:采用分层设计,从上到下分为接口层、服务层、适配层和驱动层
- 服务化设计:基于系统服务框架,提供统一的设备控制服务
- 插件化架构:支持多种小器件类型的扩展
- 异步处理:采用多线程和异步处理机制,确保系统响应性
设计模式:
- 单例模式:服务类和连接类采用单例模式,确保全局唯一性
- 代理模式:客户端通过代理对象访问服务
- 观察者模式:设备状态变化通知机制
- 策略模式:不同振动效果的实现策略
- 工厂模式:设备对象的创建和管理
2. 模块结构
2.1 源文件与头文件
2.1.1 核心服务文件
services/miscdevice_service/
├── include/
│ ├── miscdevice_service.h # 主服务类定义
│ ├── vibrator_thread.h # 振动线程管理
│ ├── vibration_priority_manager.h # 振动优先级管理
│ ├── miscdevice_observer.h # 设备状态观察者
│ └── miscdevice_dump.h # 调试转储功能
└── src/├── miscdevice_service.cpp # 主服务实现├── vibrator_thread.cpp # 振动线程实现├── vibration_priority_manager.cpp # 优先级管理实现├── miscdevice_observer.cpp # 观察者实现└── miscdevice_dump.cpp # 调试功能实现
2.1.2 接口层文件
interfaces/
├── inner_api/
│ ├── vibrator/
│ │ ├── vibrator_agent.h # 振动器代理接口
│ │ └── vibrator_agent_type.h # 振动器类型定义
│ └── light/
│ ├── light_agent.h # 灯光代理接口
│ └── light_agent_type.h # 灯光类型定义
└── kits/└── c/├── vibrator.h # C语言振动器接口└── vibrator_type.h # C语言类型定义
2.1.3 框架层文件
frameworks/
├── native/
│ ├── vibrator/
│ │ ├── vibrator_agent.cpp # 振动器代理实现
│ │ ├── include/
│ │ │ ├── i_vibrator_client.h # 振动器客户端接口
│ │ │ └── vibrator_service_client.h # 振动器服务客户端
│ │ └── src/
│ │ └── vibrator_service_client.cpp
│ └── light/
│ ├── light_agent.cpp # 灯光代理实现
│ ├── include/
│ │ └── light_client.h # 灯光客户端
│ └── src/
│ └── light_client.cpp
├── js/
│ └── napi/
│ └── vibrator/
│ ├── src/
│ │ ├── vibrator_js.cpp # JavaScript接口实现
│ │ └── vibrator_napi_utils.cpp
│ └── include/
│ └── vibrator_napi_utils.h
└── capi/└── vibrator.cpp # C API实现
2.2 类、结构体、函数与方法
2.2.1 核心类设计
MiscdeviceService类:
class MiscdeviceService : public SystemAbility, public MiscdeviceServiceStub {
public:// 生命周期管理void OnStart() override;void OnStop() override;// 振动控制接口virtual int32_t Vibrate(const VibratorIdentifierIPC& identifier, int32_t timeOut, int32_t usage, bool systemUsage) override;virtual int32_t PlayVibratorEffect(const VibratorIdentifierIPC& identifier, const std::string &effect, int32_t loopCount, int32_t usage, bool systemUsage) override;virtual int32_t StopVibrator(const VibratorIdentifierIPC& identifier) override;// 灯光控制接口virtual int32_t TurnOn(int32_t lightId, int32_t singleColor, const LightAnimationIPC &animation) override;virtual int32_t TurnOff(int32_t lightId) override;// 设备管理接口virtual int32_t GetVibratorList(const VibratorIdentifierIPC& identifier,std::vector<VibratorInfoIPC>& vibratorInfoIPC) override;virtual int32_t GetLightList(std::vector<LightInfoIPC> &lightInfoIpcList) override;
};
VibratorThread类:
class VibratorThread : public Thread {
public:// 振动控制void UpdateVibratorEffect(const VibrateInfo &vibrateInfo, const VibratorIdentifierIPC& identifier,std::vector<HdfWaveInformation> &waveInfos);VibrateInfo GetCurrentVibrateInfo();void SetExitStatus(bool status);void WakeUp();protected:virtual bool Run() override;private:int32_t PlayOnce(const VibrateInfo &info, const VibratorIdentifierIPC& identifier);int32_t PlayEffect(const VibrateInfo &info, const VibratorIdentifierIPC& identifier);int32_t PlayCustomByHdHptic(const VibrateInfo &info, const VibratorIdentifierIPC& identifier);
};
VibrationPriorityManager类:
class VibrationPriorityManager {
public:bool Init();VibrateStatus ShouldIgnoreVibrate(const VibrateInfo &vibrateInfo,const std::shared_ptr<VibratorThread> &vibratorThread, const VibratorIdentifierIPC& identifier);private:bool IsCurrentVibrate(const std::shared_ptr<VibratorThread> &vibratorThread,const VibratorIdentifierIPC& identifier) const;bool IsLoopVibrate(const VibrateInfo &vibrateInfo) const;VibrateStatus ShouldIgnoreVibrate(const VibrateInfo &vibrateInfo, VibrateInfo currentVibrateInfo) const;
};
2.2.2 主要结构体
VibratorIdentifierIPC:
struct VibratorIdentifierIPC {int32_t deviceId; // 设备IDint32_t vibratorId; // 振动器ID
};
VibrateInfo:
struct VibrateInfo {int32_t duration; // 振动持续时间std::string effectId; // 效果IDint32_t loopCount; // 循环次数int32_t usage; // 使用场景bool systemUsage; // 是否系统使用VibratorParameter parameter; // 振动参数
};
LightAnimationIPC:
struct LightAnimationIPC {int32_t mode; // 动画模式int32_t onTime; // 亮起时间int32_t offTime; // 熄灭时间int32_t count; // 闪烁次数
};
2.3 继承与多态
继承关系:
MiscdeviceService
继承自SystemAbility
和MiscdeviceServiceStub
VibratorThread
继承自Thread
VibratorHdiConnection
继承自IVibratorHdiConnection
和Singleton
LightHdiConnection
继承自ILightHdiConnection
和Singleton
多态设计:
- 通过接口抽象实现多态,支持不同硬件厂商的驱动适配
- 使用策略模式实现不同振动效果的处理
- 观察者模式支持设备状态变化的通知
2.4 类图
2.4.1 核心类关系图
2.4.2 数据结构关系图
2.4.3 接口层类图
3. 模块间交互
3.1 交互描述
与HDF层的交互:
- 通过HDF接口访问硬件驱动
- 支持振动器和LED灯的硬件抽象
- 实现设备插拔检测和状态监控
与系统服务的交互:
- 通过SAF框架注册系统服务
- 与权限管理服务交互进行访问控制
- 与数据共享服务交互获取配置信息
与客户端的交互:
- 提供C/C++、JavaScript等多种语言接口
- 支持同步和异步调用模式
- 实现客户端生命周期管理
异步处理机制:
- 使用多线程处理振动和灯光控制
- 采用条件变量和互斥锁实现线程同步
- 支持优先级队列管理多个振动请求
事件驱动机制:
- 设备插拔事件通知
- 系统状态变化事件(免打扰、低电量等)
- 客户端生命周期事件
3.2 系统架构图
3.3 模块内部依赖框图
4. 状态机转换图
4.1 状态机模型
小器件模块包含多个状态机,主要包括:
服务状态机:
- STATE_STOPPED:服务停止状态
- STATE_RUNNING:服务运行状态
振动状态机:
- IDLE:空闲状态
- VIBRATING:振动中状态
- PAUSED:暂停状态
- STOPPED:停止状态
设备状态机:
- DISCONNECTED:设备断开状态
- CONNECTED:设备连接状态
- ERROR:错误状态
4.2 状态机切换规则
服务状态切换:
- 启动事件:STATE_STOPPED → STATE_RUNNING
- 停止事件:STATE_RUNNING → STATE_STOPPED
振动状态切换:
- 开始振动:IDLE → VIBRATING
- 暂停振动:VIBRATING → PAUSED
- 恢复振动:PAUSED → VIBRATING
- 停止振动:VIBRATING/PAUSED → STOPPED
- 振动完成:VIBRATING → IDLE
设备状态切换:
- 设备插入:DISCONNECTED → CONNECTED
- 设备拔出:CONNECTED → DISCONNECTED
- 设备错误:CONNECTED → ERROR
- 错误恢复:ERROR → CONNECTED
4.3 状态机转换图
4.3.1 服务状态机
4.3.2 振动状态机
4.3.3 设备状态机
4.3.4 振动优先级状态机
5. 接口设计
5.1 公共接口
5.1.1 振动器接口
基础振动接口:
// 开始振动(持续时间)
int32_t StartVibratorOnce(int32_t duration);// 开始振动(预设效果)
int32_t StartVibrator(const char *effectId);// 停止振动
int32_t StopVibrator(const char *mode);// 取消所有振动
int32_t Cancel();
增强振动接口:
// 增强版开始振动(支持设备指定)
int32_t StartVibratorOnceEnhanced(const VibratorIdentifier identifier, int32_t duration);
int32_t StartVibratorEnhanced(const VibratorIdentifier identifier, const char *effectId);// 自定义振动
int32_t PlayVibratorCustom(int32_t fd, int64_t offset, int64_t length);// 振动模式播放
int32_t PlayPattern(const VibratorPattern &pattern);// 原始效果播放
int32_t PlayPrimitiveEffect(const char *effectId, int32_t intensity);
查询接口:
// 查询效果支持
int32_t IsSupportEffect(const char *effectId, bool *state);// 获取振动器列表
int32_t GetVibratorList(const VibratorIdentifier& identifier, std::vector<VibratorInfos>& vibratorInfo);// 获取效果信息
int32_t GetEffectInfo(const VibratorIdentifier& identifier, const std::string& effectType, EffectInfo& effectInfo);// 获取延迟时间
int32_t GetDelayTime(int32_t &delayTime);
5.1.2 灯光接口
基础灯光接口:
// 获取灯光列表
int32_t GetLightList(LightInfo **lightInfo, int32_t &count);// 打开灯光
int32_t TurnOn(int32_t lightId, const LightColor &color, const LightAnimation &animation);// 关闭灯光
int32_t TurnOff(int32_t lightId);
5.2 数据交换接口
IPC接口:
- 使用OpenHarmony IPC机制进行进程间通信
- 支持同步和异步调用模式
- 提供错误码和异常处理机制
HDF接口:
- 通过HDF接口与硬件驱动交互
- 支持设备插拔检测和状态监控
- 提供硬件抽象和统一接口
回调接口:
// 设备插拔回调
typedef void (*DevicePlugCallback)(int32_t eventCode, int32_t deviceId, int32_t vibratorCnt);// 振动器用户回调
struct VibratorUser {VibratorPlugCallback callback;void *userData;
};
5.3 接口调用时序图
5.3.1 振动器调用时序图
5.3.2 灯光控制调用时序图
5.3.3 设备插拔事件时序图
5.3.4 振动优先级管理时序图
6. 总结
小器件模块采用分层架构设计,通过服务化、插件化的方式实现了对小器件设备的统一管理。模块具有良好的扩展性和可维护性,支持多种硬件平台和开发语言接口。通过优先级管理和权限控制,确保了系统的安全性和稳定性。
主要特点:
- 分层架构:清晰的层次结构,便于维护和扩展
- 服务化设计:基于系统服务框架,提供统一的服务接口
- 多语言支持:支持C/C++、JavaScript等多种开发语言
- 权限管理:完善的权限控制机制,确保系统安全
- 优先级管理:智能的振动优先级管理,支持多种使用场景
- 异步处理:多线程异步处理,保证系统响应性
- 设备管理:支持设备插拔检测和状态监控