极物科技 | DALI协议栈 - 标准命令集解析
前言
在智能控制领域,"协议壁垒"与"系统稳定性"始终是绕不开的难题。极物科技(Zeewo)以 "重构空间交互体验" 为使命,通过自研的 极物 OS,实现了 KNX、DALI、CAN、RS485 等多种总线协议在单一主机上的深度融合。
我们认为,一个真正优秀的智能系统,不仅要实现灯光、遮阳、温控、音乐、安防等全生态设备的无界融合 ,更要确保本地运行、断网可用 ,并具备WEB 远程调试 和 OTA 固件升级的能力。基于此底层架构,我们推出了诸如带双路 DALI 的 KNX 主机、HomeKit 网桥等核心硬件,并将极物 OS 成功接入了 Apple HomeKit、小度、纯血鸿蒙及 HomeAssistant 等主流生态系统。
一句话概述:本文深入解析极物 DALI 协议栈 0-31 标准命令集的完整实现逻辑。
本文聚焦于 DALI 基础控制命令与场景调用命令,涵盖 OFF/UP/DOWN/STEP、RECALL MAX/MIN、GO TO SCENE 等核心命令的处理流程、渐变引擎触发、状态机更新等关键机制。


1. 命令分类总览
1.1 基础控制命令 (0-10)
| 命令值 | 命令名称 | 功能说明 |
|---|---|---|
| 0 | OFF | 关灯(无渐变) |
| 1 | UP | 向上调光 200ms |
| 2 | DOWN | 向下调光 200ms |
| 3 | STEP_UP | 亮度 +1(无渐变) |
| 4 | STEP_DOWN | 亮度 -1(无渐变) |
| 5 | RECALL_MAX_LEVEL | 调至最大亮度 |
| 6 | RECALL_MIN_LEVEL | 调至最小亮度 |
| 7 | STEP_DOWN_AND_OFF | 亮度 -1,到最小则关 |
| 8 | ON_AND_STEP_UP | 开灯并 +1 |
| 9 | ENABLE_DAPC_SEQUENCE | 启用 DAPC 序列 |
| 10 | GO_TO_LAST_ACTIVE_LEVEL | 恢复上次亮度 |
1.2 场景调用命令 (16-31)
| 命令值 | 命令名称 | 功能说明 |
|---|---|---|
| 16~31 | GO_TO_SCENE 0~15 | 调用场景 0~15 |
2. 命令处理入口
c
uint16_t dali_cmd_process_normal(dali_slave_service_info_t *slave_info, uint8_t repeat_flag) {
if (slave_info->rec_data >= REFERENCE_SYSTEM_POWER) {
// 扩展应用命令 (224-255)
return dali_cmd_process_extended_application(slave_info, repeat_flag);
} else {
// 标准命令 (0-223)
return dali_cmd_process_common(slave_info, repeat_flag);
}
}
3. 基础控制命令详解
3.1 OFF 命令 (0)
功能:立即关灯,无渐变过程。
c
case OFF:
dali_cmd_direct_arc_power_control(0);
break;
执行流程:
c
void dali_cmd_direct_arc_power_control(uint8_t level) {
device_enabled = false;
write_memory_enabled = false;
if (level == 0) {
if (dali.s.level == dali_ram.variable.minimum_level) {
// 从最小亮度关到 OFF
fade_direction = FADE_BETWEEN_MINLEVEL_AND_OFF;
} else {
// 渐变到最小亮度后关闭
fade_direction = FADE_TIME_DOWN_OFF;
level_change = (dali.s.level - dali_ram.variable.minimum_level);
}
}
dali_ram.variable.target_level = 0;
// 计算渐变步进
fade_step = flash_inv_fadetime_val[fade_time] * level_change;
fade_step = fade_step >> 1;
status_information &= ~LAMP_ON; // 清除开灯标志
}
3.2 UP 命令 (1)
功能:以设定的渐变速度向上调光 200ms。
c
case UP:
status_information |= LAMP_ON;
status_information &= ~LAMP_FAILURE;
if (status_information & LAMP_ON) {
if (dali.s.level < dali_ram.variable.maximum_level) {
fade_direction = FADE_RATE_UP;
current_fade_time = W200MS;
current_fade = dali_ram.variable.fade_rate;
fade_step = flash_fade_rate_val[current_fade];
fade_step = fade_step << 7; // 左移 7 bit
need_fade = true;
status_information |= FADE_RUNNING;
} else {
status_information |= LIMIT_ERROR;
fade_direction = FADE_STOP;
}
} else {
fade_direction = FADE_STOP; // 灯灭时不执行
}
light_flag = true;
break;
关键点:
- 使用
fade_rate而非fade_time - 固定 200ms 调光时长
- 灯灭状态下无效
3.3 DOWN 命令 (2)
功能:以设定的渐变速度向下调光 200ms。
c
case DOWN:
if (status_information & LAMP_ON) {
if (dali.s.level > dali_ram.variable.minimum_level) {
fade_direction = FADE_RATE_DOWN;
current_fade_time = W200MS;
current_fade = dali_ram.variable.fade_rate;
fade_step = flash_fade_rate_val[current_fade];
fade_step = fade_step << 7;
need_fade = true;
status_information |= FADE_RUNNING;
} else {
status_information |= LIMIT_ERROR;
fade_direction = FADE_STOP;
}
} else {
fade_direction = FADE_STOP;
}
light_flag = true;
break;
3.4 STEP_UP 命令 (3)
功能:亮度立即 +1,无渐变。
c
case STEP_UP:
if (status_information & LAMP_ON) {
if (dali.s.level < dali_ram.variable.maximum_level) {
dali.s.level = dali.s.level + 1;
dali_ram.variable.target_level = dali.s.level;
status_information &= ~LIMIT_ERROR;
} else {
status_information |= LIMIT_ERROR;
}
fade_direction = FADE_DIRECT;
}
light_flag = true;
break;
3.5 STEP_DOWN 命令 (4)
功能:亮度立即 -1,无渐变。
c
case STEP_DOWN:
if (status_information & LAMP_ON) {
if (dali.s.level > dali_ram.variable.minimum_level) {
dali.s.level = dali.s.level - 1;
dali_ram.variable.target_level = dali.s.level;
status_information &= ~LIMIT_ERROR;
} else {
status_information |= LIMIT_ERROR;
}
fade_direction = FADE_DIRECT;
}
light_flag = true;
break;
3.6 RECALL_MAX_LEVEL 命令 (5)
功能:调至最大亮度(可触发识别模式)。
c
case RECALL_MAX_LEVEL:
dali_cmd_direct_arc_power_control(dali_ram.variable.maximum_level);
light_flag = true;
break;
识别模式处理(代码中被注释):
c
// 原始逻辑:
if (w15min_waiting_time > 0) {
// 处于初始化窗口,进入识别模式
fade_direction = FADE_DIRECT_IDENTIFICATION;
recall_level_flag = MAX_LEVEL_FLAG;
} else {
fade_direction = FADE_DIRECT;
}
3.7 RECALL_MIN_LEVEL 命令 (6)
功能:调至最小亮度。
c
case RECALL_MIN_LEVEL:
dali_cmd_direct_arc_power_control(dali_ram.variable.minimum_level);
light_flag = true;
break;
3.8 STEP_DOWN_AND_OFF 命令 (7)
功能:亮度 -1,如果已在最小亮度则关灯。
c
case STEP_DOWN_AND_OFF:
if (dali.s.level <= dali_ram.variable.minimum_level) {
dali_ram.variable.target_level = 0;
dali.long_level = 0;
} else {
dali.s.level = dali.s.level - 1;
dali_ram.variable.target_level = dali.s.level;
}
status_information &= ~LIMIT_ERROR;
fade_direction = FADE_DIRECT;
light_flag = true;
break;
3.9 ON_AND_STEP_UP 命令 (8)
功能:如果灯灭则开至最小亮度,否则亮度 +1。
c
case ON_AND_STEP_UP:
if (dali.s.level == 0) {
dali.s.level = dali_ram.variable.minimum_level;
dali_ram.variable.target_level = dali.s.level;
status_information &= ~LIMIT_ERROR;
} else if (dali.s.level < dali_ram.variable.maximum_level) {
dali.s.level = dali.s.level + 1;
dali_ram.variable.target_level = dali.s.level;
status_information &= ~LIMIT_ERROR;
} else {
status_information |= LIMIT_ERROR;
}
fade_direction = FADE_DIRECT;
light_flag = true;
break;
3.10 ENABLE_DAPC_SEQUENCE 命令 (9)
功能:标记 DAPC 序列开始,后续调光使用快速渐变。
c
case ENABLE_DAPC_SEQUENCE:
dapc_sequence = true;
dapc_sequence_time = W200MS;
break;
DAPC 序列中的调光:
c
if (dapc_sequence == true) {
if (dali.s.level == 0) {
// 当前为 0,直接设置目标值
dali.s.level = level;
fade_direction = FADE_DIRECT;
} else {
// 使用 fade_rate = 1(最快速度)
current_fade = 1;
dapc_sequence_time = W200MS;
}
}
3.11 GO_TO_LAST_ACTIVE_LEVEL 命令 (10)
功能:恢复到上次非 OFF 状态的亮度。
c
case GO_TO_LAST_ACTIVE_LEVEL:
if (dali.s.level != last_active_level) {
dali_cmd_direct_arc_power_control(last_active_level);
}
light_flag = true;
break;
last_active_level 更新时机:
c
// 在 dali_cmd_direct_arc_power_control 中
if (level != 0) {
last_active_level = level; // 记录非零亮度值
}
4. 场景调用命令 (16-31)
4.1 场景调用逻辑
c
case GO_TO_SCENE0:
case GO_TO_SCENE1:
// ... 到 GO_TO_SCENE15
temp = dali_ram.variable.scene[slave_info->rec_data & 0x0F];
// 场景值不为 MASK 才执行
if (temp != POWER_MASK) {
power_on_flag = false;
dali_cmd_direct_arc_power_control(temp);
// 同时设置色温
temp = dali_ram.variable.tc_scene[slave_info->rec_data & 0x0F];
if (temp != POWER_MASK) {
dali_cmd_direct_arc_tc_control(temp);
}
}
status_information &= ~POWER_CYCLE_SEEN;
break;
4.2 场景值说明
| 场景值 | 含义 |
|---|---|
| 0~254 | 有效亮度/色温值 |
| 255 (MASK) | 该场景未配置,不改变当前状态 |
4.3 场景调用示例
场景 3 配置:
scene[3] = 180 // 亮度 180
tc_scene[3] = 200 // 色温 200
调用场景 3:
→ dali_cmd_direct_arc_power_control(180)
→ dali_cmd_direct_arc_tc_control(200)
→ 亮度渐变到 180,色温渐变到 200
5. 渐变方向枚举
c
enum {
FADE_IDLE, // 空闲
FADE_STOP, // 停止渐变
FADE_TIME_UP, // 按时间向上渐变
FADE_TIME_DOWN, // 按时间向下渐变
FADE_TIME_DOWN_OFF, // 渐变到最小后关闭
FADE_RATE_UP, // 按速度向上渐变
FADE_RATE_DOWN, // 按速度向下渐变
FADE_DIRECT, // 直接设置(无渐变)
FADE_DIRECT_IDENTIFICATION, // 直接设置 + 识别模式
FADE_PENDING, // 等待执行
FADE_BETWEEN_MINLEVEL_AND_OFF // 最小亮度与 OFF 之间渐变
};
6. 渐变参数表
6.1 渐变时间表 (fade_time)
c
// fade_time 对应实际时间
uint16_t tc_fade_time[] = {
0, 700, 1000, 1400, 2000, 2800, 4000, 5700,
8000, 11300, 16000, 22600, 32000, 45300, 64000, 90500
};
| fade_time | 实际时间 |
|---|---|
| 0 | 0s (直接) |
| 1 | 0.7s |
| 2 | 1.0s |
| 3 | 1.4s |
| 4 | 2.0s |
| 5 | 2.8s |
| 6 | 4.0s |
| 7 | 5.7s |
| 8 | 8.0s |
| 9 | 11.3s |
| 10 | 16.0s |
| 11 | 22.6s |
| 12 | 32.0s |
| 13 | 45.3s |
| 14 | 64.0s |
| 15 | 90.5s |
6.2 渐变速度表 (fade_rate)
c
uint16_t const flash_fade_rate_val[] = {
0x0000, 0xB731, 0x8189, 0x5B99, 0x40C5,
0x2DCC, 0x2062, 0x16E6, 0x1031, 0x0B73,
0x0819, 0x05BA, 0x040C, 0x02DD, 0x0206, 0x016E
};
fade_rate 值越大,渐变速度越慢。
6.3 渐变时间倒数表
c
uint32_t const flash_inv_fadetime_val[] = {
0x0000, 0xB964, 0x8312, 0x5CB2, 0x4189,
0x2E59, 0x20C5, 0x172B, 0x1062, 0x0B96,
0x0831, 0x05CB, 0x0419, 0x02E5, 0x020C, 0x0173
};
用于计算 fade_step:
c
fade_step = flash_inv_fadetime_val[fade_time];
fade_step = fade_step * level_change;
fade_step = fade_step >> 1;
7. 状态标志更新
7.1 light_flag 作用
以下命令执行后会设置 light_flag = true:
- UP, DOWN, STEP_UP, STEP_DOWN
- RECALL_MAX_LEVEL, RECALL_MIN_LEVEL
- STEP_DOWN_AND_OFF, ON_AND_STEP_UP
- GO_TO_LAST_ACTIVE_LEVEL
- GO_TO_SCENE 0~15
light_flag 触发清理:
c
if (light_flag == true) {
status_information &= ~POWER_CYCLE_SEEN; // 清除上电标志
dapc_sequence = false; // 清除 DAPC 序列
power_on_flag = false; // 清除上电标志
}
7.2 LIMIT_ERROR 标志
当亮度超出范围时设置:
c
if (level < dali_ram.variable.minimum_level) {
level = dali_ram.variable.minimum_level;
status_information |= LIMIT_ERROR;
} else if (level > dali_ram.variable.maximum_level) {
level = dali_ram.variable.maximum_level;
status_information |= LIMIT_ERROR;
}
7.3 FADE_RUNNING 标志
渐变进行中设置:
c
if (need_fade) {
status_information |= FADE_RUNNING;
}
8. 注意事项
- DAPC 命令 :S=0 时直接调用
dali_cmd_direct_arc_power_control(),无需重复帧 - 场景 MASK:场景值为 255 时不执行任何操作
- UP/DOWN 限制:灯灭状态下 UP/DOWN 无效
- 渐变速度:fade_rate=0 保留不用,有效范围 1~15
- last_active_level:仅在亮度非 0 时更新
- LIMIT_ERROR:亮度被限制在 min~max 范围内时设置
9. 相关文档
- 《极物科技 | DALI协议栈 - 架构总览与模块设计》
- 《极物科技 | DALI协议栈 - 物理层位编解码详解》
- 《极物科技 | DALI协议栈 - 帧传输状态机与地址解析》
- 《极物科技 | DALI协议栈 - 配置命令详解》
- 《极物科技 | DALI协议栈 - 查询命令全解》
- 《极物科技 | DALI调光灯 - 快速接入指南》
关于极物科技(ZEEWO)
极物科技(Zeewo)致力于为用户提供智能控制系统及硬件产品。我们以总线系统为技术底座,以**"稳定、可靠、快速响应"**为产品底线,是国内少有的拥有 KNX、DALI 全套软硬件自主研发能力的厂商之一。
我们的核心能力:
- 系统架构:自研极物 OS,支持多协议无界融合(KNX/DALI/CAN/RS485/IP)。
- 核心硬件:带双路 DALI 的 KNX 主机、超薄全金属定制面板、各类智选传感器及网关。
- 生态互联:深度融入 Apple HomeKit、Matter、小度、HomeAssistant 及纯血鸿蒙生态。
- 调试交付:独家支持 ETS 导出 XML 直接导入进行 APP 免编程调试,支持远程 WEB 运维。
我们的市场覆盖:
服务网点已覆盖全国核心城市(含长三角、珠三角、成渝等),并以高品质的方案深耕家居生活、酒店民宿、企业办公、疗愈康养、餐馆会所等多个细分领域。
(如果您在开发或落地中遇到技术问题,欢迎通过官网或后台私信与我交流探讨)

