# float和position 浮动和定位

当给元素的float属性赋值后,元素会脱离文档流,进行左右浮动,比如这里我们将其中一个<div>元素添加了float属性

<style>

  div {

    border: solid 1px red;

    width: 50px;

    height: 50px;

  }

  .float {

    float: left;

  }

</style>

<div>1</div>

<div class="float">2</div>

<div class="float">3</div>

<div style='background: red;'>4</div>

<div style='background: blue;'>5</div>

<div class="float">6</div>

可以看到当元素设置为float之后,它就脱离文档流,同时也不再占据原本的空间。

4和5并没有重合,之所以看4和5它们像重合了,是因为浮动元素会对相邻的元素造成影响,其中就包括了文字会尽可能围绕浮动元素。在 div4 上加上 clear: left; 就可以清除 float 带来的影响

如果给2设置上背景色且不透明,那么就看不到4的背景色red的样式了,相当于2脱离了文档流,浮动在4的上方了。

BFC模式

<!-- 开启了BFC模式之后,4就不会被2遮住了 -->
<div style='background: red;overflow:hidden'>4</div>

在这样的情况下,可以使用以下方法撑开父元素:

  • 父元素使用overflow: hidden(此时高度为auto);
  • 使父元素也成为浮动float元素;
  • 使用clear清除浮动。

除了 clear 清除浮动之外,这些方法为什么可以达到撑开父元素的效果呢,这是因为 BFC(Block Formatting Context,块格式化上下文)的特性。BFC 是 Web 页面的可视 CSS 渲染的一部分,是块盒子的布局过程发生的区域,也是浮动元素与其他元素交互的区域

可以查看 MDN 中的描述:“float CSS属性指定一个元素应沿其容器的左侧或右侧放置,允许文本和内联元素环绕它。该元素从网页的正常流动(文档流)中移除,尽管仍然保持部分的流动性。”可见,浮动元素的确会从文档流中删除,但它并不是完全彻底地移除。 而我们常说的“脱离”二字并没有官方的定义,因此你和你的面试官理解或许不一样。如果将脱离认为是不符合正常的文档流,那么它便是脱离的;如果将脱离认为是彻底从文档流中移除,那么它便是不会脱离的。

<style>
*{
	margin:0;
	padding:0
}
#container {
  padding-left: 200px; 
  padding-right: 150px;
}
#container .column {
  float: left;
}

#center {
  width: 100%;
  background:greenyellow;
  opacity: 0.3;
}


#left {
  width: 200px; 
  margin-left: -50%;
  opacity: 0.4;
  background: skyblue;
}


#footer {
  clear: both;
}

</style>
<div id="header">header</div>
<div id="container">
  <div id="center" class="column">1</div>
  <div id="left" class="column">2</div>
</div>
<div id="footer">footer</div>
1
2

#left元素的margin-left: -50%;样式会使其向左移动父级宽度的50%。但是,因为#center已经占据了整个容器的宽度,#left实际上会向左移动到#center的左侧,从而与#center重叠。

这里的关键是理解浮动元素如何与它们的容器和其他浮动元素交互。即使为#left设置了负的外边距,它仍然会尝试浮动到左侧,直到遇到#container的边界或另一个浮动元素。由于#center已经占据了整个容器的宽度,#left没有空间可以浮动到,因此会与#center重叠。

# sticky

元素根据正常文档流进行定位,然后相对它的最近滚动祖先(nearest scrolling ancestor)和 containing block(最近块级祖先 nearest block-level ancestor),包括 table-related 元素,基于 top、right、bottom 和 left 的值进行偏移。偏移值不会影响任何其他元素的位置。 该值总是创建一个新的层叠上下文(stacking context)。注意,一个 sticky 元素会“固定”在离它最近的一个拥有“滚动机制”的祖先上(当该祖先的 overflow 是 hidden、scroll、auto 或 overlay 时),即便这个祖先不是最近的真实可滚动祖先。这有效地抑制了任何“sticky”行为(详情见 Github issue on W3C CSSWG)。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Sticky Layout with Flexbox</title>
    <style>
		* {
		    box-sizing: border-box;
		    margin: 0;
		    padding: 0;
		}
		
		body, html {
		    height: 100%;
		    font-family: Arial, sans-serif;
		}
		
		.container {
		    display: flex;
		    flex-direction: column;
		    min-height: 100vh;
		}
		
		.header {
		    background-color: #333;
		    color: white;
		    padding: 1rem;
		    text-align: center;
		    position: sticky;
		    top: 0;
		    z-index: 1000; /* Ensure it stays above other content */
		}
		
		.content {
		    display: flex;
		    flex: 1;
		    overflow: hidden; /* Prevent scrolling within this container */
		}
		
		.sidebar {
		    background-color: #f4f4f4;
		    width: 200px;
		    padding: 1rem;
		    box-shadow: -2px 0 5px rgba(0,0,0,0.1);
		}
		
		.main {
		    flex: 1;
		    padding: 1rem;
		    overflow-y: auto; /* Enable vertical scrolling within the main content area */
		}
		
		.scrollable-content {
		    max-width: 800px;
		    margin: 0 auto;
		}
	</style>
</head>
<body>
    <div class="container">
        <header class="header">Header</header>
        <div class="content">
            <aside class="sidebar">Sidebar</aside>
            <main class="main">
                <div class="scrollable-content">
                    <p>Scroll down to see the sticky header effect.</p>
                    <!-- Add more content here to enable scrolling -->
                      <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. 
                    Nullam quisque arcus laborum, magnis dis parturient montes,
                    nascetur ridiculus mus. Proin nsapien te fugit,
                    sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
                    </p>
                    <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit.
                    Nullam quisque arcus laborum, magnis dis parturient montes,
                    nascetur ridiculus mus. Proin nsapien te fugit,
                      sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
                      </p>
                      <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit.
                      Nullam quisque arcus laborum, magnis dis parturient montes,
                      nascetur ridiculus mus. Proin nsapien te fugit,
                      sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
                      </p>
                      <p>Lorem ipsum dolor sit amet, consectetur adipiscing elit.
                      Nullam quisque arcus laborum, magnis dis parturient montes,
                      nascetur ridiculus mus. Proin nsapien te fugit,
                        sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.
                        </p>
                    <!-- Repeat the above paragraph multiple times to create enough content -->
                </div>
            </main>
        </div>
    </div>
</body>
</html>
最后更新: 12/11/2024, 12:15:29 PM