解决css高度塌陷及父子元素外边距重叠问题

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接: https://blog.csdn.net/qq_35165469/article/details/102579665

1、元素浮动导致高度塌陷问题:

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8" />
		<title></title>
		<style type="text/css">
			
			.box1{
				/*为box1设置一个边框*/
				border: 10px red solid;
				
			}
			
			.box2{
				width: 100px;
				height: 100px;
				background-color: blue;
				
				/*
				 * 在文档流中,父元素的高度默认是被子元素撑开的,
				 * 	也就是子元素多高,父元素就多高。
				 * 但是当为子元素设置浮动以后,子元素会完全脱离文档流,
				 * 	此时将会导致子元素无法撑起父元素的高度,导致父元素的高度塌陷。
				 * 	由于父元素的高度塌陷了,则父元素下的所有元素都会向上移动,这样将会导致页面布局混乱。
				 * 
				 * 所以在开发中一定要避免出现高度塌陷的问题,
				 * 	我们可以将父元素的高度写死,以避免塌陷的问题出现,
				 * 	但是一旦高度写死,父元素的高度将不能自动适应子元素的高度,所以这种方案是不推荐使用的。
				 */
				
				/*为子元素设置向左浮动*/
				float: left;
			}
			
			.box3{
				 height: 100px;
				 background-color: yellow;
			}
			
		</style>
	</head>
	<body>
		
		<div class="box1">
			<div class="box2"></div>
		</div>
		
		<div class="box3"></div>
		
	</body>
</html>

 如下是高度塌陷效果:

解决之后的缺陷图:

     

完美解决图:

解决高度塌陷的方法:

第一种方法:给父元素设置高度

    .box1{
        height:100px;
    }
    
    结论:这样子元素的扩展就被限制了,因为通常是父元素的高度是被子元素的内容所撑开的

第二种方法:父元素也设置浮动

    .box1{
        float:left;
    }
    
    结论:虽然父元素被撑开了,没有了高度塌陷,但是因为float之后,元素会脱离文档流,而脱离文档流的元素的宽高是由内容撑开的,导致父元素宽度丢失,而且下面的元素会往上顶上去,也会导致布局错乱。

第三种方法:父元素设置绝对定位

    .box1{
        position:absolute;
    }

第四种方法:父元素设置inline-block

    .box1{
        display:inline-block;
    }
    
    结论:虽然父元素被撑开了,但是根据行内块级元素的特性,导致父元素宽度丢失,而且父元素后面的元素会和父元素独占一行。

扩展知识1:
    根据W3C的标准,页面中的每一个元素都有一个隐藏的属性BFC(Block Formatting Context),该属性有一个可以打开或关闭的开关,默认是关闭状态。

    1、如果开启元素的BFC属性,元素将会具有以下特性:
        1)父元素的垂直外边距不会和子元素重叠;
        2)开启BFC的元素不会被浮动元素所覆盖;
        3)开启BFC的元素可以包含浮动的子元素。

    2、开启BFC属性的方法如下:
        1)设置元素浮动【float】
          注:这也就是【第二种方法】使用浮动的原因,在这里再扩展一个知识点:【在文档流中的块级元素是独占一行的,宽度默认的是100%,高度由内容撑开;内联元素不会独占一行,高度和宽度都是由内容所撑开的,如果脱离了文档流,那么块级元素的宽度就由内容所撑开了,内联元素就会变成块级元素了】。
        2)设置元素的绝对定位【position:absolute】
          同样的绝对定位也会脱离文档流,故和float同理
        3)设置元素为inline-block【display:inline-block】
          因为inline-block是一个行内块级元素,元素不会独占一行,并且可以设置宽高。
        4)设置元素为overflow(非static的值)
          建议使用overflow:hidden,因为hidden开启BFC的副作用是最小的。

第五种方法:设置父元素的overflow
    
    .box1{
        overflow:hidden;
    }

扩展知识2:
    因为IE6及以下版本浏览器并不支持BFC,所以这种方式并不能兼容IE6;但是IE6中有另外一个隐含属性叫做hasLayout,该属性的作用和BFC类似,因此可以通过开启hasLayout来解决浏览器兼容问题,比如:【zoom:1】就是一个副作用最小的开启hasLayout的方法:
zoom表示放大的意思,后边跟着一个数值,写几就将元素放大几倍;
zoom:1表示不放大元素,但是通过该样式可以开启hasLayout;
zoom这个样式,只在IE中支持,其他浏览器都不支持.

所以最完美的第五种方法是如下:

    .box1{
        overflow:hidden;
        zoom:1;
    }

第六种解决方法:给父元素最后面加一个空的子元素,并且为它设置清除浮动
html:
    <div class="box1">
		<div class="box2"></div>
		<div class="clear"></div>
	</div>
css:
    .clear{
        clear:both;
    }
    
    结论:该方法可以适应任何一个浏览器版本,但是美中不足的是添加了多余的代码。

扩展知识3:
    clear是用来清除其他元素浮动之后,对当前元素所产生的影响;清除浮动以后,当前元素会回到浮动元素之前所在的位置
    其可选值:none不清楚浮动
             left清除左侧浮动元素所造成的影响
             right清除右侧浮动元素所造成的影响
             both清除两边元素浮动所造成的影响

第七种解决方法:为了解决第六种方法的不足,我们可以使用伪类【after】去设置
html:
    <div class="box1 clearfix">
		<div class="box2"></div>
	</div>

css:
    .clearfix:after{
        display:block;
        content:'';
        clear:both;
    }
注:该after伪类,在浏览器IE6及以下不支持该伪类,这就需要我们再次开启IE6的hasLayout,如下代码:

    .clearfix{
        zoom:1;
    }



    

    

2、解决父子元素外边距重叠问题:

1)什么是父子元素外边距重叠问题?

扫描二维码关注公众号,回复: 7590853 查看本文章

      指的是:子元素和父元素相邻的垂直外边距发生重叠,子元素的外边距会传递给父元素。

<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title></title>
		<style type="text/css">
			
			.box1{
				width: 300px;
				height: 300px;
				background-color: #bfa;
			}
			.box2{
				width: 200px;
				height: 200px;
				background-color: yellow;
				
				/*
				 * 子元素和父元素相邻的垂直外边距会发生重叠,子元素的外边距会传递给父元素
				 * 使用空的table标签可以隔离父子元素的外边距,阻止外边距的重叠
				 */
				margin-top: 100px;
			}
			.box3{
				border: 10px red solid;
			}
			
			.box4{
				width: 100px;
				height: 100px;
				background-color: yellowgreen;
				float: left;
			}
		</style>
	</head>
	<body>
		<!--高度塌陷问题-->
		<div class="box3 clearfix">
			<div class="box4"></div>
		</div>
		<!--父子元素外边距重叠-->
		<div class="box1 clearfix">
			<div class="box2"></div>
		</div>
		
	</body>
</html>

2)外边距重叠效果

3)解决高度塌陷问题:

第一种方法:
直接使用空的table标签可以隔离父子元素的外边距,阻止外边距发生重叠

html:
    <div class="box1 clearfix">
        <!--该table标签用来阻止外边距发生重叠-->
		<table></table>
		<div class="box2"></div>
	</div>
结论:结构中增加了多余的代码

第二种方法:为了解决第一种方法的缺陷,故我们可以使用伪类

css:
    .clearfix:before{
        content:"";
        display:table;
    }

3、总结高度塌陷及父子元素外边距重叠问题:

因为两者问题中都使用了伪类,而且还都是设置了空元素,但经测试,clear:both并不影响父子外边距问题,而高度塌陷中的display:block原本目的就是让新增的空元素为块级元素,经CSS api文档中查看,display:table这一则属性值,同样也会成为块级元素,由上诉结论可整理如下完整解决方案:


.clearfix:before,.clearfix:after{
    content:"";
    display:table;
    clear:both;
}

/*解决IE6浏览器高度塌陷兼容问题*/
.clearfix{
    zoom:1;
}

 

猜你喜欢

转载自blog.csdn.net/qq_35165469/article/details/102579665