唯杰地图 logo唯杰地图
VJMAP
EN

fx-presets

vjmapext/references/perf/fx-presets.md 7.5 KB166 行
原文

本文回答:fx 的 12 点预设 + 5 线预设 —— 各自效果、适合场景、选型指南。

一、12 点预设

所有点预设签名:fx.addPoint(name, opts) → handle。

# 预设 视觉 典型用途
1 fire 火焰(动态噪声 + 暖色) 故障点 / 燃烧告警
2 pulseRing 脉冲光环(持续扩散) 监控告警 / 活动节点
3 halo 柔光光晕(静态发光) 重要位置突出 / hover 提示
4 radarSweep 雷达扫描(扇形旋转) 扫描范围 / 动态指示
5 smoke 烟雾(柔和粒子) 工厂 / 事故现场
6 lightning 闪电(分叉动画) 瞬时告警 / 一次性触发
7 meteor 流星(拖尾扩散) 动态飞入点 / 粒子爆炸
8 vortex 漩涡(旋转几何) 动态压制 / 风暴中心
9 shield 护盾(几何网格) 防护范围 / 隔离区
10 firework 烟花(一次性爆炸) 庆祝 / 警报一次
11 crosshair 十字锁定(描边瞄准) 战术锁定关键目标
12 shadertoy ⚠️ 1.0.1 经 addPoint 用时忽略 fragmentShader,渲染的是 fire 着色器 自定义 GLSL 请改用 fx.addShadertoy(见 shadertoy)

二、通用字段

fx.addPoint('halo', {
  cad: [100, 200],         // 或 lngLat / mercator
  size: 80,                // 尺寸(默认 'map' 单位)
  sizeUnits: 'map',        // 'map' 跟随缩放 / 'pixels' 屏幕恒定
  color: [1, 0.5, 0, 1],   // RGBA 0~1
  params: [0, 1, 1, 0.5],  // [kind, p1, p2, p3]:槽 0 会被强制覆盖为预设 kind,只需关心 1..3
  bucket: 'above',         // 'below' / 'above' / 'topmost'
  visible: true,
  triggerOnce: false,      // 一次性
  ttl: 2000                // 一次性的生命周期(ms)
});

params[0] 是预设 kind——实现里会被强制覆盖为所选预设的 kind 值,传什么都被忽略;params[1..3] 才是可调参数(含义随预设变化)。注意 params 若传必须恰好是长度 4 的 vec4(SymbolFxImage.setParams/preset 校验长度,不对直接 throw)。

三、5 线预设

签名:fx.addLine(name, opts) → handle。

# 预设 视觉 典型用途
1 flowLine 流光管线(光沿线跑) 管道 / 链路流向
2 meteor 流星线(头亮尾淡) 态势飞线 / 攻击路径
3 lightning 闪电线(分叉抖动) 瞬时告警路径
4 arrowFlow 箭头流动(带方向) 有向图 / 数据流
5 dashFlow 虚线流动 非实体线 / 提示
fx.addLine('flowLine', {
  path: { cad: [[x1, y1], [x2, y2], [x3, y3]] },  // FxPathInput:cad / lngLat / mercator 三选一
  width: 4,          // 线宽(widthUnits 默认 'pixels')
  color: [0, 1, 1, 1],
  bucket: 'above'
});

四、Shadertoy 入口

3 个自定义入口:

// 三者都是单参数 opts 对象
fx.addShadertoy({ cad: [x, y], fragmentShader: 'void mainImage(...)...', size: 120 });
fx.addShadertoyLine({ path: { cad: [[x1,y1],[x2,y2]] }, fragmentShader: '...', width: 6 });
fx.addShadertoyFullscreen({ fragmentShader: '...' });   // 全屏 NDC 覆盖,不绑坐标

支持 5 种 alphaMode:premul / opaque / additive / luma / colorKey,用于和底图混合。

详见 vjmapext 的 fx shadertoy 文档(MCP mapext/docs/fx/shadertoy.md,入口 https://vjmap.com/server/aimcp/mcp?products=mapext)。

五、一次性触发

fx.addPoint('lightning', {
  cad: [x, y], size: 60,
  triggerOnce: true,
  ttl: 800          // 800ms 后自动移除
});

内建 lightning 和 firework 是"瞬发即灭"型;triggerOnce: true 跑完自动清理。

六、选型指南

数量

数量 推荐
< 100 任何预设都 OK
100~1000 全部 standard / 部分 lite
1000~10000 lite + 精选 2~3 个预设
> 10000 fx.symbolImage 走 symbol 图层

场景

场景 推荐预设
动态告警 pulseRing / halo / fire
瞬时事件 lightning / firework(triggerOnce)
流向 flowLine / arrowFlow / meteor line
范围 shield / radarSweep
锁定 crosshair
高级自定义 fx.addShadertoy(不是 addPoint('shadertoy'))

七、CAD 实体绑定 FX

const circle = new vjmapext.CircleEnt([100, 200], 50);
mapcadLayer.addEntity(circle);

fx.bindToEntity(circle, 'pulseRing', {
  color: [1, 0, 0, 1],
  size: 60
});

// 实体动 → FX 跟随;实体删 → FX 自动清理

八、关掉不用的预设省 GPU

// 清空某预设在默认 'above' 桶的全部实例(replaceAllPoints 传空数组)
fx.replaceAllPoints('fire', []);
// 或整个 FX 层清空(所有预设所有 bucket):fx.removeAll()

预设首次使用时编译 shader / 创建 buffer;不再用时可清零回收。没有 removeAllOfPreset——按预设清空用 replaceAllPoints(preset, []),按句柄删单个用 fx.remove(handle)。

⚠️ replaceAllPoints 的限制(1.0.1):

  • 只动默认 above 桶:below/topmost 里的同预设实例不清;新列表里每项的 bucket 也被忽略,一律加进 above。
  • 不走 addPoint 的语法糖:triggerOnce/ttl 自动移除、lightning 的 strikeEvery 都不生效。
  • 它会重置该预设的槽位分配器——之前拿到的该预设句柄(含 bindToEntity 绑定的)全部失效,甚至可能与新点串号;有实体绑定的预设别用它整批替换。

九、色彩搭配建议

语义 色值(RGBA 0~1)
告警红 [1, 0, 0, 1]
警告橙 [1, 0.5, 0, 1]
信息蓝 [0, 0.7, 1, 1]
成功绿 [0, 1, 0.3, 1]
高亮金 [1, 0.85, 0, 1]

alpha 0.8~0.9 对光晕类效果自然;完全不透明会掩盖底图。

十、常见坑

  1. params[0] 传了自定义值:无害但无效——实现会强制覆盖为预设 kind;要调效果改 p1/p2/p3(各预设含义不同)。
  2. 颜色传 0~255:FX 要 0~1;传错没错误但色很淡。
  3. sizeUnits 用 pixels 但 size 太大:屏占比大 → GPU 贵;用 map 跟随缩放。
  4. 所有预设都 cinematic:卡;按重要度选档。
  5. triggerOnce 但没 ttl:内建 lightning/firework 有默认 ttl;自定义没有 ttl 永不清理。
  6. addLine 的坐标要包在 opts.path 里:addLine('flowLine', { cad: [[x1,y1],[x2,y2]] })(把 cad 写在 opts 顶层)会抛 Cannot read properties of undefined (reading 'lngLat')——校验器读的是 opts.path.cad。正确形态 addLine('flowLine', { path: { cad: [[...]] } })。
  7. 校验报错是无条件的,并非只在 dev 抛出:fx.addPoint('not-a-preset', {cad}) 抛 [FX] unknown point preset,缺坐标(cad/lngLat/mercator 三选一都不给)、size<=0、非法 bucket、params 非 vec4 同样总是抛错——addPoint/addLine/addPoints 的 validatePointOptions/validateLineOptions 在调用链上不被环境门控。真正被 if(ht)(typeof process==="undefined" || NODE_ENV!=="production")包裹的只是 addShadertoy/addShadertoyLine/addShadertoyFullscreen/setShadertoyUniforms 里的 mainImage 正则、resolution 等额外校验——而浏览器里 process 未定义使 ht 恒为 true,这些校验在 vite 产物中实际也总是执行。

相关