建站学习网,专业提供各类建站教程,网页素材,SEO资讯等建站资源!

网站模板_网站源码_网站素材_建站教程_建站学习网

当前位置:建站学习网 > 网页设计 > 交互设计教程 >

深入理解CSS盒子模型

更新时间:2017-04-10整理编辑:建站学习网阅读:0

深入理解CSS盒子模型

前言:前阵子在做一个项目时,在页面布局方面遇到了一点小问题,于是上stackoverflow上求助。ifaou在帮助我解决我问题的同时,还推荐我阅读一篇有关CSS盒子模型的文章《The CSS Box Model》,阅读之后受益匪浅,才知道自己对盒子模型知识还是如此欠缺。恰逢学期末,项目验收后暂时告一段落,有空闲的时间。于是想把这篇文章翻译出来,一方面再给自己一点挑战和锻炼,另一方面也给大家参考,让更多的人受益。

这篇文章适合初级web设计朋友,让你对盒子模型有更近一步的理解。但是在阅读这篇文章之前你应该对盒子模型html等基础知识是有一定的了解,否则只会让你更加云里雾里。这篇文章不会像很多的中文教程那样,把盒子模型内边距,外边距,如何定位等概念有条不紊的介绍一遍。这篇文章更多的是教你在实战过程中如何自如的控制盒子的宽度,如何用最恰当的方法定位盒子,如何解决IE中盒子的种种bug。

之所以翻译这篇外国文章,是因为我在学习的过程中也发现,国外的教程和过内的相比,它们授人以渔,更授人以鱼 。不同于国内教程有章有节有点有条目,他们的叙述方式更接近谈话式的由浅入深……总而言之,目的在于给更多的初学者提供一点启示和帮助,不必像我一样走了许多弯路。

这是我第一次翻译,有欠缺的地方请大家指正。我尽量把它翻译的通俗易懂,同时也加入了一些自己的语言自己的体会,和帮助理解的图示(为了阅读流畅,也就不另表示了)。附上原文地址:http://reference.sitepoint.com/css/boxmodel

深入理解CSS盒子模型(The CSS Box Model)

如果你了解盒子模型(box model)的概念,了解它是如何决定某一个元素的最终尺寸的话,会有助你理解一个元素如何在网页上定位的。盒子模型主要适用于块级元素。顺便提一个与此相关的概念:行内布局模型(inline layout model)——定义了行内元素是如何定位的,在行内元素格式(InlineFormatting)中有具体说明

盒子的尺寸的计算(Calculating BoxDimensions)

在CSS2.1中,块级元素只能是矩形形状的。当我们需要计算一个块级元素的整体尺寸时,需要同时把内容区域(content area)[注释1]的长宽,连同此元素的外边距,内边距,以及边框都计算在内

[注释1]:此文章中频繁提到content 和content area这两个概念,虽然从字面上都可以理解为盒子中的内容区域(content),但从后文的叙述来看,这两个概念还是有区别的,到这篇文章发布为止,我还是对这两者的区别有迷惑,希望有兴趣阅读原文的朋友能留言告诉我这两者的区别,以便于我更正文中的错误。

我们可以通过声明宽和高来定义一个元素的内容(content)的宽度和高度。如果没有做任何的声明,宽度和高度的默认值将是自动(auto)

w3schools上对于盒子模型的图示如下

在图的下方有一段很重要的话Important: When you specifythe width and height properties of an element with CSS, you are just settingthe width and height of the content area.也就是说当我们在css中设计一个块级元素的width和height属性时比如.box{width :100px; height:100px}时,其中的width 和height仅仅是对content部分设置的,即定义上图中padding下虚线方框内区域的长和宽。而不是内容,内边距,边框的总和(但在IE的早期版本包括IE6中,盒子模型的width和height却恰恰是这样定义的,尽管符合人们思考的逻辑,但是不符合规范,这会造成严重的问题)

对宽度为自动状态的静态(static)定位元素(即无定位),和相对定位(relatively positioned)元素来说,计算宽度的方法是,将他们包含块(containing block)[注释2]的宽度减去此元素的横向的所有外边距,内边距,边框,滚动条。也就是说,从包含块的宽度中除去元素的横向外边距,内边距,边框,滚动条(如果存在的话)的宽度,所剩的值就是了。

[注释2]:包含块(containing block)。如果你知道绝对定位和相对定位的实现原理的话,这个注释可以忽略。包含块可以理解为一个矩形,而这个矩形的作用是为它里面包含的元素提供一个参考,内部元素的尺寸和位置的计算往往是由该元素所在的包含块决定的。例如在绝对定位中,距离它最近的已定位(position为fixed,relative或absolute)的祖先元素即为包含块。这算比较初级的概念,不深究,请百度。

包含块的定位属性和尺寸被作为后代元素定位和尺寸计算的参考。尽管元素的定位必须遵从与他们的块级元素来进行定位,但是他们也非受限于它。后代的元素也可以溢出包含块。在大多数情况下, generated boxes[注释3]通常扮演着子代元素包含块的角色。想要充分了解包含块的大量细节信息请点击ContainingBlock

[注释3] :不知道generated boxes应该如何翻译,有知道的朋友请告知,谢谢

对于浮动(floated)和绝对定位(absolutelypositioned)元素(包括固定定位(fixed)元素)来说, 自动状态的宽度会使generated box收缩到紧贴它内容大小。

我觉得我在这里有必要总结一下前两段话的意思,前两段话都是在说在宽度缺省的情况下(auto),盒子模型自动设置宽度的两种方式。

我们知道,当我们放置一个块级元素于页面上时,并且不设置它的定位属性(relative,absolute,fixed),即position:static,或者设置了position:relative的情况下,块的宽度是延伸自动填充满它的父元素的宽度区域

举个例子:

 

以下为引用的内容:

.box1

{

background:black;

color:White;

height:100px;

padding:10px;

border:20px solid Red;

margin:30px;

}

 

注意.box1没有设置任何的position属性,也没有宽度属性。这是为了实验相对定位或者无定位的情况

Html代码:

 

以下为引用的内容:

<h2>Static or Relative Box</h2>

<div class="box1">For floated or absolutely positioned </div>

 

结果为:

即块的宽度是延伸自动填充满它的父元素的宽度区域。

所以当我们在计算一个被包裹中的元素的宽度时,我们只需要用父元素减去这个元素的外边距,边框,内边距,和scrollbar,剩下就是它的宽度,因为它会自动填充。虽然这个基本上没有实际应用可言……

但是浮动floated元素和绝对定位元素,他们的结果却恰恰相反,他们会收缩以致包裹紧贴内容,同样举个例子

 

以下为引用的内容:

.box2

{

background:black;

color:White;

height:100px;

padding:10px;

border:20px solid Red;

margin:30px;

position:absolute;

}

 

 

 

这里同样没有设置宽度,但是进行了绝对定位,html代码:

 

以下为引用的内容:

<h2>Absolute or Float</h2>   

<div class="box2">For floated or absolutely positioned </div>

 

结果:

浮动元素和宽度

之前,在CSS2中,没有声明宽度的浮动元素,不会收缩并于紧贴(shrink to wrap)住他们的内容,恰恰相反的是,他们会不断的延伸至与他们父元素最大宽度相当。这种行为在CSS2.1中被收缩紧贴代替了。但是无论如何,在IE6和更早的浏览器版本中,一个没有声明宽度的浮动元素还是会收缩紧贴住它的内容作为一种默认的设置,除非子元素有自己的布局(has a layout)[注释3],比如说在这种情况下,父元素会伸展来适应父元素中的可用内容的宽度

[注释3]:“IE的表现与其它浏览器不同的原因之一是,显示引擎使用了一个称为布局的内部概念……windows上的IE使用布局概念来控制元素的尺寸和定位。那些“拥有布局“的元素负责本身及其子元素的尺寸设置和定位。如果一个元素“没有拥有布局“,那么它的尺寸和位置由最近的拥有布局的祖先元素控制……布局是许多IE显示bug的根源“——摘自Andy Budd、Simon Collision、Cameron Moll的《CSS Mastery Advanced WebStandards Solutions(Second Edition)》(精通CSS 高级Web标准解决方案 第二版)

正如以上所说,对于没有声明宽度的浮动元素,在IE6和之前的版本都是采取收缩紧贴内容的行为,所以这种说法无从考证了,我也在IETest下测试过,的确如此

同样应该被注意的是,当一个浮动元素(没有声明宽度)包含一个向右浮动的子元素时,它同样也会自动的延伸填充,以适应父元素的可用内容的宽度。这种情况在之前的IE浏览器,包括IE7中都是存在的(之前的Firefox,包括2.0版本中也存在这个bug,但是这个问题在Firefox3.0 Alpha 6版本中已经得到了解决)。

我也为以上这段话写了个例子给大家:

 

以下为引用的内容:

<div class="parent">      

<div class="containing-block">  
         
<div class="box">For floated or absolutely positioned </div>  
      
</div>            

</div>

 

对照一面那段话:首先是一个浮动元素containing-block,包含一个向右浮动的子元素box,父元素为parent……

 

以下为引用的内容:

.box

{

background:black;

color:White;

height:100px;

padding:10px;

border:20px solid Red;

margin:30px;

float:right;

}

.containing-block

{

background:blue;

height:250px;

float:right;

}

.parent

{

background:gray;

height:300px;

width:500px;

}

 

在Firefox中运行结果为:

  

但是在IETester中用IE5.5运行的效果是:

所以,为了避免上面提及的bug,如果可能的话,尽量为一个浮动元素指定一个具体的宽度值,总是会比较安全一点的。无论如何,只要你总是有留意到以上提及的问题,你或许会发现无宽度的浮动在一些场合下还是非常管用的,比如横向流式(fluid-width)布局菜单

无论内容区域如何定位,如果高度,最小高度(min-height),最大高度(max-height等没有被声明的话,内容区域高度与内容的高度是相等的[注释4]。

[注释4]:这里就是让我对content area和content产生疑惑的地方,不知道有没有朋友能帮我看看,帮我解释一下

所以,当你为了弄清把一个元素放在页面上究竟需要多大尺寸时,把已经声明内边距,边框,外边距值统统与内容区域加上。当然,如果一个元素没有内边距,边框,外边距的话,也就是它的尺寸仅仅是由它的内容来决定

如果一个元素仅仅包含浮动或者绝对定位的元素,它没有一丁点的内容,那么它的高度将为0。我们将在Floating and Clearing做更多讨论

实现盒子模型

说明盒子模型的最好方式是用一个简短的例子。我们用计算来看看在页面上放置一个元素总到底需要多大的尺寸(这里先忽略外边距的叠加效果——以下会有更详细有关这个的说明):

Total width = left margin + left border + left padding + width +

right padding + right border + right margin

Total height = top margin + top border + top padding + height +

bottom padding + bottom border + bottom margin

这里是我们的CSS样例——为了一个类名为’box’的元素声明盒子的各个属性:

 

以下为引用的内容:

.box {

width: 300px;

height: 200px;

padding: 10px;

border: 1px solid #000;

margin: 15px;

}

 

以上的元素总共被计算出来的的尺寸是:

Total width = 15 + 1 + 10 + 300 + 10 + 1 + 15 = 352px

Total height = 15 + 1 + 10 + 200 + 10 + 1 + 15 = 252px

以上的计算在图1中给出了具体描述,这是从Firebug元素布局展示中截下的图,

在图1中,我们可以很清晰的看到内容区域处于中央,围绕着内容区域的内边距区域,边框区域,外边距区域。内容区域的外边缘称为内容边缘(content edge),或者是内边缘(inner edge);内边距区域的外边缘被称为外边距边缘(padding edge);边框区域的外边缘被称为边框边缘(border edge);外边距区域的外边缘被称为——你应该可以猜到了——外边距边缘(margin edge)或外边缘(outer edge)

你可以从这个简短的例子中看到,为了使这个元素适应这个页面,我们需要一个至少352px 宽度和252px高度的区域。如果可用的区域小于这个,这个元素会错位,或者溢出它的包含块。注意到IE6或者更早的浏览器版本中,在这种情况下会伸展包含块的以容纳内容区域的多余高度,这很明显会扰乱网页的布局。但其它版本的浏览器会使元素溢出它的边界,同时忽略内容。

这个Bug翻译过来是:“如果元素的内容比元素本身大,那么我们希望内容溢出到元素外。但是,在IE6和更低版本中,拥有布局的元素会错误的拓展以便适应内容的尺寸……这种错误意味着Window上的IE中的width实际上更像是min-width“——Andy Budd、Simon Collision、Cameron Moll的《CSS Mastery Advanced Web Standards Solutions(Second Edition)》(精通CSS 高级Web标准解决方案第二版),给大家演示一下,很简单的:

 

以下为引用的内容:

<div class="IEbug">  
 
<p>Your understanding of the box model concept, and how it relates to the way in which an element,  final dimensions are determined, </p>

</div>

 

 

.IEbug

{

background:yellow;

width:100px;

height:100px;

}

 

火狐下测试结果:

IE6下测试结果:

留意外边距叠加效应

尽管在上面的计算元素所需区域大小的例子中外边距已经在计算中包括在内了,但是需要注意的是纵向的无定位(static)元素的相邻外边距会叠加合成为其中一个较大宽度的外外边距的值,并非两者之和。这就意味当计算实际上需要存放一个元素的区域大小时,并不是从外边距的边缘开始算起,只有最宽的外边距会生效,并且较窄的外边距会与较大的叠加在一起,请阅读CollapsingMargins来了解更多有关这相当复杂的一个主题。

实际盒子模型应用

非常值得注意的一点是,当一个元素的宽度被设置为100%时(也就是说父元素的内容宽度是100%),它不应该有任何的外边距,内边距,或者是边框,这只会使它放置的区域需要更大的面积。这通常会被设计师们所忽略忽略并且很严重的扰乱了页面的布局,这样的话内容要么溢出要么使元素比他们应该的样式更宽

 

以下为引用的内容:

<div class="contain">
 
<div class="box"></div>    
  
</div>

 

没有margin和padding,仅有width情况下的CSS:

 

以下为引用的内容:

.box

{

background:black;

width:100%;

height:100px;

}

.contain

{

background:yellow;

height:120px;

width:200px;

}

 

效果如图所示:

可见在没有margin和padding的情况下,100%的内容能恰到好处的填充父元素

一旦加入了margin和padding(margin:10px;padding:10px;)之后效果如图:

在firebug中的布局图:

而加入了margin和padding之后,元素出现了错位,并且只能显示左侧的margin

解决办法是,在大多数情况下,避免给宽属性添加具体的值(绝不是自动),并且只应用外边距,内边距,边框。无定位元素的宽度将会默认为自动。甚至就算定义了内边距,边框,外边距,它仍然会认为可用的内容宽度为全满状态。

当然,这种方法对某些例子可能失效,比如当元素不是无定位元素时,并且它的确需要一个指定的宽度(就像那个浮动元素不会自动填充它父元素的例子一样)。在这些情况下,你有两个选择。

如果可用区域是固定宽度的,你能简单的把每一个属性元素(margin,padding等)的宽度都相加起来以匹配可用的那个固定宽度。举个例子,如果可用的区域宽度是500px,并且你需要一个元素有20px的内边距,简单的把这个元素的宽度设置为460px,内边距为20px(20+460+20=500)。这个办法中先决条件是宽度值和元素盒子属性使用的都是同一测量单位,因为你不希望把混合单位相加起来(200px + 10%,只是举个例子而已,在内容中这样的写法是没有意义的)。

当可用内容区域的宽度是未知的时候——比如在流式布局(fluid layout)中——这个方法是行不通的,因为百分比(percentages)和像素(pixels)不能一起相加。在这种情况下,解决方法应该是为需要的元素声明一个100%的宽度值,并且把内边距,边框,外边距的值都设置到一个嵌套其中的元素中去。这个嵌套元素没有任何的宽度值声明,并且可以在没有干扰父元素的情况下展示需要的内边距,边框,外边距。[注释5]

[注释5]呃,其实这段话我也没有理解……

现在你应该能清晰的理解CSS盒子模型了

后记:由于本人水平有限,可能很多地方翻译的并不是很通俗。只希望能起一个抛砖引玉的作用,有更多的朋友来完善它,指出我翻译和理解不正确的地方。如果时间允许的话,我继续翻译与此相关的一些列文章(即本文中的链接)。

最后向大家推荐Andy Budd、Simon Collision、Cameron Moll写的《CSS Mastery Advanced Web Standards Solutions(Second Edition)》(精通CSS 高级Web标准解决方案第二版),翻译这篇文章时参考了其中不少内容,这也是一本适合CSS进阶类图书,不适合初学者。希望有兴趣的朋友可以参考一下。

本文网址:https://www.dedexuexi.com/wysj/jhsj/2639.html

本站部分文章搜集与网络,如有侵权请联系本站,转载请说明出处。

收藏此文 赞一下!() 打赏本站

如本文对您有帮助,就请建站学习网抽根烟吧!

支付宝打赏
微信打赏
网页上显示日期的两种方法
« 上一篇2017年04月10日
怎么做才像在BEHANCE经常发作品的设计师?
2017年04月10日下一篇 »
  • 网易云音乐WP1.0设计项目实战
    0阅读
    WP 平台是很多设计师很少涉足的地方,优设之前发过一篇WP设计规范指南,今天网易的同学继续上干货,来一篇WP的设计项目实战!作为一款有诚意的音乐APP,这次设计过程相当用心,值得学习的地方也很多,学习来。项目背景Windows Phone一直是各家公司缺少投入的平台,WP用户不得不经常面对一个成...
  • 马伯庸教你如何做一个万年好甲方
    0阅读
    编者按:原以为亲王精通历史,会写小说,现在才知道他也很懂作为甲方的门道啊。今天分享@马伯庸 同学的一篇好文,前有笑点,后有干货,有趣得紧。作为设计师,能遇到这样的甲方就嫁了吧。@马伯庸 :对我们甲方来说,艺术性是第三才需要考虑的因素。我们第二考虑的是如何有效率地把核心信息传达到客户那儿去。无论多么...
  • 网站设计主题和风格是重点
    0阅读
    企业为了在互联网上争夺一席之地,纷纷建起了网站。企业的网站就像企业的网络门户,既然是门面那么就要将网站建设好,充分展现企业的良好形象。貌似许多企业建网站是为了赶时髦,因为他们的企业网站设计的实在是不堪入目,这样不仅不会为企业带来什么利益,相反还会毁了企业的形象。那么企业要建好这样的门面应该如何入手呢...
  • 如何给网站布置干净的“关于我们”页面
    0阅读
    所有网站,无论是官方、电子商务、社会化网络还是个人站点,都应该设计一个恰到好处的关于页面,直截了当地告诉到访者,为什么要浪费他们宝贵的时间浏览你的网站。 一、为什么要有关于页面 不要让用户思考! 1、向浏览者传达本站的价值,留住用户 2、始终提醒自己站点的主旨,不要跑题 二、起什么名 关于页面存在的...
  • 如何建立一个成功的移动应用
    0阅读
    一个消费者应用程序是否成功,只通过相加其组成部分的总和来计算。简单的查看用户手机应用的下载历史,用户设备残留的移动应用数量,和那些真的被坚持使用的移动应用情况,就能知道这句话的真实含义。然而,如果你想知道为什么有些用户不再使用某些手机应用,那这篇文章可能会给你一些启示。 像一台机器一样,移动应用通过...
 
QQ在线咨询