当前位置: 首页 > Web前端 > HTML5

css布局基础知识总结

时间:2023-04-06 00:22:13 HTML5

前端css布局知识复杂,实现方法五花八门。要想写出高效合理的布局,必须要有扎实的CSS基础。为了方便记忆和复习,将CSS布局的要点记录如下。内容很多,应用不是很详细,但都是很实用的点。所谓布局,就是把元素设置成我们想要的大小,放在我们想要的位置上。位置和尺寸是核心的两个要素。这些元素其实就是一些方块,页面就是由各种方块组成的。现在主要有三种布局方式:传统的CSS布局方案(position、float、line-height等)。实现复杂,需要多个属性一起使用,兼容性最好。弹性布局方案。布局灵活,易于实施,兼容性好。网格布局方案。使用哪种布局方式取决于项目的具体要求。如果不需要兼容IE,推荐使用flex或者grid。这两个是未来的趋势。如果要考虑兼容性,最好使用传统的css布局方案。传统的css布局方案css标准盒模型前面说了,一个html元素就是一个盒子,再仔细一点,就是盒模型。盒子模型是这样的:我们可以在chrome开发者工具的styles中查看:css盒子模型,分为4部分:content:显示元素内容区域,包括子元素padding:内容区域到的距离border,又称内边距border:显示自己的外边距margin:用来设置元素本身与同级元素或父元素之间的距离。所有的html元素都是按照一定的规则排列和渲染的。在HTML中,不仅有一种规则,而且有多种规则。了解这些渲染规则以及这些规则生效的条件,对我们理解css有很大的帮助。文档流文档流可以理解为所有元素的默认渲染规则。它的规则很简单:元素按照各自类型的布局特点从左到右,从上到下排列。元素在布局上分为三种:块级元素:默认占据一整行,即使设置了宽度,仍然占据一整行,辅以margin(霸道总裁)、block、table、flex、grid,list-item内联元素:宽度被内容扩展,只占自己的位置。即使设置了宽度,它也不起作用。边距也适用于左右,但不适用于上下(每位女士)。inline内联块级元素有:width由内容打开,它只占据自己的位置,可以设置自己的宽度(两人的孩子?),有inline-block,inline-table,inline-flex,和内联元素上方的内联网格。其实是不对的,这里要特别说一下,内联元素分为两种:可替换内联元素:该元素显示的内容不在css范围内,典型的如img、video、object、input、textarea等,显示内容由src、value等决定,这个元素可以设置宽高。不可替换的内联元素:普通的内联元素,比如span、a、i、em等,可以通过两种方式脱离文档流,绝对定位和浮动,我们下面详细说说。BFCBFC的全称是BlockFormattingContext,块级格式化上下文。BFC环境中的元素按照以下规则进行渲染:和文档流一样,元素按照自身类型的布局特点从左到右,从上到下依次排列。BFC是一个独立的、封闭的渲染区域。子元素的样式对BFC的外部有影响。BFC可以识别浮动子元素。BFC可以识别浮动的兄弟元素。使用它来制作灵活的布局。那么BFC是什么样的渲染区域呢?一个BFC的渲染区域可以通过以下方式显示和声明:根元素或包含根元素的元素的值不是noneposition是absolute的或者fixedoverflow的值不是visibledisplay是inline-block,table-cell,table-captionsizeelement的大小有两种情况:默认情况:块级元素默认宽度为100%,高度被内容展开;内联元素和内联块级元素的宽度和高度默认按内容扩展。DeveloperSettings:主动设置width,height,line-height等。先搞清楚元素的尺寸概念。我们都知道元素的盒子模型。元素由四个区域组成:内容、填充、边框和边距。那么大小到底是什么意思呢?我们可以将大小分为三类:元素大小:由内容、填充和边框组成。在原生DOMAPI中,使用offsetWidth和offsetHeight获取元素的内部尺寸:由content和padding组成。在原生DOMAPI中,使用clientWidth和clientHeight获取元素的外部尺寸:由content、padding、border和margin组成。没有对应的DOMAPI,但是理解这个对布局很有帮助。我们在css中设置的宽度和高度代表哪部分区域是模糊的。我们可以通过设置box-sizing来切换width和height所代表的区域。box-sizingbox-sizing,可以切换宽高表示的区域。box-sizing主流浏览器有两个值:content-box:width和height设置内容的宽度和高度border-box:width和height设置内容的宽度和高度,padding,border结合这两个属性导致歧义width和height,很多情况下是全局设置的,非常隐蔽,新手容易混淆。这两个属性的产生有一定的历史原因。最初的盒子模型默认使用border-box,早期的IE就是这样,也称为IE盒子模型。后来W3C觉得content-box更好,把盒子模型改成了默认的content-box模式。后来随着灵活布局的流行,border-box的优势越来越明显。大家更愿意用border-box来布局,W3C也想找回border-box。但是,现在已经有很多基于内容框的网站,不能为了兼容而随便改动。所以W3C想出了box-sizing的方法,支持border-box,但默认还是content-box。使用box-sizing需要注意的地方:全局添加box-sizing:border-box,注意第三方组件库的侵入,因为第三方组件很可能是基于content-box布局,设置所有元素的box-sizing属性是inherit:*,*:before,*:after{box-sizing:inherit;}这样我们就可以设置父元素的box-sizing,控制所有元素的box-sizing属性子元素。对于我们封装的Components来说,搭建整个组件环境是非常方便的,只要我们在封装组件的时候强行设置box-sizing,就不怕全局样式入侵了。content-box模式可以使用calc属性辅助设置弹性布局,或者设置两层div的大小百分比来设置包含块。我们知道宽高可以用百分比来设置,那么这个百分比的参考对象是谁呢?这里有一个概念叫做包含块(CB,ContainingBlock)。元素的包含块是元素的宽高百分比的引用对象。很多新手同学在设置宽高百分比的时候有时会觉得莫名其妙,各种奇怪的现象怎么设置都不行。其实并没有包含块的概念。谁是一个元素的包含块主要取决于该元素的position属性,总结如下:对于position为static和relative的元素,包含块是父元素的content-box位置为absolute的元素,而thecontainingblock是它最近的位置非静态祖先元素的padding-box,如果非静态祖先元素没有定位,它是初始包含块(后面解释)位置固定的元素,包含块是当视口位置是绝对且固定时的视口,包含块也可能是满足以下条件的最近父元素的填充框:除none之外的变换或透视值变换或透视的will-change值过滤器valueotherthannoneorawill-changevalueoffilter(onlyworksonFirefox)这一项比较特殊,遇到的情况比较少。除了width和height相对于包含块的百分比之外,margin和padding的百分比也是相对于包含块设置的,只不过margin和padding的百分比是相对于包含块的。宽度设置(在水平模式下)。绝对定位的偏移属性top、left、right、bottom也是相对于包含块设置的,后面会详细介绍。初始包含块元素的包含块是自己的祖先元素,那么hmtl元素没有祖先元素,其百分比设置是相对的?是初始包含块,根元素(hmtl)所在的包含块是一个矩形,称为初始包含块。这个矩形的大小就是浏览器视口的大小。需要注意的一件事是那些不以非静态祖先元素为目标的引用是初始包含块,而不是html元素。Margin因为margin在布局中有一些重要的特点和特殊情况,所以我们单独说一下。margin:auto我们知道,即使设置了块级元素的宽度,它也会占据一整行。为什么会这样?谁占据了剩余的空间?这里要明确一点,一个块级元素占一行,也就是说块级元素的外部尺寸占一行,也就是margin-box。当margin设置为auto时,margin将自动填充剩余空间。margin-left:默认为0,当为auto时,会自动填充剩余空间margin-right:默认为0,当为auto时,会自动填充剩余空间margin-top:默认为0,当为auto时,该值仍为0margin-bottom:默认为0。当为auto时,该值仍为0。当margin-left和margin-right同时为auto时,剩余空间将平分。这就是margin:auto将元素水平居中的原因。那么margin:auto不能让元素垂直居中,因为在垂直方向上,块级元素不会自动展开,它的外部尺寸不会自动填满父元素,没有剩余空间可言。如果我们在父元素上设置writing-mode:vertical-lr,那么margin:auto会使子元素垂直居中,但是水平居中无效。有什么方法可以使用margin:auto使元素水平和垂直居中?答案是肯定的,就是在绝对定位的情况下。.father{宽度:300px;高度:150px;位置:相对;}.son{位置:绝对;顶部:0;右:0;底部:0;左:0;宽度:200px;高度:200px;;}这时候son的外部尺寸会自动填满它的包含块,效果和块级元素差不多。这时候如果给.son元素设置宽高,就会有剩余空间,margin:auto会自动平分剩余空间,让.son水平和垂直居中。Margin对元素的布局有两个影响:影响内部尺寸,影响外部尺寸,影响元素内部尺寸,块级元素,是一种布局特性,会自动填充宽度方向的空间,当没有设置宽度,设置margin-left和margin-right来影响元素的内部空间。当margin为正值时,元素尺寸减小;当边距为负值时,元素大小增加。因为元素的外部尺寸已经确定,就是它的包含块的尺寸,外部尺寸等于元素尺寸加上边距。如果边距为负,元素大小自然会增加。利用内部尺寸增加而外部尺寸不变的特性,我们可以对等距列表进行布局。比如我们实现一个一行三列的布局,两边没有空隙,中间有20px的空隙:.father{margin-right:-20px;}.son{width:calc(calc(100%-20px*3)/3);margin-right:20px;}影响元素的外部尺寸当元素的宽高固定时,相当于元素固定尺寸,margin开始影响元素的外部尺寸。正边距会增加元素的外部尺寸,负边距会缩小元素的外部尺寸。这很容易理解,我就不说了。主要讲负值。这时候margin-top、margin-left、margin-right、margin-bottom的表现看似不同,其实本质是一样的。当margin-top和margin-left为负值时,表示元素向上或向左移动;当margin-right和margin-bottom为负值时,表示右边或下面的元素将相应地向左或向上移动。仔细想想,这是元素外部尺寸缩小的一种表现。margin-top和margin-left使得左边上边和上边的尺寸缩小,自然会向左或向上移动。margin-right和margin-bottom缩小了右边和底边的尺寸,旁边和下面的元素自然会占据左边或上面的空间。margin在某些情况下合并块级元素的顶部和底部边距。需要注意的是,浮动元素和绝对定位元素不会合并,合并只会发生在垂直方向。有以下3种合并场景。当相邻兄弟元素的父元素和第一个/最后一个元素为空时,高度为0,用户的上下外边距将合并。保证金合并的计算规则有正负之分。添加negativeparent和取small(-20px,-50pxmergeandtake-50px)防止marginmerge把合并后的元素变成BFC,比如设置display:inline-block,overflow:hidden,float:left和其他父子合并/空元素合并时,给父元素/空元素设置border和padding可以防止合并内联元素的大小。主要想说两个属性,line-height和vertical-align。这两个属性对高度有重要的影响,如果不了解这两个属性的作用,往往会遇到一些比较奇怪的布局问题,不好解决。ghostblanknode这个名字是张新旭定义的,在W3C规范中也可以找到。一书中,为了证明ghostblank节点的存在,举了一个例子:div{background-color:#cd0000;}span{display:inline-block;}

你可能已经猜到了div的高度不是0,我在chrome下试了21px的高度。这个高度猜测应该和div的字体、字号、行高有关。这个ghostblank节点的存在会造成一些奇怪的现象,比如:
div的高度总是比img高,img下面总是有空隙。这也是一个幽灵空白节点在起作用。line-heightline-height转换为行高。它指的是线框的高度。那么什么是线框呢?行框是一行内联或内联块元素。通过实验,我发现一条线构成行框的前提有两个:要么有文本内容,要么有行内块级元素。如果有一堆空的内联元素,比如span,它们是不会组成linebox的。line-height是指定linebox所占的高度。line-height仅在形成linebox时才有效。这里可能会有一些误解的情况,比如:.father{line-height:300px;}你好
这个时候。fahter的高度是300px。这里要注意,作用于.son的不是line-height,而是.son内部形成了一个lineframe,line-height作用于这个linebox。.son的高度是300px。打开.父亲。vertical-alignvertical-align用于设置内联元素或内联块级元素在行框中的对齐方式或垂直位置。verticle-align有四种取值方式。这里直接说对布局比较重要的两种类型:线型:baseline(默认值),top,middle,bottom值型:比如20px,20embaseline我们先看一张图:vertical-align默认是基线对齐,基线的位置很重要。并且基线定义为:字母x的下边缘。中线的位置是基线上方1/2x高度,也就是x交叉的地方。这里需要注意的一点是,纯文本的中心线是x交叉的地方,但是内联元素的中心线恰好是内联元素的中间。让我们看一个例子:div{line-height:100px;background:yellow;
xhello
效果如下:一切正常,div高度为100px,文字也近似垂直居中。但是如果我们在.world元素中加上vertical-align:middle,就会发现文字向下偏移了,div的高度变成了102px。结盟?答案是幽灵空白节点。幽灵空白节点是一个很神奇的存在,看不见摸不着,但它确实起作用。它的作用相当于一个x字符的作用,用于提供对齐基准。正如我们上面提到的,在div元素中有一个图片的例子。img是一个可替换的内联元素,它的基线是它的底部。默认是基线对齐,所以图片是对齐鬼空白节点x的基线,x基线位置下面有一个空白,就是这个空白的来源。为了更直观,我们在上面的例子中在span元素前面加了一个x字符,作为ghost空白节点,看看效果:原来xhello中的x和x是对齐的。设置vertical-align后,我们可以看到xhello字符向下移动了某个位置。这是因为span元素的垂直中线位置高于xhello中的x交点。现在要与之前的x交点对齐,转到下移。又因为x和xhello的行高都是100px,现在因为错位,整体高度多了2px。垂直居中应用程序使用line-height和vertical-align在各种场景下设置垂直居中。单行居中div{line-height:anyvalue}
helloworld
父元素固定垂直居中。在.box上设置line-height实际上是将ghostblank节点的行高设置为120px,然后通过.content与ghostblank节点中间对齐实现垂直居中。.box{行高:120px;背景色:#f0f3f9;}.content{显示:内联块;行高:20px;边距:020px;vertical-align:middle;Multi-linetext...
父元素垂直居中,高度固定。原理其实和父元素固定高度是一样的,但是因为高度不固定,所以不能设置父元素的line-height,这时候我们可以设置一个父元素的伪元素,设置高度为100%,vertical:middle,因为元素是从左上到下排列的,所以vertical:middle会将ghostblank节点的x拉到父元素的垂直中心。这时候我们可以设置子元素的vertical-align:middle来达到目的。.container{位置:固定;顶部:0;右:0;底部:0;左:0;背景色:rgba(0,0,0,.5);}.container:after{content:'';显示:内联块;高度:100%;vertical-align:middle;}.dialog{display:inline-block;vertical-align:middle;position元素的位置由position属性和float属性决定。position属性position有4个值:static:默认值,按照css规则排列relative:相对定位,可以设置offset,top,left,right,bottom,offset百分比大小的参考是它的包含块,有偏差的displacement的position引用对象是自己的positionabsolute:绝对定位,offset可以设置,top,left,right,bottom,偏移百分比,size和position的引用对象是它的containingblockfixed:固定定位,offset可以设置offset,top,left,right,bottom,offsetpercentagesizeandposition引用对象是包含块视口需要注意的:当position是relative,absolute,fixed时,如果没有设置offset,默认position是一个元素其位置是绝对的,固定在文档流的正常位置。当它脱离文档流时,文档流中的元素不识别该元素,不识别其位置为absolute和fiexed的occupation、width和height(不是它自己的children)元素。宽度渲染规则与内联块级元素相同。默认情况下,宽度由内容扩展。您可以设置宽度和高度浮动属性。浮动属性可以使元素脱离文档流向左或向右移动,直到它触及包含块的填充或命中另一个浮动元素。注意:如果position是absolute或者fixed,floating属性会失效。float会使元素块状,display的值,inline-table会变成table,其余的会变成blcok,但是元素宽度和inlineblocklevel的渲染规则元素是一样的,宽度被内容扩大默认情况下,可以设置宽度和高度。Float以其高度崩溃而闻名。高度塌陷的原因与浮标设计的初衷有关。float属性最初是为了实现文字环绕效果而设计的。

我是文字,我想把你包围

.img-wrap因为高度塌陷,实际上不识别float元素,高度为0,p元素与之重合,从而达到文字环绕效果。高度折叠的特性在实现布局的时候是不合理的,但是现在很少有文字环绕的场景,基本都是float来布局。现在这实际上已经成为一个“错误”。所以css提供了另一个清除浮动的属性:clearfix。mdn上的clearfixclearfix是指定一个元素是可以在它之前的浮动元素旁边(我觉得这里用巧合更合适),还是必须向下移动(clearfloating)到它下面。注意上面这句话,指定一个元素表示clearfix的目标是元素本身,前面的浮动元素表示clearfix的条件是前面有一个浮动元素,效果clearfix的作用是让元素换行显示。所以clearfix的作用是,如果元素前面有浮动元素,可以指定元素换行显示,或者识别前面的浮动元素。clearfix有3个值:left:clearleftfloatingright:clearrightfloatingboth:clearleftandrightfloating一般使用clearfix:both。清除浮动的一个重要应用是解决浮动高度崩溃的问题。一个通用的解决方案是设置.clearfix类:.clearfix{display:block;缩放:1;&:之后{内容:“”;显示:块;字体大小:0;高度:0;明确:两者;可见性:隐藏;}}只需在包含浮动元素的父元素上设置此类。博客地址参考张新旭《CSS世界》https://mp.weixin.qq.com/s/8e...