28
CSS往往是我们前端开发者不太看重的一环,而且现在重构岗也越来越少,不像前几年前端领域还分为js岗和重构岗。注重基础的面试官,在CSS基础回答不上时,印象分就会有所下降。下面整理一些常问到的CSS的知识点,欢迎指正,整理不易,点个赞再走吧。。。

首先我们以一道面试题为考察点

如何实现三栏布局?

三列布局,其中一列宽度自适应,其他两列固定
首先我们来看最终实现效果,对于下方几种实现方式,可以先自己试试,再往下看

  • 首先对样式进行reset
<style>
    * {
        margin: 0;
        padding: 0;
    }
    div {
        min-height: 100px;
    }
    h2, h4 {
        text-align: center;
    }
    .left, .right {
        width: 300px;
        background: rgba(0, 0, 0, 0.3);
    }
    .center {
        background: rgba(0, 0, 0, 0.2);
    }
    .layout {
        margin: 10px 0;
    }
</style>
  • 浮动布局
<div class="layout float">
    <style media="screen">
        .float .left {
            float: left;
        }

        .float .right {
            float: right;
        }
    </style>
    <section class="float-layout">
        <div class="left"></div>
        <div class="right"></div>
        <div class="center">
            <h4>浮动三栏布局</h4>
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
        </div>
    </section>
</div>
  • 绝对定位布局
<div class="layout absolute">
    <style>
        .absolute div {
            position: absolute;
        }

        .absolute .left {
            left: 0;
            width: 300px;
        }

        .absolute .center {
            left: 300px;
            right: 300px;
        }

        .absolute .right {
            right: 0;
            width: 300px;
        }
    </style>
    <section class="absolute-layout">
        <div class="left"></div>
        <div class="center">
            <h4>绝对定位解决方案</h4>
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
        </div>
        <div class="right"></div>
    </section>
</div>
  • flex布局
<div class="layout flexbox">
    <style>
        .flexbox .flex-layout {
            display: flex;
        }

        .flexbox .left {
            width: 300px;
        }

        .flexbox .center {
            flex: 1;
        }

        .flexbox .right {
            width: 300px;
        }
    </style>
    <section class="flex-layout">
        <div class="left"></div>
        <div class="center">
            <h4>flexbox解决方案</h4>
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
        </div>
        <div class="right"></div>
    </section>
</div>
  • table布局
<div class="layout table">
    <style>
        .layout.table .table-layout {
            width: 100%;
            height: 100px;
            display: table;
        }

        .layout.table .table-layout>div {
            display: table-cell;
        }
    </style>
    <section class="table-layout">
        <div class="left"></div>
        <div class="center">
            <h4>表格布局解决方案</h4>
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
        </div>
        <div class="right"></div>
    </section>
</div>
  • grid布局
<div class="layout grid">
    <style>
        .grid .grid-layout {
            width: 100%;
            display: grid;
            grid-template-rows: 100px;
            grid-template-columns: 300px auto 300px;
        }    
        .grid .left {
            width: 300px;
        }
    </style>
    <section class="grid-layout">
        <div class="left"></div>
        <div class="center">
            <h4>网格布局解决方案</h4>
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
            这是三栏布局的浮动解决方案;
        </div>
        <div class="right"></div>
    </section>
</div>

还有许多相似的问题,比如水平垂直居中品字布局的实现方式等,都是同一个原理,主要的考察点:

1、为什么要进行reset?

2、对于float、postion的理解

3、对于flex伸缩盒的掌握

4、对于不常用的table布局有没有掌握

5、对于兼容性不好的grid新型布局是有所了解,我觉得这是一个加分项

为什么要进行样式reset?

各个浏览器的默认展示样式不一致,CSS reset的作用是让各个浏览器的CSS样式有一个统一的基准。
例如暴力的

* {
    margin: 0;
    padding: 0;
}

后来我们也出现了reset.css
Normalize.css比较官方的解决方式,当然我比较推荐Normalize.css。

那如何清除浮动?

一般我们会有两种解决方法:

  • 使用clear属性进行清除浮动;
  • 使父容器形成BFC。例如在父容器加上overflow: hidden属性是我们常用的操作;

什么是BFC?

BFC是Web页面的可视化CSS渲染的一部分,是块盒子的布局过程发生的区域,也是浮动元素与其他元素交互的区域,也就是说它是一个独立渲染的区域,它规定了内部的Block-level Box去如何进行布局,与外部无关。比如清除浮动,外边距塌陷等都是可以通过BFC来进行解决。
关于定义MDN说的比较清楚了。BFC链接

下列方式会创建块格式化上下文:

  • 根元素(<html>)
  • 浮动元素(元素的 float 不是 none)
  • 绝对定位元素(元素的 position 为 absolute 或 fixed)
  • 行内块元素(元素的 display 为 inline-block)
  • 表格单元格(元素的 display为 table-cell,HTML表格单元格默认为该值)
  • 表格标题(元素的 display 为 table-caption,HTML表格标题默认为该值)
  • 匿名表格单元格元素(元素的 display为 table、table-row、 table-row-group、table-header-group、table-footer-group(分别是HTML table、row、tbody、thead、tfoot的默认属性)或 inline-table)
  • overflow 值不为 visible 的块元素
  • display 值为 flow-root 的元素
  • contain 值为 layout、content或 paint 的元素
  • 弹性元素(display为 flex 或 inline-flex元素的直接子元素)
  • 网格元素(display为 grid 或 inline-grid 元素的直接子元素)
  • 多列容器(元素的 column-count 或 column-width 不为 auto,包括 column-count 为 1)

column-span 为 all 的元素始终会创建一个新的BFC,即使该元素没有包裹在一个多列容器中(标准变更,Chrome bug)。

position属性

position的面试点应该就是在absolute的理解吧,position的定位是相对于最近的非static定位祖先元素的便宜,强调一下是非static,而不是只有relative

  • static

该关键字指定元素使用正常的布局行为,即元素在文档常规流中当前的布局位置。此时 top, right, bottom, left 和 z-index 属性无效。

  • relative

该关键字下,元素先放置在未添加定位时的位置,再在不改变页面布局的前提下调整元素位置(因此会在此元素未添加定位时所在位置留下空白)。position:relative 对 table-*-group, table-row, table-column, table-cell, table-caption 元素无效。

  • absolute

元素会被移出正常文档流,并不为元素预留空间,通过指定元素相对于最近的非 static 定位祖先元素的偏移,来确定元素位置。绝对定位的元素可以设置外边距(margins),且不会与其他边距合并。

  • fixed

元素会被移出正常文档流,并不为元素预留空间,而是通过指定元素相对于屏幕视口(viewport)的位置来指定元素位置。元素的位置在屏幕滚动时不会改变。打印时,元素会出现在的每页的固定位置。fixed 属性会创建新的层叠上下文。当元素祖先的 transform, perspective 或 filter 属性非 none 时,容器由视口改为该祖先。

  • sticky

元素根据正常文档流进行定位,然后相对它的最近滚动祖先(nearest scrolling ancestor)和 containing block (最近块级祖先 nearest block-level ancestor),包括table-related元素,基于top, right, bottom, 和 left的值进行偏移。偏移值不会影响任何其他元素的位置。

flex弹性盒前,我们说下什么是盒子模型?

盒子模型包括content、padding、border、margin这几块内容

  • W3C 标准盒模型:width和height只包含content,不包含padding和border。通过box-sizing: content-box来进行设置
  • IE盒子模型:width和height包含content+border+padding。box-sizing: border-box来设置,为了计算方便,似乎更倾向于这种设置方式
<div class="box">
    <style>
        .box div {
            width: 200px;
            margin: 10px auto;
        }
        .content-box {
            box-sizing: content-box;
            width: 100%;
            border: solid rgba(0, 0, 0, 0.2) 10px;
            padding: 5px;
        }
        .border-box {
            box-sizing: border-box;
            width: 100%;
            border: solid rgba(0, 0, 0, 0.3) 10px;
            padding: 5px;
        }
    </style>
    <h4>盒子模型</h4>
    <div class="border-box"></div>
    <div class="content-box"></div>
</div>

flex伸缩盒

伸缩盒可以让响应式设计,表单的对齐,固定布局等可以很简单的实现

用法:

{
    display:flex;
    flex-direction: row | row-reverse | column | column-reverse; 排列方向
    flex-wrap: nowrap | wrap | wrap-reverse;
    align-content: flex-start | flex-end | center | space-between | space-around | stretch; 多根轴线的对齐方式。如果项目只有一根轴线,该属性不起作用
    align-item: center; 垂直方向对齐方式
    justify-content: center; 水平方向对齐方式
}

想深入了解的同学可以看看
flex布局对性能的影响主要体现在哪方面?

以上是我个人理解这个题目的考察点,下面还有部分常问的CSS知识

如何计算CSS的优先级

浏览器通过优先级来判断哪些属性值与一个元素最为相关,从而在该元素上应用这些属性值。优先级是基于不同种类选择器组成的匹配规则。优先级就是分配给指定的 CSS 声明的一个权重,它由 匹配的选择器中的 每一种选择器类型的 数值 决定。

优先级规则

  • 最近的祖先样式比其他祖先样式优先级高
<div style="color: red">
    <div style="color: blue">
        <div class="son"></div> // blue
    </div>
</div>
  • "直接样式"比"祖先样式"优先级高
<div style="color: red">
    <div class="son" style="color: blue"></div> // blue
</div>
  • 优先级关系:内联样式 > ID 选择器 > 类选择器 = 属性选择器 = 伪类选择器 > 标签选择器 = 伪元素选择器
<div class="content-class" id="content-id" style="color: black"></div> // black

#content-id {
    color: red;
}
.content-class {
    color: blue;
}
div {
    color: grey;
}
  • 内联样式表的权值最高 1000;ID 选择器的权值为 100; class 类选择器的权值为 10;html 标签选择器的权值为 1。这个只是个人理解
<div id="con-id">
    <span class="con-span"></span> // red 
</div>

// CSS
#con-id span {
    color: red; // 值为100 + 1
}
div .con-span {
    color: blue; // 值为 1 + 10
}

inline-block元素之间的间隙如何去除?

因为习惯于父子dom的编写会换行,而且换行符会占用一定的宽度,所以导致元素之间会有间隙
解决:
  • 父元素font-size设置为0;
  • 元素设置float浮动;
  • 使用注释将元素连接起来;
<div class="box parent">
    <div class="children"></div><!--
    --><div class="children"></div><!--
    --><div class="children"></div>
</div>

CSS三角形

三角形的原理是因为border并不是和我们盒模型一样是一个矩形,当设置一个div的border都是5px时,每条border都是一个梯形。
<div class="border"></div>
<style>
   .border{
       width:100px;  
       height: 100px;  
       border: 40px solid;  
       border-color: #ff0000 #0000ff #ff0000 #0000ff;
       margin: 0 auto;
   } 
</style>

当我们把height和width都设置为0

最终我们就可以设置一些border-color: transparent;达到这个效果

<div class="border"></div>
<style>
   .border{
       width: 0;  
       height: 0;  
       border: 40px solid transparent;
       border-bottom: 80px solid #ff0000;
   } 
</style>

最后,希望大家都能够找到自己满意的工作。关注我的公众号:前端30K,后续会持续更新。。。


Toby
3.9k 声望366 粉丝