移动端大屏端布局适配
刀刀
4/8/2025
0 字
0 分钟
- UP主:三十的前端课,视频地址:前往学习
核心思想
- 布局更多使用
flex
,尺寸使用rem
、vw
、vh
为单位 - 根据不同屏幕尺寸需要不同布局,采用多个站点切换或者媒体查询使用
css
rem
页面尺寸计算
以 HTML 字体大小为 1rem 的大小,HTML 为 16px ,1rem 则为 16px。rem
之所以能自适应就是根据屏幕大小用 JavaScript 重新计算设置 1rem 的大小。
计算公式为:页面宽度 除以 设计稿宽度(一般是 750)再乘想要设置 1rem 为多少 px
(这里取 1rem 为 16px)。
来到 index.html
或 App.vue
组件,计算 1rem 的大小。步骤如下:
- 获取整体页面宽度
- 根据比例计算 1rem 的大小
- 为整体 HTML 根元素添加字体大小的样式
- 绑定页面尺寸修改事件,触发事件后重新计算
const resizeFn = () => {
let fontSize = (document.body.clientWidth / 750) * 16;
document.documentElement.style.fontSize = fontSize + "px";
};
resizeFn();
window.addEventListener("resize", resizeFn);
如果想要给整体项目添加最大宽度,则用页面整体宽度和最大宽度做比较取最小值。
let fontSize = (Math.min(document.body.clientWidth, 750) / 750) * 16; // [!code++]
document.documentElement.style.fontSize = fontSize + "px";
现在可以把页面元素样式单位修改为 rem
,保存刷新后就可查看效果。
第三方库使用
手动一个个把 px
改成 rem
费时费力,开发效率低下,引入第三方库 postcss-pxtorem
可以有效提高开发效率。该第三方库可以在运行时和打包部署后自动帮我们转换单位。
下载依赖
shpnpm i postcss-pxtorem
在
vite.config.js
引入jsimport postcsspxtorem from "postcss-pxtorem";
配置
jsexport default defineConfig({ css: { postcss: { plugins: [ postcsspxtorem({ rootValue: 16, // ui设计稿宽度 / 10 unitPrecision: 3, // 指定`px`转换为视窗单位值的小数位数 propList: ['*'], // 需要转换的属性列表,*表示全部(如果设置width,则width的值会被转换) selectorBlackList: ['ignore'], // 指定不需要转换的类 replace: true, // 是否直接更换属性值,而不添加备用属性 mediaQuery: false, // 是否在媒体查询的css代码中也进行转换,默认false minPixelValue: 0, // 设置最小的转换数值,如果为1的话,只有大于1的值会被转换 exclude: /node_modules/i // 忽略某些文件夹下的文件或特定文件,例如 'node_modules' 下的文件 }) ] } } })
现在可以解放双手,放心大胆的设置单位为 px
,它会帮我们自动转为 rem
。
注意
使用这个第三方库还是要在 index.html
或 App.vue
组件设置根元素的字体大小样式,否则不生效。
vw,vh
1vw-1%视口宽度,1vh-1%视口高度。
假设屏幕宽高为 750*1200,那么 1vw 就是 75px,1vh 就是 120。
使用 vw
做单位无需要做计算,因为 vw
会自动根据屏幕宽度变化,vh
一般用来做全屏设计。
对应的自动转化库:postcss-px-to-viewport
。
第三方库
下载依赖
shpnpm i postcss-px-to-viewport
引入
jsimport postcsspxtoviewport from "postcss-px-to-viewport";
配置
jsexport default defineConfig({ css: { postcss: { plugins: [ postcsspxtorem({ // ... }), postcsspxtoviewport({ unitToConvert: "apx", // 想要转换的单位 viewportWidth: 750, unitPrecision: 6, propList: ["*"], // 需要转换的属性列表,*表示全部(如果设置width,则width的值会被转换) viewportUnit: "vw", // 指定需要转换成的单位,默认vw selectorBlackList: ["ignore"], // 指定不需要转换的类 minPixelValue: 1, // 默认值1,小于或等于1ox不做转换 mediaQuery: false, // 是否在媒体查询的css代码中也做转换,默认false replace: true, // 是否直接更换属性值,而不添加备用属性 }), ], }, }, });
百分比
百分比是相对于父元素的百分比,所以一般除非是最外层的容器,否则不具备响应式调整的功能。
方案对比
rem VS vw
两个方案都可以用于控制某个盒子的大小,都会根据屏幕宽度灵活变化。rem
相对于 vw
灵活度更高,如果你的移动端项目还需要 web
端浏览,那么 rem
可以做到 vw
做不到事情。如果页面单纯是在移动端看(比如 app
内 web
)。
rem
不去监听 resize
事件,去修改 fontSize
是做不到在动态改变屏幕宽度时变化大小的。如果不想监听 resize
事件,或者变化触发不了 resize
,使用 vw
。
百分比
百分比并不是一无是处,rem
和 vw
都是根据屏慕去算的,如果我们需要根据父组件去缩放我们可以就必须用百分比了,比如父元素是一个用 js
计算出来的尺寸的盒子,我们现在希望里面的两个内容一个占百分之 30,一个占百分之 70。
其他注意事项
- 关于边距处理-靠左靠右这种用
flex
,顶开部分小距离rem
,vw
- 图片一般都定宽不定高,防止图片变形,但是如果如果屏幕跨度过大,可能会导致图片大到很夸张,可以考虑把图片设置最大宽度,然后居中,避免过长
- 在一些大屏可视化项目中,界面必须是刚好满屏幕的,不能溢出不能短。但是当通过 F11 切换全屏,会引起高度变化,
rem
和vw
是不会变化的。所以这种需求的项目,有的高度可以用 vh 来做。
总体效果
总体效果可前往刀刀博客查看,地址 刀刀博客 。