写过 JS 的人都踩过这个坑——CSS 属性读了半天还是个字符串,今天 CSS Typed OM 把这件事彻底原生化了

每次用 JS 读 CSS 属性都要和字符串打交道:el.style.opacity 返回的是字符串,不是数字。想做个简单的加法都要 parseFloat 转一圈。更坑的是,你以为自己在做加法:el.style.opacity += 0.1,结果是字符串拼接,不是数值加法。

Firefox 155 稳定版把这件事彻底原生化了——CSS Typed OM 让所有 CSS 属性在你的 JS 里以类型化对象的形式存在,读出来是什么类型、写进去还是什么类型,数学运算不用再绕弯。

为什么字符串式的 CSSOM 一言难尽

传统 CSSOM 暴露的属性值全是字符串:const width = div.style.width; // “200px”,字符串。数值运算要手动 parse、字符串拼接 bug、单位处理靠猜。Typed OM 把这些问题全部用类型系统封死了。

Typed OM 核心:两种 StylePropertyMap

读 computed 样式用 computedStyleMap():

const styleMap = element.computedStyleMap();
const opacity = styleMap.get(“opacity”);
console.log(opacity.value, opacity.unit); // 0.5, “number”

写行内样式用 attributeStyleMap:

element.attributeStyleMap.set(“opacity”, CSS.number(0.3));
element.attributeStyleMap.set(“width”, CSS.px(200));
const op = element.attributeStyleMap.get(“opacity”);
op.value += 0.1; // 0.4,不是字符串拼接
element.attributeStyleMap.set(“opacity”, CSS.number(op.value));

delete():终于可以删单个属性了

Firefox 155 新增的支持,element.attributeStyleMap.delete(“opacity”),配合 has/set 形成完整 CRUD。

实际场景:动画插值

以前:const from = parseFloat(getComputedStyle(el).opacity); el.style.opacity = String(from + (1 – from) * 0.5);

Typed OM:const fromVal = el.computedStyleMap().get(“opacity”).value; el.attributeStyleMap.set(“opacity”, CSS.number(fromVal + (1 – fromVal) * 0.5));

兼容性

Chrome 66+ 从 2018 年就开始支持,Firefox 155 稳定版补全了 StylePropertyMap.delete()。Safari 暂未支持,约 70% 全球覆盖。建议渐进增强。

下一步

如果你在写任何涉及 CSS 数值读写的 JS——动画、拖拽、resize 监听——先数一下代码里有多少 parseFloat。Typed OM 可以把这些全部替换掉,bug 会少很多。

评论区

0 条评论

登录后可评论。

阿柯·前端架构 16 阅读