npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

postcss-adaptive-matrix

v0.8.1

Published

Responsive CSS compiler for PostCSS 8 with per-design canvases, optional fluid bounds, rem-aware typography, container units, component-library routing, and CLI diagnostics.

Readme

你按设计稿写 px,编译器负责换算。但换算的前提是先知道这个 px 画在哪张稿子上——这就是整个项目的核心模型。

同一个 16px,三个正确答案

页面画在 750 上,装进来的移动端组件库画在 375 上,桌面端组件库根本没有画布而是按真实像素绘制。把它们塞进同一个换算公式,得到的一定是三个错误里挑一个。

把组件库加进忽略名单也解决不了:页面缩放而组件不动,或者组件按错误画布被拉变形——这正是忽略名单唯一能给出的两个选项。

给每张设计稿一个画布,才是对的。而这是默认行为,不需要配置。

安装

npm i -D postcss postcss-adaptive-matrix

程序化接口

构建脚本与编辑器工具也可以直接调用编译接口:

import { compileAdaptiveCss } from 'postcss-adaptive-matrix'

const { css, warnings } = await compileAdaptiveCss('.card { padding: 24px }')

只有 CSS 输入必填。多文件可使用 createAdaptiveCompiler() 复用配置,也可按需传入 PostCSS 源码映射选项和浏览器目标。结果字段和错误处理见程序化编译。

快速开始

在 postcss.config.mjs 中先零配置接入:

import adaptiveMatrix from 'postcss-adaptive-matrix'

export default {
  plugins: [adaptiveMatrix()],
}

这会使用内置画布和组件库路由,不注入全局根样式。开始使用不需要填写任何配置字段。只覆盖与设计稿或布局不同的部分即可;例如下面的移动端/桌面端预设使用 #app 根容器基础样式:

import adaptiveMatrix, { appPcPreset } from 'postcss-adaptive-matrix'

export default {
  plugins: [
    adaptiveMatrix(
      appPcPreset({
        appDesignWidth: 375,
        pcDesignWidth: 1440,
        rootSelector: '#app',
      }),
    ),
  ],
}

业务 CSS 照常写:

.page {
  padding: 16px;
  font-size: 16px;
}

@adaptive pc {
  .page {
    padding: 48px 64px;
  }
}

输出:

.page {
  padding: clamp(13.65333px, 4.26667vw, 20.48px);
  font-size: clamp(0.94867rem, calc(0.65rem + 1.49333vw), 1.098rem);
}

@media (min-width: 768px) {
  .page {
    padding: clamp(34.13333px, 3.33333vw, 64px) clamp(45.51111px, 4.44444vw, 85.33333px);
  }
}

到这里,组件库适配、安全区变量、根列布局和 position: fixed 修正已经全部生效,不需要再写一行配置。

能力

| | | | --- | --- | | 多画布 | App、PC、平板、车机各有独立设计宽度、断点、流体区间与单位 | | 有界流体 | 默认输出 clamp(),不会无限放大或无限压缩 | | 根字号响应 | rem + vw 混合公式保留根字号相对分量;仍需真实缩放验收 | | 组件库开箱适配 | 11 个库、12 个适配条目:移动端库按各自画布换算,桌面端库默认保留原始像素 | | 主题 token | :root 上的库变量按名字识别,字号自动走文字公式 | | 固定定位修正 | 居中列布局下 position: fixed 不再贴到视口边 | | 容器查询 | unit: 'cqi' + @container,尺寸依赖容器而非窗口 | | 原子化 CSS | Tailwind 与 UnoCSS 两个大版本,连它们工具类读的主题 token 一起认领 | | 可选运行时 | VisualViewport 观察器,覆盖 WebView、软键盘与动态视口 | | 命令行预览 + JSON 报告 | 改完配置不用构建;人能看逐条换算,CI 能读带版本号的结构化诊断 | | 断点接缝检查 | 自动找出「窗口变宽、尺寸反而变小」的位置——两张设计稿没对齐的地方 | | 浏览器支持审计 | 拿产物去对你要支持的最低浏览器版本,逐条列出超标的语法 | | 工程化 | 完整 TypeScript 类型,ESM + CJS 双产物,语言无关一致性套件 |

有界流体尺寸

纯 vw 没有尺寸边界。内置 profile 带有上下界:区间内尺寸跟随视口,区间外停住。这是预设的选择,不是自定义 profile 的必填字段。

fluid 不是必填,minWidth 与 maxWidth 也都不是必填:省略整个 fluid(或写 {})得到无边界流体表达式,只写一端得到单侧边界,两端都写时才生成 clamp()。Profile 真正不可省略的只有用于换算的 designWidth,不需要覆盖其他行为时还能直接简写成 profiles: { app: 375 }。

组件库开箱适配

adaptiveMatrix({
  defaultProfile: 'app',
  profiles: {
    app: { designWidth: 750, fluid: { minWidth: 320, maxWidth: 600 } },
  },
})
/* 输入 —— 四处都写 16px */
:root       { --van-padding-md: 16px }
.van-cell   { padding: 16px }
.el-input   { padding: 16px }
.page-hero  { padding: 16px }
/* 输出 —— 各按所属画布 */
:root       { --van-padding-md: clamp(13.65333px, 4.26667vw, 25.6px) }
.van-cell   { padding: clamp(13.65333px, 4.26667vw, 25.6px) }
.el-input   { padding: 16px }
.page-hero  { padding: clamp(6.82667px, 2.13333vw, 12.8px) }

内置:vant、nutui、varlet、antd-mobile、taro-ui、element-plus、antd、arco-design、naive-ui、quasar、mui。

未收录的库写一行定义即可,收录的库用 extends 改一项即可。完整说明见组件库适配。

精准控制

/* adaptive-ignore-next */
width: 320px;              /* 忽略下一条声明 */

height: 44px;              /* adaptive-ignore */   /* 忽略当前行 */

/* adaptive-ignore-rule */
.widget { width: 300px }   /* 忽略下一整个规则 */

这三个注释会保留在产物里,因此产物再过一遍编译时仍然生效(压缩器会去掉它们)。默认保留不超过 1px 的细线;字符串、url()、local()、format() 不会误转换。

改一个数字,立刻看到结果

npx adaptive-matrix src/styles/app.css
src/styles/app.css
  profiles: app (default), pc, +5 library canvases
  .page
    padding    16px → clamp(13.65333px, 4.26667vw, 20.48px)
    font-size  16px → clamp(0.94867rem, calc(0.65rem + 1.49333vw), 1.098rem)
  @media (min-width: 768px) › .page
    padding    48px → clamp(34.13333px, 3.33333vw, 64px)
  shrinks .card font-size gets smaller at 768px: 17.57px → 16.18px
  3 converted, 0 left as authored

不用启动构建,不用开浏览器。

最后那行是断点接缝检查:App 稿写 16px、PC 稿写 18px,两个数字单独看都合理,但窗口跨过断点时,正文字号会突然变小。同一固定视口画布中,单个转换长度的绝对值不会随视口变宽而减小;负外边距则是通过变得更负来增大。检查器比较已知断点两侧的绝对值,提示可能的交接问题,也会分析手写 CSS 表达式。发现问题后应检查层叠和画布选择,不能断言换画布是唯一原因;无法解析的表达式与条件可能被跳过,因此没有报告也不代表布局一定正确。

--from 还能把文件路由先试一遍——这是最容易配错又最不容易发现的一项。详见命令行预览。

产物到底要求浏览器做到什么

npx adaptive-matrix src/app.css --targets "ios_saf 13, chrome 90"
  需要 @layer — iOS Safari 13 < 15.4,Chrome 90 < 99
          不支持时:整个 @layer 块会被丢弃,连同根级基础样式一起消失——
          居中列、安全区变量和固定定位修正会同时失效。
          替代:root.layer: false 会输出不带包裹层的相同规则 …
  需要 clamp()、min()、max() — iOS Safari 13 < 13.4-13.7

CSS 不会优雅降级,它丢弃,而且全程不说话:值读不懂丢一条声明,选择器读不懂丢一整条规则,@ 规则读不懂丢一整块。所以审计读的是编译产物而不是配置——这是让两者永远不会走偏的唯一做法——并且对每一项先说丢什么,再说换成什么。

版本数据在构建期烘焙进包,因此不增加任何运行时依赖,离线可用。见浏览器特性支持与降级。

文档

| | | | --- | --- | | 快速上手与双设计稿工作流 | 从安装到 App/PC 双稿协作 | | 构建工具集成 | Vite、Nuxt、Webpack、Taro,以及四个静默出错的点 | | 命令行预览 | npx adaptive-matrix:不用构建就能看到换算结果 | | 组件库适配 | 内置清单、匹配方式、覆盖与扩展 | | 配置参考 | 全部选项、类型与默认值 | | 架构与转换公式 | 编译流程、数学公式、幂等、实现边界 | | 可选运行时 | VisualViewport 观察器:软键盘、地址栏、WebView | | 浏览器特性支持与降级 | 特性 × 版本表、不支持时丢什么、每一项怎么关 | | 迁移指南 | 从其它 px 换算方案迁移 | | 发布与兼容性 | 产物、Node 版本、版本策略 | | 一致性套件 | 语言无关的行为规范 | | 完整示例 | 可运行的 App + PC 工程 |

兼容性

  • Node.js 18+,PostCSS 8.4+
  • clamp()、min():现代浏览器基线能力
  • 容器查询配置需要支持 @container / cqi 的浏览器
  • 更老的 WebView 使用 strategy: 'viewport',或配合 preserveOriginal: true 自行提供降级值——用 --targets 可以直接看到产物到底要求了什么

开发

npm install
npm run check          # 类型检查 + 覆盖率测试 + 构建
npm run conformance:update
npm run bench

License

MIT。欢迎阅读贡献指南参与开发;安全问题请按安全策略私下报告。