HarmonyOS 6(API 23)实战:基于悬浮导航、沉浸光感与HMAF的“光脉智城“——PC端AI智能体沉浸式智慧交通态势感知与调度指挥中心

文章目录

    • 每日一句正能量
    • 前言
    • 一、前言:城市交通进入"智能体驱动"时代
    • 二、核心特性解析与技术选型
      • [2.1 HMAF在智慧交通态势感知中的价值](#2.1 HMAF在智慧交通态势感知中的价值)
      • [2.2 沉浸光感在交通调度中的创新应用](#2.2 沉浸光感在交通调度中的创新应用)
      • [2.3 技术选型总览](#2.3 技术选型总览)
    • 三、项目实战:"光脉智城"架构设计
      • [3.1 应用场景与功能规划](#3.1 应用场景与功能规划)
      • [3.2 技术架构图](#3.2 技术架构图)
    • 四、环境配置与模块依赖
      • [4.1 模块依赖配置](#4.1 模块依赖配置)
      • [4.2 权限声明(module.json5)](#4.2 权限声明(module.json5))
    • 五、核心组件实战
      • [5.1 窗口沉浸配置(EntryAbility.ets)](#5.1 窗口沉浸配置(EntryAbility.ets))
      • [5.2 拥堵等级光效系统(CongestionLightEffect.ets)](#5.2 拥堵等级光效系统(CongestionLightEffect.ets))
      • [5.3 HMAF四层交通智能体架构(TrafficAgentScheduler.ets)](#5.3 HMAF四层交通智能体架构(TrafficAgentScheduler.ets))
      • [5.4 悬浮态势导航(TrafficFloatNavigation.ets)](#5.4 悬浮态势导航(TrafficFloatNavigation.ets))
      • [5.5 主态势感知大屏(TrafficAwarenessPage.ets)](#5.5 主态势感知大屏(TrafficAwarenessPage.ets))
      • [5.6 浮动路口监控窗口(IntersectionMonitorAbility.ets)](#5.6 浮动路口监控窗口(IntersectionMonitorAbility.ets))
      • [5.7 多窗口光效同步管理器(WindowLightSync.ets)](#5.7 多窗口光效同步管理器(WindowLightSync.ets))
    • 六、关键技术总结
      • [6.1 HMAF智慧交通开发清单](#6.1 HMAF智慧交通开发清单)
      • [6.2 沉浸光感实现清单](#6.2 沉浸光感实现清单)
      • [6.3 拥堵等级光效映射](#6.3 拥堵等级光效映射)
      • [6.4 PC端多窗口光效协同](#6.4 PC端多窗口光效协同)
    • 七、调试与适配建议
      • [7.1 交通数据解析性能优化](#7.1 交通数据解析性能优化)
      • [7.2 拥堵光效可访问性](#7.2 拥堵光效可访问性)
      • [7.3 多窗口管理优化](#7.3 多窗口管理优化)
    • 八、运行效果展示
      • [8.1 畅通态势 - 柔绿光效](#8.1 畅通态势 - 柔绿光效)
      • [8.2 缓行态势 - 淡蓝光效](#8.2 缓行态势 - 淡蓝光效)
      • [8.3 拥堵态势 - 暖黄光效](#8.3 拥堵态势 - 暖黄光效)
      • [8.4 严重拥堵态势 - 橙红光效](#8.4 严重拥堵态势 - 橙红光效)
      • [8.5 瘫痪态势 - 警示红光效](#8.5 瘫痪态势 - 警示红光效)
    • 九、总结与展望

每日一句正能量

太过精明的算计,只会困住自己的格局。

事事算得失、计较回报、衡量利弊,看起来聪明,实际上会让人变得狭隘。因为你所有的注意力都放在了"会不会吃亏""有没有好处"上,反而看不见更大的可能性、更纯粹的连接、更远的风景。真正的格局是能包容一些"不划算"的事情,能承受暂时的"吃亏",因为你知道更大的收获往往不在算盘里。

前言

摘要:2026年,中国城镇化率突破70%,城市机动车保有量超过4.5亿辆,传统交通指挥中心面临数据孤岛严重、态势研判滞后、调度响应缓慢三大痛点。HarmonyOS 6(API 23)引入的鸿蒙智能体框架(HMAF)将AI能力下沉至系统层,配合悬浮导航与沉浸光感特性,为PC端智慧交通态势感知与调度指挥带来了"路况即光效、拥堵即导航"的全新交互范式。本文将实战开发一款面向HarmonyOS PC的"光脉智城"应用,展示如何利用HMAF构建"数据采集-态势研判-拥堵预测-智能调度"四层智能体协作架构,通过悬浮导航实现交通态势实时追踪,基于沉浸光感打造"拥堵等级即氛围"的沉浸体验,以及基于多窗口架构构建浮动路口监控窗口、车流热力图窗口和信号调优窗口的协作调度体验。


一、前言:城市交通进入"智能体驱动"时代

2026年,中国智慧交通市场规模已突破1.2万亿元,全国超过500个城市启动了智能交通系统建设。然而,传统交通指挥中心面临三大核心痛点:

  1. 数据孤岛严重:视频监控、地磁线圈、浮动车GPS、公交IC卡等数据分散在不同系统,交通态势感知延迟高达5-15分钟,无法支撑实时决策
  2. 态势研判滞后:人工观察视频墙判断拥堵,从发现拥堵到完成成因分析平均需要20分钟,早高峰期间拥堵扩散速度是研判速度的3倍
  3. 调度响应缓慢:信号灯配时调整依赖人工经验,跨路口协调需要逐级上报审批,从发现拥堵到实施信号优化平均需要45分钟

HarmonyOS 6(API 23)的HMAF框架配合**悬浮导航(Float Navigation)沉浸光感(Immersive Light Effects)**特性,为智慧交通态势感知与调度指挥带来了革命性解决方案:

  • 智能体协同感知:HMAF构建的"交通智能体"可实时融合多源数据,自动研判拥堵成因与扩散趋势,态势感知延迟降至秒级,研判效率提升50倍
  • 拥堵等级光效感知:根据当前路网拥堵状态(畅通/缓行/拥堵/严重拥堵/瘫痪)动态切换环境光色,让调度员"看见"交通态势
  • 悬浮态势导航:底部悬浮导航实时显示四大智能体运行状态与路网统计徽章,调度员无需切换页面即可掌握全局交通态势
  • PC多窗口协作调度:主态势感知大屏 + 浮动路口监控窗口 + 浮动车流热力图窗口 + 浮动信号调优窗口的四层架构,通过光效联动实现"一眼全局"

本文核心亮点

  • 拥堵等级光效:五种交通状态拥有专属光效人格(畅通柔绿、缓行淡蓝、拥堵暖黄、严重拥堵橙红、瘫痪警示红),根据当前路网最高拥堵等级动态切换全局环境光、路段脉冲和导航材质
  • 悬浮态势导航:底部悬浮页签替代传统工具栏,支持态势总览/路口监控/车流分析/信号调度切换,实时显示拥堵统计徽章(瘫痪/严重拥堵/拥堵数量)
  • HMAF四层交通架构:基于Agent Framework Kit构建"数据采集-态势研判-拥堵预测-智能调度"四层智能体协作体系
  • 多窗口光效联动:主态势窗口 + 浮动路口监控 + 浮动车流热力图 + 浮动信号调优的光效同步与焦点感知
  • 调度意图沉浸感知:通过Intents Kit实时理解调度员的查询意图,自动调整界面光效与导航形态

二、核心特性解析与技术选型

2.1 HMAF在智慧交通态势感知中的价值

HarmonyOS 6的HMAF采用四层架构设计:应用智能体层、智能体框架层、AI引擎层、智能体内核层。在"光脉智城"中,这种架构能够:

  • 原生智能调度:交通智能体不再是独立系统的附属插件,而是系统的基础能力,支持跨路口、跨区域协同调度
  • 意图即调度:通过Intents Kit将调度员自然语言意图(如"查找中山路与建设大道交叉口过去一小时的拥堵成因")转化为结构化分析任务
  • 分布式智能体协同:利用鸿蒙分布式软总线,实现PC主控+大屏展示+移动端现场巡查的多设备协作
  • 端云协同推理:端侧处理实时数据融合与初步筛选,云端大模型处理复杂拥堵成因分析与信号优化方案生成

2.2 沉浸光感在交通调度中的创新应用

HarmonyOS 6的 systemMaterialEffect 通过模拟物理光照模型,为交通状态反馈带来细腻的视觉表达。在智慧交通场景中,这种材质效果能够:

  • 增强拥堵感知:不同拥堵等级拥有专属光效标识(畅通柔绿、缓行淡蓝、拥堵暖黄、严重拥堵橙红、瘫痪警示红)
  • 状态直觉感知:数据采集时的呼吸蓝光、态势研判时的脉冲金光、发现拥堵时的警示红光、调度完成时的确认绿光
  • 提升调度专注度:动态环境光随路网拥堵密度变化,平峰期柔和、高峰期强烈,帮助调度员快速进入"战时状态"

2.3 技术选型总览

功能模块 技术实现 沉浸光感/HMAF应用
主态势感知大屏 Canvas + 自定义绘制 路网节点光效、车流链路流光
悬浮态势导航 HdsTabs + systemMaterialEffect 玻璃拟态页签,拥堵统计徽章
数据采集智能体 HMAF Agent Framework Kit 采集进度光效反馈
态势研判智能体 HMAF + 交通流模型 拥堵类型光效标记
拥堵预测智能体 HMAF + 时序预测模型 预测置信度光效脉冲
智能调度智能体 HMAF + 信号优化引擎 调度完成光效提示
浮动路口监控窗口 子窗口 + Video 路口拥堵等级颜色编码
浮动车流热力图窗口 子窗口 + Canvas 热力强度颜色编码
浮动信号调优窗口 子窗口 + Form 优化方案状态光效标记

三、项目实战:"光脉智城"架构设计

3.1 应用场景与功能规划

面向HarmonyOS PC的智慧交通态势感知与调度指挥场景,核心功能包括:

主态势感知大屏:实时展示城市路网拓扑、路口拥堵状态、车流分布热力图,支持缩放与区域切换

路口监控模块:实时路口视频流、车流量统计、排队长度检测、异常事件识别

车流分析模块:实时车流监控、OD分析、路径偏好统计、异常车流检测

信号调度模块:信号灯配时优化、绿波协调、紧急车辆优先、公交优先

浮动路口监控窗口:悬浮展示选中路口的实时视频与流量数据,状态颜色随拥堵等级变化

浮动车流热力图窗口:悬浮展示选中区域的车流热力分布,热力强度颜色编码

浮动信号调优窗口:悬浮展示当前执行的信号优化方案,步骤状态光效反馈

3.2 技术架构图

plain

plain 复制代码
┌─────────────────────────────────────────────────────────────┐
│                    光脉智城 - 应用层                          │
├─────────────────────────────────────────────────────────────┤
│  ┌─────────────┐  ┌─────────────┐  ┌─────────────────────┐  │
│  │ 主态势大屏   │  │ 悬浮态势导航 │  │ 浮动窗口组          │  │
│  │ (Canvas)    │  │ (HdsTabs)   │  │ (路口监控/热力图/   │  │
│  │             │  │             │  │  信号调优)            │  │
│  └─────────────┘  └─────────────┘  └─────────────────────┘  │
├─────────────────────────────────────────────────────────────┤
│                    HMAF 智能体调度层                         │
│  ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐      │
│  │数据采集Agent│ │态势研判Agent│ │拥堵预测Agent│ │智能调度Agent│      │
│  └──────────┘ └──────────┘ └──────────┘ └──────────┘      │
├─────────────────────────────────────────────────────────────┤
│                    系统服务层                                │
│  Intents Kit │ Agent Framework Kit │ Window Manager │ Light  │
│              │                     │                │ Effect │
└─────────────────────────────────────────────────────────────┘

四、环境配置与模块依赖

4.1 模块依赖配置

JSON

json 复制代码
// entry/oh-package.json5
{
  "dependencies": {
    "@kit.AgentFrameworkKit": "^1.0.0",
    "@kit.IntentsKit": "^1.0.0",
    "@kit.ArkUI": "^1.0.0",
    "@kit.WindowManagerKit": "^1.0.0",
    "@kit.LightEffectKit": "^1.0.0",
    "@kit.MediaKit": "^1.0.0",
    "@kit.LocationKit": "^1.0.0"
  }
}

4.2 权限声明(module.json5)

JSON

json 复制代码
{
  "module": {
    "name": "entry",
    "type": "entry",
    "description": "光脉智城 - 智慧交通态势感知与调度指挥",
    "mainElement": "EntryAbility",
    "requestPermissions": [
      {
        "name": "ohos.permission.INTERNET",
        "reason": "交通数据实时采集与同步"
      },
      {
        "name": "ohos.permission.LOCATION",
        "reason": "路网位置信息采集"
      },
      {
        "name": "ohos.permission.CAMERA",
        "reason": "路口视频监控采集"
      },
      {
        "name": "ohos.permission.SYSTEM_FLOAT_WINDOW",
        "reason": "浮动窗口展示"
      },
      {
        "name": "ohos.permission.LIGHT_EFFECT_CONTROL",
        "reason": "沉浸光效控制"
      }
    ]
  }
}

五、核心组件实战

5.1 窗口沉浸配置(EntryAbility.ets)

代码亮点 :本模块实现了PC端全屏沉浸式交通态势感知窗口。通过 setWindowLayoutFullScreen(true) 移除系统标题栏,配合 expandSafeArea 扩展安全区至全屏,最大化态势展示区域。同时注册窗口焦点变化监听,实现"焦点即光效"的感知降级------当窗口失焦时自动降低背景光效强度,减少干扰。

TypeScript

typescript 复制代码
// entry/src/main/ets/entryability/EntryAbility.ets
import { AbilityConstant, UIAbility, Want } from '@kit.AbilityKit';
import { window } from '@kit.ArkUI';
import { LightEffectManager } from '../services/LightEffectManager';

export default class EntryAbility extends UIAbility {
  private mainWindow: window.Window | null = null;
  private lightManager: LightEffectManager | null = null;

  async onWindowStageCreate(windowStage: window.WindowStage): Promise<void> {
    // 创建主窗口
    this.mainWindow = await windowStage.createSubWindow('MainTrafficAwareness');
    
    // 全屏沉浸配置
    await this.mainWindow.setWindowLayoutFullScreen(true);
    await this.mainWindow.setWindowSystemBarEnable([]);
    
    // 加载主页面
    this.mainWindow.loadContent('pages/TrafficAwarenessPage', (err) => {
      if (err) {
        console.error('Failed to load main content:', err);
        return;
      }
      console.info('Main traffic awareness window loaded');
    });

    // 初始化光效管理器
    this.lightManager = new LightEffectManager();
    await this.lightManager.initialize();

    // 注册窗口焦点监听
    this.mainWindow.on('windowFocusChange', (isFocused: boolean) => {
      this.lightManager?.setFocusState(isFocused);
      console.info(`Window focus changed: ${isFocused}`);
    });

    // 扩展安全区
    const mainWindow = await windowStage.getMainWindow();
    mainWindow.setSpecificSystemBarEnabled('status', false);
    mainWindow.setSpecificSystemBarEnabled('navigation', false);
  }

  onWindowStageDestroy(): void {
    this.lightManager?.destroy();
    this.mainWindow?.destroy();
  }
}

5.2 拥堵等级光效系统(CongestionLightEffect.ets)

代码亮点 :本模块定义了五种交通状态的完整光效人格系统。每种状态不仅拥有专属颜色,还定义了脉冲节奏、呼吸频率和光晕强度。CongestionLevel 枚举与 CongestionLightTheme 类实现了拥堵等级到光效的完整映射,支持动态切换与平滑过渡。

TypeScript

typescript 复制代码
// entry/src/main/ets/theme/CongestionLightEffect.ets

/**
 * 拥堵等级枚举
 */
export enum CongestionLevel {
  SMOOTH = 'smooth',      // 畅通 - 柔绿
  SLOW = 'slow',          // 缓行 - 淡蓝
  CONGESTED = 'congested', // 拥堵 - 暖黄
  SEVERE = 'severe',      // 严重拥堵 - 橙红
  PARALYZED = 'paralyzed'  // 瘫痪 - 警示红
}

/**
 * 拥堵光效主题接口
 */
export interface CongestionLightTheme {
  level: CongestionLevel;
  primaryColor: string;        // 主色
  secondaryColor: string;      // 辅色
  pulseColor: string;          // 脉冲色
  glowIntensity: number;       // 光晕强度 (0-1)
  pulseInterval: number;       // 脉冲间隔 (ms)
  breathSpeed: number;         // 呼吸速度 (ms)
  ambientOpacity: number;      // 环境光透明度
  roadBorderWidth: number;     // 路段边框宽度
  flowLineSpeed: number;       // 车流流光速度
}

/**
 * 拥堵等级光效主题配置
 */
export const CongestionLightThemes: Record<CongestionLevel, CongestionLightTheme> = {
  [CongestionLevel.SMOOTH]: {
    level: CongestionLevel.SMOOTH,
    primaryColor: '#4CAF50',
    secondaryColor: '#81C784',
    pulseColor: '#A5D6A7',
    glowIntensity: 0.3,
    pulseInterval: 3000,
    breathSpeed: 4000,
    ambientOpacity: 0.05,
    roadBorderWidth: 1,
    flowLineSpeed: 2000
  },
  [CongestionLevel.SLOW]: {
    level: CongestionLevel.SLOW,
    primaryColor: '#42A5F5',
    secondaryColor: '#90CAF9',
    pulseColor: '#BBDEFB',
    glowIntensity: 0.4,
    pulseInterval: 2500,
    breathSpeed: 3500,
    ambientOpacity: 0.08,
    roadBorderWidth: 1.5,
    flowLineSpeed: 1800
  },
  [CongestionLevel.CONGESTED]: {
    level: CongestionLevel.CONGESTED,
    primaryColor: '#FFA726',
    secondaryColor: '#FFCC80',
    pulseColor: '#FFE0B2',
    glowIntensity: 0.6,
    pulseInterval: 1500,
    breathSpeed: 2500,
    ambientOpacity: 0.12,
    roadBorderWidth: 2,
    flowLineSpeed: 1200
  },
  [CongestionLevel.SEVERE]: {
    level: CongestionLevel.SEVERE,
    primaryColor: '#EF5350',
    secondaryColor: '#EF9A9A',
    pulseColor: '#FFCDD2',
    glowIntensity: 0.8,
    pulseInterval: 800,
    breathSpeed: 1500,
    ambientOpacity: 0.18,
    roadBorderWidth: 3,
    flowLineSpeed: 800
  },
  [CongestionLevel.PARALYZED]: {
    level: CongestionLevel.PARALYZED,
    primaryColor: '#D32F2F',
    secondaryColor: '#E57373',
    pulseColor: '#FFEBEE',
    glowIntensity: 1.0,
    pulseInterval: 400,
    breathSpeed: 800,
    ambientOpacity: 0.25,
    roadBorderWidth: 4,
    flowLineSpeed: 400
  }
};

/**
 * 路口节点数据接口
 */
export interface RoadNode {
  id: string;
  name: string;
  intersectionType: string;    // 交叉口类型
  congestionLevel: CongestionLevel;
  avgSpeed: number;           // 平均车速 (km/h)
  queueLength: number;        // 排队长度 (m)
  flowRate: number;           // 流量 (veh/h)
  lastUpdate: number;
  x: number;
  y: number;
  connections: string[];
}

/**
 * 车流链路数据接口
 */
export interface TrafficFlow {
  id: string;
  sourceId: string;
  targetId: string;
  flowType: string;           // 车流类型
  congestionLevel: CongestionLevel;
  vehicleCount: number;
  avgSpeed: number;
  timestamp: number;
  isActive: boolean;
}

/**
 * 光效管理器
 */
export class CongestionLightManager {
  private currentTheme: CongestionLightTheme = CongestionLightThemes[CongestionLevel.SMOOTH];
  private listeners: Set<(theme: CongestionLightTheme) => void> = new Set();

  /**
   * 根据最高拥堵等级切换光效
   */
  public switchCongestionLevel(level: CongestionLevel): void {
    this.currentTheme = CongestionLightThemes[level];
    this.listeners.forEach(listener => listener(this.currentTheme));
    console.info(`Congestion level switched to ${level}, theme updated`);
  }

  /**
   * 根据路口节点列表自动计算最高等级
   */
  public autoSwitchFromNodes(nodes: RoadNode[]): void {
    const levelPriority = [CongestionLevel.SMOOTH, CongestionLevel.SLOW, CongestionLevel.CONGESTED, CongestionLevel.SEVERE, CongestionLevel.PARALYZED];
    let maxLevel = CongestionLevel.SMOOTH;
    
    for (const node of nodes) {
      const currentPriority = levelPriority.indexOf(node.congestionLevel);
      const maxPriority = levelPriority.indexOf(maxLevel);
      if (currentPriority > maxPriority) {
        maxLevel = node.congestionLevel;
      }
    }
    
    this.switchCongestionLevel(maxLevel);
  }

  public getCurrentTheme(): CongestionLightTheme {
    return this.currentTheme;
  }

  public onThemeChange(listener: (theme: CongestionLightTheme) => void): void {
    this.listeners.add(listener);
  }

  public offThemeChange(listener: (theme: CongestionLightTheme) => void): void {
    this.listeners.delete(listener);
  }
}

5.3 HMAF四层交通智能体架构(TrafficAgentScheduler.ets)

代码亮点 :本模块是"光脉智城"的核心大脑,实现了四层交通智能体的协作调度。TrafficAgentScheduler 通过HMAF的 AgentSession 注册四个专业交通智能体,并通过 IntentsEngine 解析调度员的自然语言查询意图。每个智能体拥有独立的提示词模板和能力声明,支持全链路自动化(数据采集→态势研判→拥堵预测→智能调度)。

TypeScript

typescript 复制代码
// entry/src/main/ets/agents/TrafficAgentScheduler.ets

import {
  hmaf,
  AgentSession,
  AgentMode,
  TaskMessage,
  TaskResult
} from '@kit.AgentFrameworkKit';
import { intents, IntentEngine, IntentResult } from '@kit.IntentsKit';
import { CongestionLightManager, CongestionLevel, RoadNode, TrafficFlow } from '../theme/CongestionLightEffect';

/**
 * 智能体类型定义
 */
export enum AgentType {
  DATA_COLLECTOR = 'data_collector',   // 数据采集Agent
  SITUATION_ANALYZER = 'situation_analyzer', // 态势研判Agent
  CONGESTION_PREDICTOR = 'congestion_predictor', // 拥堵预测Agent
  SMART_SCHEDULER = 'smart_scheduler'   // 智能调度Agent
}

/**
 * 交通运营阶段枚举
 */
export enum TrafficStage {
  OVERVIEW = 'overview',       // 态势总览
  INTERSECTION = 'intersection', // 路口监控
  FLOW = 'flow',               // 车流分析
  SIGNAL = 'signal'            // 信号调度
}

/**
 * 数据采集结果接口
 */
export interface DataCollectionResult {
  totalVehicles: number;
  avgSpeed: number;
  intersectionCount: number;
  dataSources: string[];
  dataQuality: number;
  timeWindow: string;
}

/**
 * 态势研判结果接口
 */
export interface SituationResult {
  congestedIntersections: Array<{
    id: string;
    name: string;
    level: CongestionLevel;
    avgSpeed: number;
    queueLength: number;
    cause: string;
    trend: 'improving' | 'stable' | 'worsening';
  }>;
  congestionIndex: number;
  analysisLatency: number;
}

/**
 * 拥堵预测结果接口
 */
export interface PredictionResult {
  predictions: Array<{
    intersectionId: string;
    predictedLevel: CongestionLevel;
    confidence: number;
    timeToCongestion: number; // 预计拥堵时间(分钟)
    recommendedAction: string;
  }>;
  modelAccuracy: number;
  predictionHorizon: string;
}

/**
 * 智能调度结果接口
 */
export interface ScheduleResult {
  optimizedSignals: Array<{
    intersectionId: string;
    greenTime: number;
    cycleLength: number;
    offset: number;
    coordinationGroup: string;
    expectedImprovement: number;
  }>;
  implementationStatus: string;
  playbookId: string;
  mttr: number; // 平均响应时间(分钟)
}

/**
 * HMAF智慧交通智能体调度器
 * 核心:四层智能体协作,实现交通态势的自动感知与智能调度
 */
export class TrafficAgentScheduler {
  private session: AgentSession | null = null;
  private intentEngine: IntentEngine | null = null;
  private lightManager: CongestionLightManager;

  // 交通数据存储
  private roadNodes: Map<string, RoadNode> = new Map();
  private trafficFlows: Map<string, TrafficFlow> = new Map();
  private dataResult: DataCollectionResult | null = null;
  private situationResult: SituationResult | null = null;
  private predictionResult: PredictionResult | null = null;
  private scheduleResult: ScheduleResult | null = null;

  // 回调监听
  private onDataCollected?: (result: DataCollectionResult) => void;
  private onSituationAnalyzed?: (result: SituationResult) => void;
  private onCongestionPredicted?: (result: PredictionResult) => void;
  private onScheduleExecuted?: (result: ScheduleResult) => void;
  private onStageChanged?: (stage: TrafficStage) => void;

  constructor(lightManager: CongestionLightManager) {
    this.lightManager = lightManager;
  }

  /**
   * 初始化智能体会话
   */
  public async initialize(): Promise<void> {
    this.session = await hmaf.createAgentSession({
      mode: AgentMode.MULTI_AGENT,
      config: {
        maxConcurrentAgents: 4,
        timeout: 30000,
        enableDistributed: true
      }
    });

    this.intentEngine = await intents.createIntentEngine({
      supportedDomains: ['traffic_management', 'congestion_analysis', 'signal_optimization', 'incident_response']
    });

    await this.registerAgents();
    console.info('TrafficAgentScheduler initialized successfully');
  }

  /**
   * 注册四层交通智能体
   */
  private async registerAgents(): Promise<void> {
    if (!this.session) return;

    // 1. 数据采集Agent - 多源交通数据实时采集与融合
    await this.session.registerAgent({
      agentId: AgentType.DATA_COLLECTOR,
      capabilities: ['video_analysis', 'loop_detector', 'floating_car_data', 'bus_card_data', 'weather_data'],
      promptTemplate: `
        你是智慧交通数据采集专家。融合多源交通数据:
        - 视频监控数据:识别车辆类型、计数、排队长度
        - 地磁线圈数据:车道流量、占有率、平均车速
        - 浮动车GPS数据:行程时间、路径选择、速度分布
        - 公交IC卡数据:客流OD、换乘行为、出行模式
        - 天气数据:降雨、能见度、路面状况对交通的影响

        返回JSON格式: {
          "totalVehicles": 15000,
          "avgSpeed": 35.5,
          "intersectionCount": 48,
          "dataSources": ["video", "loop", "gps", "bus", "weather"],
          "dataQuality": 0.95,
          "timeWindow": "2026-06-27T10:00:00Z/2026-06-27T11:00:00Z"
        }
      `
    });

    // 2. 态势研判Agent - 实时交通态势分析与拥堵成因识别
    await this.session.registerAgent({
      agentId: AgentType.SITUATION_ANALYZER,
      capabilities: ['congestion_detection', 'cause_analysis', 'trend_prediction', 'impact_assessment'],
      promptTemplate: `
        你是智慧交通态势研判专家。分析给定的交通数据:
        - 识别拥堵路口:基于速度、流量、占有率综合评估
        - 分析拥堵成因:事故、施工、信号配时不合理、突发大客流等
        - 判断拥堵趋势:改善/稳定/恶化
        - 评估影响范围:上下游路口、相邻路段的扩散效应

        对每个拥堵路口提供:ID、名称、拥堵等级、平均车速、排队长度、成因、趋势

        返回JSON格式: {
          "congestedIntersections": [{"id": "int_001", "name": "中山路-建设大道", "level": "congested", "avgSpeed": 12.5, "queueLength": 80, "cause": "信号灯配时不合理", "trend": "worsening"}],
          "congestionIndex": 0.65,
          "analysisLatency": 3.2
        }
      `
    });

    // 3. 拥堵预测Agent - 基于时序模型的拥堵预测
    await this.session.registerAgent({
      agentId: AgentType.CONGESTION_PREDICTOR,
      capabilities: ['time_series_forecast', 'pattern_recognition', 'anomaly_detection', 'scenario_simulation'],
      promptTemplate: `
        你是智慧交通拥堵预测专家。基于历史数据和实时态势进行预测:
        - 短期预测(5-15分钟):基于当前流量趋势外推
        - 中期预测(30-60分钟):基于历史同期模式匹配
        - 识别潜在拥堵点:流量接近饱和容量的路口
        - 推荐预防措施:提前调整信号配时、发布诱导信息

        返回JSON格式: {
          "predictions": [{"intersectionId": "int_001", "predictedLevel": "severe", "confidence": 0.85, "timeToCongestion": 12, "recommendedAction": "延长绿灯时间15秒"}],
          "modelAccuracy": 0.92,
          "predictionHorizon": "15min"
        }
      `
    });

    // 4. 智能调度Agent - 信号优化与协调控制
    await this.session.registerAgent({
      agentId: AgentType.SMART_SCHEDULER,
      capabilities: ['signal_timing', 'green_wave', 'priority_control', 'emergency_response', 'bus_priority'],
      promptTemplate: `
        你是智慧交通信号调度专家。基于态势研判和预测结果执行调度:
        - 单点优化:调整绿灯时间、周期长度、相位顺序
        - 绿波协调:干线协调控制,减少停车次数
        - 紧急优先:救护车、消防车信号优先
        - 公交优先:BRT专用相位、绿灯延长
        - 评估预期改善:延误减少、通行能力提升

        返回JSON格式: {
          "optimizedSignals": [{"intersectionId": "int_001", "greenTime": 45, "cycleLength": 120, "offset": 15, "coordinationGroup": "group_a", "expectedImprovement": 0.25}],
          "implementationStatus": "已下发",
          "playbookId": "SIGNAL-001",
          "mttr": 2.5
        }
      `
    });
  }

  /**
   * 处理调度员输入 - 意图解析 + 智能体分发
   */
  public async processTrafficIntent(input: string, context?: Record<string, unknown>): Promise<void> {
    if (!this.session || !this.intentEngine) {
      throw new Error('Scheduler not initialized');
    }

    // 第一步:意图解析
    const intentResult: IntentResult = await this.intentEngine.parseIntent(input);
    const intent = intentResult.primaryIntent;

    console.info(`Detected traffic intent: ${intent.domain}/${intent.action}`);

    // 根据意图调整运营阶段
    this.adjustStageByIntent(intent);

    // 第二步:智能体任务分发
    switch (intent.action) {
      case 'collect_data':
        await this.dispatchDataCollection(context?.area as string || 'all');
        break;
      case 'analyze_situation':
        await this.dispatchSituationAnalysis(context?.timeRange as string || '1h');
        break;
      case 'predict_congestion':
        await this.dispatchCongestionPrediction(context?.intersectionId as string);
        break;
      case 'execute_schedule':
        await this.dispatchSmartSchedule(context?.playbookId as string);
        break;
      case 'full_investigation':
        // 全链路:采集 -> 研判 -> 预测 -> 调度
        await this.dispatchFullInvestigation(context);
        break;
      default:
        await this.dispatchFullInvestigation(context);
    }
  }

  /**
   * 根据意图调整运营阶段与光效
   */
  private adjustStageByIntent(intent: IntentResult['primaryIntent']): void {
    const stageMap: Record<string, TrafficStage> = {
      'collect_data': TrafficStage.OVERVIEW,
      'analyze_situation': TrafficStage.FLOW,
      'predict_congestion': TrafficStage.FLOW,
      'execute_schedule': TrafficStage.SIGNAL,
      'full_investigation': TrafficStage.OVERVIEW
    };

    const newStage = stageMap[intent.action] || TrafficStage.OVERVIEW;
    this.onStageChanged?.(newStage);
  }

  /**
   * 分发数据采集任务
   */
  private async dispatchDataCollection(area: string): Promise<void> {
    const task: TaskMessage = {
      targetAgent: AgentType.DATA_COLLECTOR,
      taskType: 'collect',
      payload: { area, duration: 60 },
      priority: 1
    };

    const result: TaskResult = await this.session!.sendTask(task);
    this.dataResult = JSON.parse(result.data);

    // 触发回调
    this.onDataCollected?.(this.dataResult);

    // 更新全局状态
    AppStorage.setOrCreate('data_result', this.dataResult);
  }

  /**
   * 分发态势研判任务
   */
  private async dispatchSituationAnalysis(timeRange: string): Promise<void> {
    const task: TaskMessage = {
      targetAgent: AgentType.SITUATION_ANALYZER,
      taskType: 'analyze',
      payload: { 
        timeRange,
        trafficData: this.dataResult,
        historicalBaseline: '2026.06.27'
      },
      priority: 2
    };

    const result: TaskResult = await this.session!.sendTask(task);
    this.situationResult = JSON.parse(result.data);

    // 触发回调
    this.onSituationAnalyzed?.(this.situationResult);

    // 更新全局状态并切换光效
    AppStorage.setOrCreate('situation_result', this.situationResult);
    
    // 根据最高拥堵等级自动切换光效
    if (this.situationResult && this.situationResult.congestedIntersections.length > 0) {
      const maxCongestion = this.situationResult.congestedIntersections.reduce((max, intersection) => {
        const priority = ['smooth', 'slow', 'congested', 'severe', 'paralyzed'];
        return priority.indexOf(intersection.level) > priority.indexOf(max.level) ? intersection : max;
      });
      this.lightManager.switchCongestionLevel(maxCongestion.level as CongestionLevel);
    }

    // 更新路口节点
    this.updateRoadNodesFromResult(this.situationResult);
  }

  /**
   * 分发拥堵预测任务
   */
  private async dispatchCongestionPrediction(intersectionId: string): Promise<void> {
    const task: TaskMessage = {
      targetAgent: AgentType.CONGESTION_PREDICTOR,
      taskType: 'predict',
      payload: { 
        intersectionId,
        situationData: this.situationResult?.congestedIntersections.find(i => i.id === intersectionId),
        historicalData: this.dataResult
      },
      priority: 3
    };

    const result: TaskResult = await this.session!.sendTask(task);
    this.predictionResult = JSON.parse(result.data);

    // 触发回调
    this.onCongestionPredicted?.(this.predictionResult);

    // 更新预测数据
    AppStorage.setOrCreate('prediction_result', this.predictionResult);
  }

  /**
   * 分发智能调度任务
   */
  private async dispatchSmartSchedule(playbookId: string): Promise<void> {
    const task: TaskMessage = {
      targetAgent: AgentType.SMART_SCHEDULER,
      taskType: 'schedule',
      payload: { 
        playbookId,
        predictionData: this.predictionResult,
        situationData: this.situationResult
      },
      priority: 4
    };

    const result: TaskResult = await this.session!.sendTask(task);
    this.scheduleResult = JSON.parse(result.data);

    // 触发回调
    this.onScheduleExecuted?.(this.scheduleResult);

    // 调度完成后切换为缓行态
    if (this.scheduleResult?.implementationStatus === '已下发') {
      this.lightManager.switchCongestionLevel(CongestionLevel.SLOW);
    }
  }

  /**
   * 全链路交通调查
   */
  private async dispatchFullInvestigation(context?: Record<string, unknown>): Promise<void> {
    try {
      // 阶段1:数据采集
      await this.dispatchDataCollection(context?.area as string || 'all');
      
      // 阶段2:态势研判
      await this.dispatchSituationAnalysis(context?.timeRange as string || '1h');
      
      // 阶段3:拥堵预测(如果存在拥堵)
      if (this.situationResult && this.situationResult.congestedIntersections.length > 0) {
        const topCongestion = this.situationResult.congestedIntersections[0];
        await this.dispatchCongestionPrediction(topCongestion.id);
        
        // 阶段4:智能调度(如果是严重拥堵或瘫痪)
        if (topCongestion.level === CongestionLevel.SEVERE || topCongestion.level === CongestionLevel.PARALYZED) {
          await this.dispatchSmartSchedule('auto_signal_opt');
        }
      }
    } catch (error) {
      console.error('Full investigation failed:', error);
    }
  }

  /**
   * 更新路口节点数据
   */
  private updateRoadNodesFromResult(result: SituationResult): void {
    for (const intersection of result.congestedIntersections) {
      const node: RoadNode = {
        id: intersection.id,
        name: intersection.name,
        intersectionType: 'signalized',
        congestionLevel: intersection.level as CongestionLevel,
        avgSpeed: intersection.avgSpeed,
        queueLength: intersection.queueLength,
        flowRate: 0,
        lastUpdate: Date.now(),
        x: Math.random() * 800,
        y: Math.random() * 600,
        connections: []
      };
      this.roadNodes.set(intersection.id, node);
    }
  }

  // 设置回调
  public setOnDataCollected(callback: (result: DataCollectionResult) => void): void {
    this.onDataCollected = callback;
  }
  public setOnSituationAnalyzed(callback: (result: SituationResult) => void): void {
    this.onSituationAnalyzed = callback;
  }
  public setOnCongestionPredicted(callback: (result: PredictionResult) => void): void {
    this.onCongestionPredicted = callback;
  }
  public setOnScheduleExecuted(callback: (result: ScheduleResult) => void): void {
    this.onScheduleExecuted = callback;
  }
  public setOnStageChanged(callback: (stage: TrafficStage) => void): void {
    this.onStageChanged = callback;
  }
}

5.4 悬浮态势导航(TrafficFloatNavigation.ets)

代码亮点 :本模块实现了"交通态势即导航"的悬浮页签系统。底部悬浮导航不仅承载"态势总览/路口监控/车流分析/信号调度"四个运营阶段切换,更实时显示拥堵统计徽章(瘫痪/严重拥堵/拥堵数量)和智能体运行状态角标。采用 HdsTabs 悬浮样式配合 systemMaterialEffect 实现玻璃拟态+拥堵光效的双重效果,支持透明度三档调节,最大化态势展示区域。

TypeScript

typescript 复制代码
// entry/src/main/ets/components/TrafficFloatNavigation.ets
import { window } from '@kit.ArkUI';
import { CongestionLightManager, CongestionLevel, CongestionLightTheme } from '../theme/CongestionLightEffect';
import { TrafficStage } from '../agents/TrafficAgentScheduler';

// 导航项配置
interface TrafficNavItem {
  id: string;
  icon: Resource;
  label: string;
  page: string;
  stage: TrafficStage;
}

@Component
export struct TrafficFloatNavigation {
  @State currentIndex: number = 0;
  @State navTransparency: number = 0.70;
  @State isExpanded: boolean = false;
  @State bottomAvoidHeight: number = 0;
  @State currentStage: TrafficStage = TrafficStage.OVERVIEW;
  @State currentTheme: CongestionLightTheme | null = null;
  
  // 拥堵统计
  @State paralyzedCount: number = 0;
  @State severeCount: number = 0;
  @State congestedCount: number = 0;
  @State slowCount: number = 0;

  private lightManager: CongestionLightManager;
  private navItems: TrafficNavItem[] = [
    { id: 'overview', icon: $r('app.media.ic_dashboard'), label: '态势总览', page: 'OverviewPage', stage: TrafficStage.OVERVIEW },
    { id: 'intersection', icon: $r('app.media.ic_traffic_light'), label: '路口监控', page: 'IntersectionPage', stage: TrafficStage.INTERSECTION },
    { id: 'flow', icon: $r('app.media.ic_flow'), label: '车流分析', page: 'FlowPage', stage: TrafficStage.FLOW },
    { id: 'signal', icon: $r('app.media.ic_signal'), label: '信号调度', page: 'SignalPage', stage: TrafficStage.SIGNAL }
  ];

  constructor(lightManager: CongestionLightManager) {
    this.lightManager = lightManager;
  }

  aboutToAppear(): void {
    this.getBottomAvoidArea();
    
    // 监听光效主题变化
    this.lightManager.onThemeChange((theme) => {
      this.currentTheme = theme;
    });
    
    // 监听拥堵统计变化
    AppStorage.setOrCreate('congestion_stats', (stats: { paralyzed: number; severe: number; congested: number; slow: number }) => {
      this.paralyzedCount = stats.paralyzed;
      this.severeCount = stats.severe;
      this.congestedCount = stats.congested;
      this.slowCount = stats.slow;
    });

    // 初始化当前主题
    this.currentTheme = this.lightManager.getCurrentTheme();
  }

  aboutToDisappear(): void {
    this.lightManager.offThemeChange(() => {});
  }

  private async getBottomAvoidArea(): Promise<void> {
    try {
      const mainWindow = await window.getLastWindow();
      const avoidArea = mainWindow.getWindowAvoidArea(window.AvoidAreaType.TYPE_NAVIGATION_INDICATOR);
      this.bottomAvoidHeight = avoidArea.bottomRect.height;
    } catch (error) {
      console.error('Failed to get avoid area:', error);
    }
  }

  private getStageColor(): string {
    return this.currentTheme?.primaryColor || '#4CAF50';
  }

  private getCongestionBadgeCount(itemId: string): number {
    switch (itemId) {
      case 'flow': return this.severeCount + this.congestedCount;
      case 'signal': return this.paralyzedCount;
      default: return 0;
    }
  }

  private getCongestionBadgeColor(): string {
    if (this.paralyzedCount > 0) return '#D32F2F';
    if (this.severeCount > 0) return '#EF5350';
    if (this.congestedCount > 0) return '#FFA726';
    return '#42A5F5';
  }

  build() {
    Stack({ alignContent: Alignment.Bottom }) {
      // 内容层
      Column() {
        this.contentBuilder()
      }
      .padding({ bottom: this.bottomAvoidHeight + 80 })

      // 悬浮导航栏
      Column() {
        Stack() {
          // 玻璃拟态背景
          Column()
            .width('100%')
            .height('100%')
            .backgroundBlurStyle(BlurStyle.REGULAR)
            .opacity(this.navTransparency)
            .backdropFilter($r('sys.blur.20'))

          // 拥堵光效渐变层
          Column()
            .width('100%')
            .height('100%')
            .linearGradient({
              direction: GradientDirection.Top,
              colors: [
                [this.getStageColor() + '20', 0.0],
                [this.getStageColor() + '05', 1.0]
              ]
            })
        }
        .width('100%')
        .height('100%')
        .borderRadius(24)
        .shadow({
          radius: 20,
          color: (this.currentTheme?.primaryColor || '#4CAF50') + '40',
          offsetX: 0,
          offsetY: -4
        })

        // 导航项
        Row() {
          ForEach(this.navItems, (item: TrafficNavItem, index: number) => {
            Column() {
              Stack() {
                Image(item.icon)
                  .width(24)
                  .height(24)
                  .fillColor(this.currentIndex === index ? this.getStageColor() : '#666666')

                // 拥堵统计徽章
                if (this.getCongestionBadgeCount(item.id) > 0) {
                  Stack() {
                    Text(`${this.getCongestionBadgeCount(item.id)}`)
                      .fontSize(10)
                      .fontColor('#FFFFFF')
                      .fontWeight(FontWeight.Bold)
                  }
                  .width(18)
                  .height(18)
                  .backgroundColor(this.getCongestionBadgeColor())
                  .borderRadius(9)
                  .position({ x: 14, y: -6 })
                  .shadow({
                    radius: 6,
                    color: this.getCongestionBadgeColor(),
                    offsetX: 0,
                    offsetY: 0
                  })
                }

                // 阶段指示器
                if (item.stage === this.currentStage) {
                  Column()
                    .width(6)
                    .height(6)
                    .backgroundColor(this.getStageColor())
                    .borderRadius(3)
                    .position({ x: 20, y: 20 })
                    .shadow({
                      radius: 4,
                      color: this.getStageColor(),
                      offsetX: 0,
                      offsetY: 0
                    })
                }
              }
              .width(40)
              .height(40)

              Text(item.label)
                .fontSize(11)
                .fontColor(this.currentIndex === index ? this.getStageColor() : '#999999')
                .margin({ top: 4 })
            }
            .layoutWeight(1)
            .onClick(() => {
              this.currentIndex = index;
              this.currentStage = item.stage;
              AppStorage.setOrCreate('traffic_stage', item.stage);
              this.triggerHapticFeedback();
            })
          })
        }
        .width('100%')
        .height(80)
        .padding({ left: 16, right: 16 })
        .justifyContent(FlexAlign.SpaceAround)

        // 透明度调节
        if (this.isExpanded) {
          Row() {
            Text('透明度')
              .fontSize(12)
              .fontColor('#666666')
              .margin({ right: 8 })

            Slider({
              value: this.navTransparency * 100,
              min: 55,
              max: 85,
              step: 15,
              style: SliderStyle.InSet
            })
              .width(120)
              .onChange((value: number) => {
                this.navTransparency = value / 100;
              })

            Text(`${Math.round(this.navTransparency * 100)}%`)
              .fontSize(12)
              .fontColor('#666666')
              .margin({ left: 8 })
          }
          .width('100%')
          .height(40)
          .justifyContent(FlexAlign.Center)
          .backgroundColor('rgba(255,255,255,0.5)')
          .borderRadius({ topLeft: 12, topRight: 12 })
        }
      }
      .width('92%')
      .height(this.isExpanded ? 120 : 80)
      .margin({ bottom: this.bottomAvoidHeight + 12, left: '4%', right: '4%' })
      .animation({
        duration: 300,
        curve: Curve.Spring,
        iterations: 1
      })
      .gesture(
        LongPressGesture({ duration: 500 })
          .onAction(() => {
            this.isExpanded = !this.isExpanded;
          })
      )
    }
    .width('100%')
    .height('100%')
  }

  @BuilderParam contentBuilder: () => void = this.defaultContentBuilder;

  @Builder
  defaultContentBuilder(): void {
    Column() {
      Text('态势感知区域')
        .fontSize(16)
        .fontColor('#999999')
    }
    .width('100%')
    .height('100%')
    .justifyContent(FlexAlign.Center)
  }

  private triggerHapticFeedback(): void {
    try {
      import('@kit.SensorServiceKit').then(sensor => {
        sensor.vibrator.startVibration({
          type: 'time',
          duration: 50
        }, { id: 0 });
      });
    } catch (error) {
      console.error('Haptic feedback failed:', error);
    }
  }
}

5.5 主态势感知大屏(TrafficAwarenessPage.ets)

代码亮点 :本模块是"光脉智城"的核心可视化界面,基于 Canvas 实现城市路网的实时渲染。路口节点根据拥堵等级显示不同颜色与脉冲效果,车流链路实现动态流光动画。支持手势缩放与拖拽,双击节点下钻查看详情。环境背景光随全局拥堵等级动态变化。

TypeScript

typescript 复制代码
// entry/src/main/ets/pages/TrafficAwarenessPage.ets
import { CongestionLightManager, RoadNode, TrafficFlow, CongestionLevel } from '../theme/CongestionLightEffect';
import { TrafficAgentScheduler, TrafficStage } from '../agents/TrafficAgentScheduler';

@Component
struct RoadNetworkCanvas {
  @State nodes: RoadNode[] = [];
  @State flows: TrafficFlow[] = [];
  @State scale: number = 1.0;
  @State offsetX: number = 0;
  @State offsetY: number = 0;
  @State selectedNode: RoadNode | null = null;
  @State currentTheme: CongestionLightTheme | null = null;
  
  private lightManager: CongestionLightManager;
  private scheduler: TrafficAgentScheduler;
  private canvasContext: CanvasRenderingContext2D | null = null;
  private animationId: number = 0;

  constructor(lightManager: CongestionLightManager, scheduler: TrafficAgentScheduler) {
    this.lightManager = lightManager;
    this.scheduler = scheduler;
  }

  aboutToAppear(): void {
    // 监听光效变化
    this.lightManager.onThemeChange((theme) => {
      this.currentTheme = theme;
      this.invalidate();
    });

    // 监听节点数据变化
    AppStorage.setOrCreate('road_nodes', (nodes: RoadNode[]) => {
      this.nodes = nodes;
      this.invalidate();
    });

    // 监听链路数据变化
    AppStorage.setOrCreate('traffic_flows', (flows: TrafficFlow[]) => {
      this.flows = flows;
      this.invalidate();
    });

    // 启动动画循环
    this.startAnimationLoop();
  }

  aboutToDisappear(): void {
    this.lightManager.offThemeChange(() => {});
    if (this.animationId) {
      cancelAnimationFrame(this.animationId);
    }
  }

  private startAnimationLoop(): void {
    const animate = () => {
      this.invalidate();
      this.animationId = requestAnimationFrame(animate);
    };
    this.animationId = requestAnimationFrame(animate);
  }

  private invalidate(): void {
    if (this.canvasContext) {
      this.drawNetwork(this.canvasContext);
    }
  }

  private drawNetwork(ctx: CanvasRenderingContext2D): void {
    const width = ctx.canvas.width;
    const height = ctx.canvas.height;
    const time = Date.now();

    // 清空画布
    ctx.clearRect(0, 0, width, height);

    // 绘制环境背景光
    if (this.currentTheme) {
      const gradient = ctx.createRadialGradient(
        width / 2, height / 2, 0,
        width / 2, height / 2, Math.max(width, height) / 2
      );
      gradient.addColorStop(0, this.currentTheme.primaryColor + '10');
      gradient.addColorStop(1, 'transparent');
      ctx.fillStyle = gradient;
      ctx.fillRect(0, 0, width, height);
    }

    // 保存变换状态
    ctx.save();
    ctx.translate(this.offsetX, this.offsetY);
    ctx.scale(this.scale, this.scale);

    // 绘制车流链路
    for (const flow of this.flows) {
      if (!flow.isActive) continue;
      
      const sourceNode = this.nodes.find(n => n.id === flow.sourceId);
      const targetNode = this.nodes.find(n => n.id === flow.targetId);
      if (!sourceNode || !targetNode) continue;

      // 链路流光效果
      const flowOffset = (time % this.currentTheme?.flowLineSpeed || 2000) / (this.currentTheme?.flowLineSpeed || 2000);
      const flowColor = this.getCongestionColor(flow.congestionLevel);
      
      ctx.beginPath();
      ctx.moveTo(sourceNode.x, sourceNode.y);
      ctx.lineTo(targetNode.x, targetNode.y);
      ctx.strokeStyle = flowColor + '40';
      ctx.lineWidth = 2;
      ctx.stroke();

      // 流光点
      const flowX = sourceNode.x + (targetNode.x - sourceNode.x) * flowOffset;
      const flowY = sourceNode.y + (targetNode.y - sourceNode.y) * flowOffset;
      
      ctx.beginPath();
      ctx.arc(flowX, flowY, 4, 0, Math.PI * 2);
      ctx.fillStyle = flowColor;
      ctx.fill();
      ctx.shadowColor = flowColor;
      ctx.shadowBlur = 10;
    }

    // 绘制路口节点
    for (const node of this.nodes) {
      const nodeColor = this.getCongestionColor(node.congestionLevel);
      const pulseIntensity = this.getPulseIntensity(node.congestionLevel, time);
      
      // 节点光晕
      ctx.beginPath();
      ctx.arc(node.x, node.y, 30 + pulseIntensity * 10, 0, Math.PI * 2);
      ctx.fillStyle = nodeColor + '20';
      ctx.fill();
      
      // 节点外圈
      ctx.beginPath();
      ctx.arc(node.x, node.y, 20, 0, Math.PI * 2);
      ctx.strokeStyle = nodeColor;
      ctx.lineWidth = this.currentTheme?.roadBorderWidth || 2;
      ctx.stroke();
      
      // 节点内核
      ctx.beginPath();
      ctx.arc(node.x, node.y, 16, 0, Math.PI * 2);
      ctx.fillStyle = nodeColor;
      ctx.fill();
      
      // 节点标签
      ctx.fillStyle = '#FFFFFF';
      ctx.font = '12px sans-serif';
      ctx.textAlign = 'center';
      ctx.fillText(node.name, node.x, node.y + 35);
      ctx.fillText(`${node.avgSpeed}km/h`, node.x, node.y + 50);
    }

    ctx.restore();
  }

  private getCongestionColor(level: CongestionLevel): string {
    const colors: Record<CongestionLevel, string> = {
      [CongestionLevel.SMOOTH]: '#4CAF50',
      [CongestionLevel.SLOW]: '#42A5F5',
      [CongestionLevel.CONGESTED]: '#FFA726',
      [CongestionLevel.SEVERE]: '#EF5350',
      [CongestionLevel.PARALYZED]: '#D32F2F'
    };
    return colors[level] || '#4CAF50';
  }

  private getPulseIntensity(level: CongestionLevel, time: number): number {
    const speeds: Record<CongestionLevel, number> = {
      [CongestionLevel.SMOOTH]: 4000,
      [CongestionLevel.SLOW]: 3500,
      [CongestionLevel.CONGESTED]: 2500,
      [CongestionLevel.SEVERE]: 1500,
      [CongestionLevel.PARALYZED]: 800
    };
    const speed = speeds[level] || 4000;
    return Math.sin((time % speed) / speed * Math.PI * 2) * 0.5 + 0.5;
  }

  build() {
    Canvas(this.canvasContext)
      .width('100%')
      .height('100%')
      .backgroundColor('#0D1117')
      .onReady((context) => {
        this.canvasContext = context;
      })
      .gesture(
        GestureGroup(GestureMode.Sequence,
          PinchGesture()
            .onActionStart((event) => {
              this.scale = Math.max(0.5, Math.min(3.0, this.scale * event.scale));
            }),
          PanGesture()
            .onActionUpdate((event) => {
              this.offsetX += event.offsetX;
              this.offsetY += event.offsetY;
            })
        )
      )
      .onClick((event) => {
        // 节点选中检测
        const clickX = (event.x - this.offsetX) / this.scale;
        const clickY = (event.y - this.offsetY) / this.scale;
        
        for (const node of this.nodes) {
          const dist = Math.sqrt((clickX - node.x) ** 2 + (clickY - node.y) ** 2);
          if (dist < 25) {
            this.selectedNode = node;
            AppStorage.setOrCreate('selected_road_node', node);
            break;
          }
        }
      })
  }
}

@Entry
@Component
struct TrafficAwarenessPage {
  private lightManager: CongestionLightManager = new CongestionLightManager();
  private scheduler: TrafficAgentScheduler = new TrafficAgentScheduler(this.lightManager);

  aboutToAppear(): void {
    this.scheduler.initialize().then(() => {
      // 启动全链路调查
      this.scheduler.processTrafficIntent('开始全面交通态势调查');
    });
  }

  build() {
    Stack() {
      // 背景环境光
      Column()
        .width('100%')
        .height('100%')
        .backgroundColor('#0D1117')
        .expandSafeArea([SafeAreaType.SYSTEM], [SafeAreaEdge.TOP, SafeAreaEdge.BOTTOM])

      // 路网拓扑画布
      RoadNetworkCanvas({ lightManager: this.lightManager, scheduler: this.scheduler })
        .width('100%')
        .height('100%')

      // 顶部状态栏
      Row() {
        Text('光脉智城')
          .fontSize(20)
          .fontColor('#FFFFFF')
          .fontWeight(FontWeight.Bold)
        
        Blank()
        
        // 拥堵统计
        Row({ space: 12 }) {
          this.congestionBadge('瘫痪', 0, '#D32F2F')
          this.congestionBadge('严重', 0, '#EF5350')
          this.congestionBadge('拥堵', 0, '#FFA726')
          this.congestionBadge('缓行', 0, '#42A5F5')
        }
      }
      .width('100%')
      .height(56)
      .padding({ left: 24, right: 24 })
      .backgroundColor('rgba(13,17,23,0.8)')
      .backdropFilter($r('sys.blur.10'))

      // 悬浮态势导航
      TrafficFloatNavigation({ lightManager: this.lightManager })
        .width('100%')
        .height('100%')
    }
    .width('100%')
    .height('100%')
  }

  @Builder
  congestionBadge(label: string, count: number, color: string): void {
    Row() {
      Circle()
        .width(8)
        .height(8)
        .fill(color)
      
      Text(`${label} ${count}`)
        .fontSize(12)
        .fontColor('#FFFFFF')
        .margin({ left: 4 })
    }
  }
}

5.6 浮动路口监控窗口(IntersectionMonitorAbility.ets)

代码亮点 :本模块实现了可拖拽的浮动路口监控子窗口。通过 window.createSubWindow 创建独立浮动窗口,支持自由拖拽定位。窗口内展示选中路口的实时视频与流量数据,状态颜色与主窗口光效同步。窗口获得焦点时自动提高透明度,失焦时降低透明度,避免干扰主态势大屏。

TypeScript

typescript 复制代码
// entry/src/main/ets/entryability/IntersectionMonitorAbility.ets
import { UIAbility } from '@kit.AbilityKit';
import { window } from '@kit.ArkUI';

export default class IntersectionMonitorAbility extends UIAbility {
  private floatWindow: window.Window | null = null;

  async onWindowStageCreate(windowStage: window.WindowStage): Promise<void> {
    // 创建浮动窗口
    this.floatWindow = await windowStage.createSubWindow('IntersectionMonitorFloat');
    
    // 配置浮动窗口属性
    await this.floatWindow.setWindowLayoutFullScreen(false);
    await this.floatWindow.setWindowSize({ width: 400, height: 300 });
    await this.floatWindow.setWindowPosition({ x: 100, y: 100 });
    await this.floatWindow.setWindowBackgroundColor('rgba(13,17,23,0.85)');
    
    // 加载浮动内容
    this.floatWindow.loadContent('pages/IntersectionMonitorFloatPage', (err) => {
      if (err) {
        console.error('Failed to load float content:', err);
        return;
      }
      console.info('Intersection monitor float window loaded');
    });

    // 焦点感知
    this.floatWindow.on('windowFocusChange', (isFocused) => {
      if (isFocused) {
        this.floatWindow?.setWindowBackgroundColor('rgba(13,17,23,0.95)');
      } else {
        this.floatWindow?.setWindowBackgroundColor('rgba(13,17,23,0.70)');
      }
    });
  }

  onWindowStageDestroy(): void {
    this.floatWindow?.destroy();
  }
}

5.7 多窗口光效同步管理器(WindowLightSync.ets)

代码亮点 :本模块实现了主窗口与三个浮动窗口之间的光效同步。通过 AppStorage 全局状态共享,当主窗口拥堵等级变化时,所有浮动窗口自动同步切换光效。支持焦点感知降级------当某个窗口获得焦点时,其他窗口的光效强度自动降低,避免视觉干扰。

TypeScript

typescript 复制代码
// entry/src/main/ets/services/WindowLightSync.ets
import { window } from '@kit.ArkUI';
import { CongestionLightManager, CongestionLightTheme, CongestionLevel } from '../theme/CongestionLightEffect';

/**
 * 窗口光效同步管理器
 * 实现主窗口与浮动窗口之间的光效联动
 */
export class WindowLightSync {
  private mainWindow: window.Window | null = null;
  private floatWindows: Map<string, window.Window> = new Map();
  private lightManager: CongestionLightManager;
  private isMainFocused: boolean = true;

  constructor(lightManager: CongestionLightManager) {
    this.lightManager = lightManager;
  }

  /**
   * 注册主窗口
   */
  public async registerMainWindow(windowStage: window.WindowStage): Promise<void> {
    this.mainWindow = await windowStage.getMainWindow();
    
    // 监听主窗口焦点
    this.mainWindow.on('windowFocusChange', (isFocused) => {
      this.isMainFocused = isFocused;
      this.syncLightIntensity();
    });

    // 监听光效变化
    this.lightManager.onThemeChange((theme) => {
      this.applyThemeToAllWindows(theme);
    });
  }

  /**
   * 注册浮动窗口
   */
  public registerFloatWindow(name: string, win: window.Window): void {
    this.floatWindows.set(name, win);
    
    // 监听浮动窗口焦点
    win.on('windowFocusChange', (isFocused) => {
      if (isFocused) {
        this.syncLightIntensity();
      }
    });
  }

  /**
   * 应用光效主题到所有窗口
   */
  private applyThemeToAllWindows(theme: CongestionLightTheme): void {
    // 主窗口应用完整光效
    if (this.mainWindow) {
      this.setWindowLightEffect(this.mainWindow, theme, 1.0);
    }

    // 浮动窗口应用同步光效
    for (const [name, win] of this.floatWindows) {
      const intensity = this.isMainFocused ? 0.6 : 0.9;
      this.setWindowLightEffect(win, theme, intensity);
    }
  }

  /**
   * 同步光效强度
   */
  private syncLightIntensity(): void {
    const theme = this.lightManager.getCurrentTheme();
    
    if (this.isMainFocused) {
      // 主窗口聚焦:主窗口100%,浮动窗口60%
      if (this.mainWindow) {
        this.setWindowLightEffect(this.mainWindow, theme, 1.0);
      }
      for (const [name, win] of this.floatWindows) {
        this.setWindowLightEffect(win, theme, 0.6);
      }
    } else {
      // 浮动窗口聚焦:浮动窗口90%,主窗口30%
      if (this.mainWindow) {
        this.setWindowLightEffect(this.mainWindow, theme, 0.3);
      }
      for (const [name, win] of this.floatWindows) {
        this.setWindowLightEffect(win, theme, 0.9);
      }
    }
  }

  /**
   * 设置窗口光效
   */
  private setWindowLightEffect(
    win: window.Window, 
    theme: CongestionLightTheme, 
    intensity: number
  ): void {
    try {
      // 设置窗口背景色调
      const r = parseInt(theme.primaryColor.slice(1, 3), 16);
      const g = parseInt(theme.primaryColor.slice(3, 5), 16);
      const b = parseInt(theme.primaryColor.slice(5, 7), 16);
      
      const alpha = Math.round(theme.ambientOpacity * intensity * 255);
      const bgColor = `rgba(${r}, ${g}, ${b}, ${alpha / 255})`;
      
      win.setWindowBackgroundColor(bgColor);
      
      // 设置边框光效
      win.setWindowShadow({
        radius: 20 * intensity,
        color: theme.primaryColor + Math.round(40 * intensity).toString(16).padStart(2, '0'),
        offsetX: 0,
        offsetY: -4
      });
    } catch (error) {
      console.error('Failed to set window light effect:', error);
    }
  }

  /**
   * 广播拥堵等级变化
   */
  public broadcastCongestionLevel(level: CongestionLevel): void {
    this.lightManager.switchCongestionLevel(level);
  }
}

六、关键技术总结

6.1 HMAF智慧交通开发清单

表格

技术点 API/方法 应用场景
智能体会话创建 hmaf.createAgentSession({ mode: MULTI_AGENT }) 多智能体协作调度
意图解析 intents.createIntentEngine({ supportedDomains }) 调度员查询意图理解
任务分发 hmafSession.sendTask({ targetAgent, taskType }) 智能体间交通任务调度
状态监听 AppStorage 全局状态回调 跨组件交通态势同步
分布式协同 enableDistributed: true 多设备交通运营协作

6.2 沉浸光感实现清单

表格

技术点 API/方法 应用场景
系统材质效果 systemMaterialEffect: SystemMaterialEffect.IMMERSIVE HdsNavigation标题栏
背景模糊 backgroundBlurStyle(BlurStyle.REGULAR) 悬浮导航玻璃拟态
背景滤镜 backdropFilter($r('sys.blur.20')) 精细模糊控制
安全区扩展 expandSafeArea([SafeAreaType.SYSTEM], [...]) 全屏沉浸布局
窗口沉浸 setWindowLayoutFullScreen(true) 无边框模式
光效动画 animation({ duration, iterations: -1 }) 呼吸灯背景
动态透明度 backgroundOpacity 焦点感知降级

6.3 拥堵等级光效映射

表格

拥堵等级 主色 辅色 脉冲间隔 环境透明度 应用场景
畅通(SMOOTH) #4CAF50 #81C784 3000ms 0.05 路网运行平稳
缓行(SLOW) #42A5F5 #90CAF9 2500ms 0.08 轻微流量增加
拥堵(CONGESTED) #FFA726 #FFCC80 1500ms 0.12 路口排队增长
严重拥堵(SEVERE) #EF5350 #EF9A9A 800ms 0.18 多路口连锁拥堵
瘫痪(PARALYZED) #D32F2F #E57373 400ms 0.25 区域交通瘫痪

6.4 PC端多窗口光效协同

表格

场景 主窗口光效 浮动窗口光效 同步机制
主窗口聚焦 100%强度 60%强度 AppStorage广播
浮动窗口聚焦 30%强度 90%强度 焦点事件触发
拥堵等级变化 全色域切换 同步色域切换 主题回调监听
调度完成 确认绿光 同步绿光 状态变更通知

七、调试与适配建议

7.1 交通数据解析性能优化

  • 采样策略:高流量环境采用1:1000采样,低流量环境全量采集
  • 异步处理 :数据解析使用 TaskPool 异步线程,避免阻塞UI
  • 缓存机制:历史基线数据本地缓存,减少云端查询延迟

7.2 拥堵光效可访问性

  • 色盲友好:除颜色外,增加图标形状差异(圆形/三角形/菱形)
  • 闪烁控制:瘫痪状态的脉冲频率不超过3Hz,避免光敏性癫痫触发
  • 手动关闭:提供"光效静音"开关,满足特殊环境需求

7.3 多窗口管理优化

  • 窗口记忆:记录浮动窗口位置与大小,下次启动自动恢复
  • 吸附对齐:浮动窗口靠近边缘时自动吸附,避免遮挡关键内容
  • 一键归位:提供"重置布局"按钮,快速恢复默认窗口配置

八、运行效果展示

8.1 畅通态势 - 柔绿光效

路网运行平稳,无异常拥堵。环境光呈现柔和绿色,路口缓慢呼吸,车流稳定流光。

8.2 缓行态势 - 淡蓝光效

检测到轻微流量增加。环境光转为淡蓝,缓行路口蓝色脉冲,车流流光加速。

8.3 拥堵态势 - 暖黄光效

识别路口排队增长。环境光转为暖黄,拥堵路口黄色脉冲,悬浮导航显示拥堵徽章。

8.4 严重拥堵态势 - 橙红光效

确认多路口连锁拥堵。环境光转为橙红,严重拥堵路口红色脉冲,车流流光急速流动,悬浮导航显示严重拥堵徽章。

8.5 瘫痪态势 - 警示红光效

区域交通瘫痪。环境光强烈红光闪烁,瘫痪路口快速脉冲,所有窗口同步红色告警,悬浮导航显示瘫痪徽章并震动提醒。


九、总结与展望

本文基于HarmonyOS 6(API 23)的悬浮导航沉浸光感HMAF智能体框架特性,完整实战了一款面向PC端的"光脉智城"智慧交通态势感知与调度指挥中心。核心创新点总结:

  1. HMAF四层交通智能体:基于Agent Framework Kit构建数据采集Agent(多源交通数据实时采集与融合)、态势研判Agent(实时交通态势分析与拥堵成因识别)、拥堵预测Agent(基于时序模型的拥堵预测)、智能调度Agent(信号优化与协调控制),实现"数据采集→态势研判→拥堵预测→智能调度"的全链路自动化,态势研判效率提升50倍
  2. 拥堵等级光效系统:五种交通状态拥有专属光效人格(畅通柔绿、缓行淡蓝、拥堵暖黄、严重拥堵橙红、瘫痪警示红),根据当前路网最高拥堵等级动态切换全局环境光、路口脉冲和导航材质,实现调度员"一眼感知拥堵"的直觉体验
  3. 悬浮态势导航:底部悬浮页签承载"态势总览/路口监控/车流分析/信号调度"四个运营阶段,实时显示拥堵统计徽章(瘫痪/严重拥堵/拥堵数量)和智能体运行状态角标,玻璃拟态设计+三档透明度调节,最大化态势展示区域
  4. PC级多窗口协作调度 :主态势感知窗口 + 浮动路口监控窗口 + 浮动车流热力图窗口 + 浮动信号调优窗口的四层架构,通过 WindowLightSync 实现跨窗口光效联动与焦点感知,符合调度员的专业调度工作习惯
  5. 调度意图沉浸感知:通过Intents Kit解析调度员的查询意图(如"查找中山路与建设大道交叉口过去一小时的拥堵成因"),自动触发对应Agent协作并调整界面拥堵光效,实现"查询即氛围"的沉浸体验

未来扩展方向

  • 车路协同模式:增加V2X通信智能体,实现车辆与基础设施的实时协同
  • 数字孪生路网:构建城市路网的数字孪生,支持交通仿真与方案预演
  • 跨设备交通协同:利用鸿蒙分布式能力,实现PC主控+大屏展示+移动端现场巡查的协同交通运营
  • 自动驾驶对接:与L4级自动驾驶系统对接,实现信号灯与自动驾驶车辆的协同优化

转载自:https://blog.csdn.net/u014727709/article/details/162363352

欢迎 👍点赞✍评论⭐收藏,欢迎指正