今天臨下班的時候隔壁組的同事拉住我跟我討論一個問題,想要實現的功能以下:javascript
在一個div中有多個水平排列的div,但這些div的寬度不定,而且能夠動態增長或者減小。要求這些div組始終居中排列。如圖:css
看了一下他的代碼,是用浮動來作的,可是全部的div都靠左排列。由於塊下班了,兩我的急急忙忙調試了一下子沒能獲得正確的結果,因而下班後想好好研究一下。最終找到了三種實現的方式,寫出來跟你們一塊兒討論討論。html
嘗試一:使用Float+margin:auto+js
我就沿着他的float思路繼續思考。若是使用float的話,被浮動的元素始終會靠左或者靠右排列,只有將其父元素居中,這些元素纔有可能居中放置。否則的話要動態改動他們的margin-left或者margin-right才能實現效果。
那麼如何實現父元素居中呢,若是是定寬的元素那好辦,直接"margin: 0 auto"就能夠實現。可是這裏的父元素的大小是不固定的,要隨着子元素增減而改變。繼續走下去的辦法只有用JS去控制父元素的寬度。寫了代碼進行實驗,是能夠作到。java
1 <!DOCTYPE> 2 <html> 3 <head> 4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 5 <style type="text/css"> 6 #content{ 7 margin: 0 auto; //父元素水平居中 8 height: 202px; 9 background-color: lightblue; 10 } 11 #content div{ 12 width: 100px; 13 height: 200px; 14 float: left; //子元素向左浮動 15 border: 1px solid blue; 16 background-color:gray; 17 } 18 #toolbar{ 19 margin: 20px auto; 20 text-align: center; 21 } 22 #footer{ 23 clear: both; 24 } 25 </style> 26 27 <script type="text/javascript"> 28 function doLayout(){ 29 var contentDiv = document.getElementById("content"); 30 var children = contentDiv.children; 31 var width = 0; 32 for(var i = 0, l = children.length; i < l; i ++){ 33 width += children[i].offsetWidth; 34 } 35 36 contentDiv.style.width = width+"px"; 37 } 38 function addDiv(){ 39 var contentDiv = document.getElementById("content"); 40 var newDiv = document.createElement("Div"); 41 newDiv.innerHTML = "new added div"; 42 contentDiv.appendChild(newDiv); 43 doLayout(); 44 } 45 </script> 46 47 </head> 48 <body onload="doLayout()"> 49 <div id="page"> 50 <div id="header"><h1>自動水平居中</h1></div> 51 <div id="content"> 52 <div id="div1"> 53 <p>13123</p> 54 <span>13123</span> 55 </div> 56 <div id="div2"> 57 <a href="#">13123</a> 58 <p>13123</p> 59 <span>13123</span> 60 </div> 61 </div> 62 <div id="toolbar"> 63 <input type="button" value="Add Float Div" onClick="addDiv()"/> 64 </div> 65 <div id="footer"> 66 <p>沒人關注的頁腳</P> 67 </div> 68 </div> 69 </body> 70 </html>
嘗試二:使用inline-blockchrome
使用JS固然能夠解決這樣的問題,但到底只使用css能不能實現呢,畢竟這應該屬於一個佈局的問題。因而想到了前幾天看的一篇關於inline-block代替float實現瀑布流的文章,就想試試這裏也可否使用inline-block實現這個水平居中的效果。瀏覽器
因而開始查找inline-block的定義和用法:app
inline-block:This value causes an element to generate an inline-level block container. The inside of an inline-block is formatted as a block box, and the element itself is formatted as an atomic inline-level box.ide
意思是:inline-block會觸發元素呈現成一個行級別的塊包含對象,這個對象內部的元素呈現成塊級元素,而這個元素自己呈現成行級別的元素。 個人理解是,對與它的父元素以及兄弟元素,它是一個行級別的元素,能夠與其餘行級別元素同行放置;但對於它內部的元素,它是塊級元素,及內部的元素不須要額外的設置來觸發BFC。佈局
通過必定的嘗試和調試,終於在text-align:center的配合下,基本實現了想要的效果:ui
1 <!DOCTYPE> 2 <html> 3 <head> 4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 5 <style type="text/css"> 6 #content{ 7 text-align:center; //內部元素居中 8 height: 200px; 9 background-color: lightblue; 10 } 11 #content div{ 12 width: 100px; 13 height: 200px; 14 display:inline-block; 15 border: 1px solid blue; 16 background-color:gray; 17 } 18 #toolbar{ 19 margin: 20px auto; 20 text-align: center; 21 } 22 #footer{ 23 clear: both; 24 } 25 </style> 26 27 <script type="text/javascript"> 28 function addDiv(){ 29 var contentDiv = document.getElementById("content"); 30 var newDiv = document.createElement("Div"); 31 contentDiv.appendChild(newDiv); 32 } 33 </script> 34 </head> 35 <body> 36 <div id="page"> 37 <div id="header"><h1>自動水平居中</h1></div> 38 39 <div id="content"> 40 <div id="div1"> 41 </div> 42 <div id="div2"> 43 </div> 44 </div> 45 46 <div id="toolbar"> 47 <input type="button" value="Add Float Div" onClick="addDiv()"/> 48 </div> 49 <div id="footer"> 50 <p>沒人關注的頁腳</P> 51 </div> 52 </div> 53 </body> 54 </html>
可是在嘗試放入了一些塊級元素到各個div中的時候,發現當內部元素高度不同的時候,各個塊的排列就不能對齊了:
這可能就是內部的塊級元素產生了換行的緣由吧,可是也不能肯定,有時間仔細研究一下,也但願知道的高手能指點一下。
可是我仍是找到了解決的辦法,就是vertical-align,在設置成top以後,每一個元素內部都從頂端開始排布,因此也就能對齊了。
1 <!DOCTYPE> 2 <html> 3 <head> 4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 5 <style type="text/css"> 6 #content{ 7 text-align:center; 8 height: 202px; 9 background-color: lightblue; 10 } 11 #content div{ 12 width: 100px; 13 height: 200px; 14 display:inline-block; 15 border: 1px solid blue; 16 vertical-align: top; 17 background-color:gray; 18 } 19 #toolbar{ 20 margin: 20px auto; 21 text-align: center; 22 } 23 #footer{ 24 clear: both; 25 } 26 </style> 27 28 <script type="text/javascript"> 29 function addDiv(){ 30 var contentDiv = document.getElementById("content"); 31 var newDiv = document.createElement("Div"); 32 newDiv.innerHTML = "new added div"; 33 contentDiv.appendChild(newDiv); 34 } 35 </script> 36 </head> 37 <body> 38 <div id="page"> 39 <div id="header"><h1>自動水平居中</h1></div> 40 41 <div id="content"> 42 <div id="div1"> 43 <p>13123</p> 44 <span>13123</span> 45 </div> 46 <div id="div2"> 47 <a href="#">13123</a> 48 <p>13123</p> 49 <span>13123</span> 50 </div> 51 </div> 52 53 <div id="toolbar"> 54 <input type="button" value="Add Float Div" onClick="addDiv()"/> 55 </div> 56 <div id="footer"> 57 <p>沒人關注的頁腳</P> 58 </div> 59 </div> 60 </body> 61 </html>
至此,使用inline-block順利解決了問題。可是在查閱資料的時候都說inline-block有瀏覽器兼容的問題,本身在chrome,firefox和IE10試了以後都沒發現問題。也算是一種解決方案吧。
嘗試三:使用position:relative實現
在查閱水平居中的過程中,還看到有同窗說可使用position:relative加上float來實現,因而也嘗試了一下。確實也是能夠的:
1 <!DOCTYPE> 2 <html> 3 <head> 4 <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> 5 <style type="text/css"> 6 #content{ 7 float: left; 8 position:relative; 9 left: 50%;//父元素相對左50% 10 height: 202px; 11 } 12 #content div{ 13 float: left; 14 position:relative; 15 right: 50%;//子元素相對右50% 這裏寫成left:-50%也能工做 16 width: 100px; 17 height: 200px; 18 border: 1px solid blue; 19 background-color:gray; 20 } 21 #toolbar{ 22 clear:both; 23 margin: 20px auto; 24 text-align: center; 25 } 26 #footer{ 27 clear: both; 28 } 29 </style> 30 31 <script type="text/javascript"> 32 function addDiv(){ 33 var contentDiv = document.getElementById("content"); 34 var newDiv = document.createElement("Div"); 35 newDiv.innerHTML = "new added div"; 36 contentDiv.appendChild(newDiv); 37 } 38 </script> 39 </head> 40 <body> 41 <div id="page"> 42 <div id="header"><h1>自動水平居中</h1></div> 43 44 <div id="content"> 45 <div id="div1"> 46 <p>13123</p> 47 <span>13123</span> 48 </div> 49 <div id="div2"> 50 <a href="#">13123</a> 51 <p>13123</p> 52 <span>13123</span> 53 </div> 54 </div> 55 56 <div id="toolbar"> 57 <input type="button" value="Add Float Div" onClick="addDiv()"/> 58 </div> 59 <div id="footer"> 60 <p>沒人關注的頁腳</P> 61 </div> 62 </div> 63 </body> 64 </html>
這裏先普及一下polistion:relative的概念:
relative : 對象不可層疊,但將依據left,right,top,bottom等屬性在正常文檔流中偏移位置。
這個解釋與通常的理解有點誤差,我最開始的時候也是理解成相對定位,覺得是相對父節點的,但實際上相對的是正常狀況下本身的位置。因此也就很容易解釋,代碼中的父節點相對其父節點向右移動50%後它的開始就正好在正中間,而後子元素都相對自身向左偏移50%,天然也就能將本身的中心放在總體的中間。也就實現了居中排放的效果。
至此,這個自動水平居中的問題也算完美解決了。技術這種東西,都是取之於民用之於民,但願可以給你們一些幫助,也但願能跟你們一塊兒探討更多的問題。