MST
星途 面试题库

面试题:CSS 响应式设计中媒体查询与响应式单位的前沿实践与性能权衡

在一个具有复杂交互和动画效果的单页应用中,要实现全方位的响应式设计。不仅要考虑不同屏幕尺寸(从手表等小屏幕到超大显示器),还要兼顾高刷新率屏幕和不同像素密度设备。请详细阐述如何结合媒体查询与响应式单位(包括 vw/vh、rem 等)进行设计,以及如何在保证视觉效果和交互流畅性的同时,平衡页面性能,给出具体的策略和示例代码片段。
15.0万 热度难度
前端开发CSS

知识考点

AI 面试

面试题答案

一键面试

结合媒体查询与响应式单位进行设计

  1. 媒体查询 媒体查询允许根据设备的特性(如屏幕宽度、高度、分辨率、方向等)应用不同的 CSS 样式。
    • 屏幕宽度:针对不同的屏幕宽度范围设置样式,以适配手机、平板、桌面等设备。
    /* 手机屏幕(竖屏) */
    @media (max - width: 480px) {
      body {
        font - size: 14px;
      }
    }
    /* 平板屏幕(竖屏) */
    @media (min - width: 481px) and (max - width: 768px) {
      body {
        font - size: 16px;
      }
    }
    /* 桌面屏幕 */
    @media (min - width: 769px) {
      body {
        font - size: 18px;
      }
    }
    
    • 屏幕方向:根据设备是竖屏还是横屏调整布局。
    /* 竖屏 */
    @media (orientation: portrait) {
      .container {
        flex - direction: column;
      }
    }
    /* 横屏 */
    @media (orientation: landscape) {
      .container {
        flex - direction: row;
      }
    }
    
    • 分辨率:处理不同像素密度的设备,例如视网膜屏。
    /* 高分辨率屏幕 */
    @media (-webkit - min - device - pixel - ratio: 2), (min - resolution: 192dpi) {
      .image {
        background - image: url(high - res - image.jpg);
      }
    }
    
  2. 响应式单位
    • vw/vh:视窗宽度(vw)和视窗高度(vh)是相对于视口的尺寸。1vw 等于视口宽度的 1%,1vh 等于视口高度的 1%。常用于设置元素的宽度、高度、字体大小等。
    .header {
      height: 10vh;
      width: 100vw;
    }
    
    • rem:根 em 单位,是相对于根元素(通常是 <html> 元素)的字体大小。通过改变根元素的字体大小,可以统一调整整个页面的尺寸。
    html {
      font - size: 16px;
    }
    body {
      font - size: 1rem; /* 等于 16px */
    }
    .small - text {
      font - size: 0.875rem; /* 14px */
    }
    

平衡页面性能策略

  1. 图片优化
    • 对于不同屏幕分辨率和尺寸,提供合适分辨率和尺寸的图片。可以使用 <picture> 元素结合 srcset 属性。
    <picture>
      <source media="(min - width: 1200px)" srcset="large - image.jpg">
      <source media="(min - width: 768px)" srcset="medium - image.jpg">
      <img src="small - image.jpg" alt="description">
    </picture>
    
  2. 动画与交互优化
    • 使用 CSS 动画而不是 JavaScript 动画,因为 CSS 动画由浏览器的合成器处理,性能更好。
    • 对于复杂动画,使用 requestAnimationFrame 来控制动画的帧率,避免过度绘制。
    function animate() {
      // 动画逻辑
      requestAnimationFrame(animate);
    }
    animate();
    
  3. 代码拆分与懒加载
    • 将单页应用的代码拆分成多个部分,按需加载。例如,使用动态导入(ES6 的 import())加载路由组件。
    const routes = [
      {
        path: '/home',
        component: () => import('./components/Home.vue')
      },
      {
        path: '/about',
        component: () => import('./components/About.vue')
      }
    ];
    
    • 对于非关键资源(如图片、脚本等),使用懒加载。例如,使用 IntersectionObserver 实现图片懒加载。
    const images = document.querySelectorAll('img[data - lazy]');
    const observer = new IntersectionObserver((entries, observer) => {
      entries.forEach(entry => {
        if (entry.isIntersecting) {
          const img = entry.target;
          img.src = img.dataset.lazy;
          observer.unobserve(img);
        }
      });
    });
    images.forEach(image => {
      observer.observe(image);
    });