整合營銷服務(wù)商

          電腦端+手機端+微信端=數(shù)據(jù)同步管理

          免費咨詢熱線:

          前端學(xué)習(xí)教程:移動web必會技能-圖片居中處理

          們在日常使用移動APP的時候,特別是一些資訊類的APP,都會有圖片展示的相關(guān)UI,例如APP的單大圖和三圖模式,如下圖:單圖:

          三圖:

          或者是類似微博或者朋友圈這種9宮格的圖片展示效果,如下圖:

          對于這些圖片,如果你單純的以為直接用幾個<img>,配置一下src地址,然后渲染在頁面上,那就大錯特錯了

          對于這種類型的UI展示,我們需要明確下面幾點:

          1. 圖片在上傳后,會有不同的大小,有的是長圖(長大于寬),有的是寬圖(寬大于長),或者是一些接近正方形的圖片。
          2. 在保證圖片原本長寬比的情況下,要想將圖片顯示在一個正方形的區(qū)域內(nèi),或者是固定長寬的區(qū)域內(nèi),是必須要截取一部分圖片展示的。
          3. 采用CSS或者JavaScript都可以實現(xiàn)這種效果。

          大家可以看下面這幾張圖,紅色的是圖片本身,虛線框就是展示出來的區(qū)域,便于理解:寬圖:

          長圖:

          CSS的background-size:

          單獨使用CSS的話,我們可以輕松的實現(xiàn)上面這個效果,主要利用到的屬性就是background-size這個屬性,可以先從概念上了解一下這個屬性:

          background-size: length|percentage|cover|contain
          
          • length:設(shè)置背景圖像的高度和寬度。第一個值設(shè)置寬度,第二個值設(shè)置高度。如果只設(shè)置一個值,則第二個值會被設(shè)置為 “auto”。
          • percentage:以父元素的百分比來設(shè)置背景圖像的寬度和高度。第一個值設(shè)置寬度,第二個值設(shè)置高度。如果只設(shè)置一個值,則第二個值會被設(shè)置為 “auto”。
          • cover:在保持圖像的縱橫比的前提下,以適合鋪滿整個容器并將圖像縮放成將完全覆蓋背景定位區(qū)域的最小大小。優(yōu)點是背景圖片全部覆蓋所屬元素區(qū)域;缺點是超出的部分會被隱藏。
          • contain:與cover相反,在保持圖像的縱橫比的情況下,以適合鋪滿整個容器,并將圖像縮放成將適合背景定位區(qū)域的最大大小。優(yōu)點是圖片不會出現(xiàn)變形,同時背景圖片被完全展示出來;缺點是當(dāng)所屬元素的寬高比與背景圖片的寬高比不同時,會出現(xiàn)背景留白。

          我們可以采用background-size:cover;比較合適,在保證縱橫比的情況下,如果圖片超過背景區(qū)域,將多余部分隱藏即可,同時設(shè)置background-position: center center;將主要內(nèi)容居中顯示。

          CSS的object-fit:

          HTML5新增的<img />標(biāo)簽的屬性object-fit也可滿足需求,但是要注意兼容性。

          object-fit: fill|contain|cover|scale-down|none|initial|inherit;
          

          主要用到以下屬性:

          • fill:默認,不保證保持原有的比例,內(nèi)容拉伸整個內(nèi)容容器。
          • contain:保持原有尺寸比例,內(nèi)容被縮放,參考background-size:contain。
          • cover:保持原有尺寸比例,但部分內(nèi)容可能被剪切,參考background-size:cover。
          • scale-down:保持原有尺寸比例。內(nèi)容的尺寸與 none 或 contain 中的一個相同,取決于它們兩個之間誰得到的對象尺寸會更小一些,更加智能。

          代碼效果demo:

          如果是一個單大圖,我們可以直接給一個div設(shè)置background-image,然后設(shè)置background-image即可,代碼如下:

          <div class="one-img"></div>
          
              .one-img {
                width: 100%;
                padding-top: 50%;
                background-image: url('https://gpic.qpic.cn/gbar_pic/osL7w6JTehzgKuaKrPEJ8V3lia1zoLaPShY05MdBofOpBye0yNpRXYA/');
                background-size: cover;
                background-position: center center;
              }
          

          效果如下圖:

          代碼中圖片來源于網(wǎng)絡(luò)

          這里有一個知識點,我們?nèi)绻胍獙崿F(xiàn)屏幕的適配,div的長寬是絕不可以寫成固定值px的,所以寬度可以設(shè)置成100%,這樣如果在大屏幕下,圖片自身會變大,但是高度我們是無法設(shè)置一個合適的百分比的,這里我們借助了padding-top屬性,將padding-top設(shè)置成百分比,可以讓一個div的高度被撐開,具體的值依據(jù)寬度的值,即50%表示是寬度(width:100%)的50%。

          三張連續(xù)圖,代碼如下:

              <div class="three-img-other-wrap">
               <div class="three-img-other-1 img-1"></div>
               <div class="three-img-other-2 img-2"></div>
               <div class="three-img-other-3 img-3"></div>
             </div>
          
          .three-img-wrap {
               margin-top: 5px;
               width: 100%;
               overflow: hidden;
             }
          .three-img {
               float: left;
               width: 33.3333%;
               padding-top: 33.3333%;
               border-right: 1px solid #fff;
               background-size: cover;
               background-position: center center;
               box-sizing: border-box;
             }
          

          效果如下:

          每個div,設(shè)置float:left來實現(xiàn)橫向平鋪,注意一下這里不建議使用display:inline-block,會出現(xiàn)都得空隙,如果想要實現(xiàn)9宮格,將這3個復(fù)制2份即可。

          或者是另外一種3+2+1顯示方式圖,代碼如下:

          .three-img-other-wrap {
                margin-top: 5px;
                width: 100%;
                overflow: hidden;
          }
          
          .three-img-other-1 {
                width: 66.6666%;
                padding-top: 66.6666%;
                float: left;
                border-right: 1px solid #fff;
                background-size: cover;
                background-position: center center;
                box-sizing: border-box;
              }
          .three-img-other-2 {
                width: 33.3333%;
                padding-top: 33.3333%;
                float: left;
                border-bottom: 1px solid #fff;
                background-size: cover;
                background-position: center center;
                box-sizing: border-box;
          
          }
          .three-img-other-3 {
                width: 33.3333%;
                padding-top: 33.3333%;
                float: left;
                background-size: cover;
                background-position: center center;
                box-sizing: border-box;
          }
          
          <div class="three-img-other-wrap">
             <div class="three-img-other-1 img-1"></div>
             <div class="three-img-other-2 img-2"></div>
             <div class="three-img-other-3 img-3"></div>
          </div>
          

          效果如下:

          圖片之間的縫問題:

          從上面的效果圖來看,每張圖片之間都有一定的間距(一般是1px-3px之間),在這里我們?nèi)绻褂胢argin來實現(xiàn)的話,我們是無法設(shè)置一個具體的數(shù)值的,因為我們的長寬都是采用百分比,margin也必須采用百分比,否則會出現(xiàn)錯亂,但是在此場景下margin不適合采用百分比,所以我們采用border邊框來模擬這個間距:

          border-right: 1px solid #fff;
          box-sizing: border-box;
          

          需要注意box-sizing: border-box;,這樣border將的長度將會計算在整個寬度里面,即border+width等于具體的設(shè)置的百分比。

          采用JavaScript來實現(xiàn):

          其實從代碼的優(yōu)雅程度上來說,采用我們上面講解的純Css的方法是比較好的一種方法,但是也有弊端:1. 無法監(jiān)聽圖片的加載成功和失敗事件,例如onerror或者onload。這會導(dǎo)致我們無法給加載失敗的圖片一個默認的顯示圖。2. 我們在實現(xiàn)圖片懶加載的邏輯時,div+background-image這種方式相交于<img>方式需要寫更多的邏輯。

          在這里給大家介紹一下div+background-image和<img>之間的區(qū)別:

          在網(wǎng)頁加載的過程中,以css背景圖存在的圖片background-image會等到結(jié)構(gòu)加載完成(網(wǎng)頁的內(nèi)容全部顯示以后)才開始加載,而html中的標(biāo)簽img是網(wǎng)頁結(jié)構(gòu)(內(nèi)容)的一部分會在加載結(jié)構(gòu)的過程中加載,換句話講,網(wǎng)頁會先加載標(biāo)簽<img>的內(nèi)容,再加載背景圖片background-image,如果你用引入了一個很大的圖片,那么在這個圖片下載完成之前,<img>后的內(nèi)容都不會顯示。而如果用css來引入同樣的圖片,網(wǎng)頁結(jié)構(gòu)和內(nèi)容加載完成之后,才開始加載背景圖片,不會影響你瀏覽網(wǎng)頁內(nèi)容。

          如果我們想要用JavaScript加<img>,來實現(xiàn)這種效果,基本邏輯是:

          1. 首先需要知道圖片的寬高。
          2. 給每個<img>設(shè)置src之后,需要同時設(shè)置一個父div用來包裹這個<img>。
          3. 同時父div需要設(shè)置overflow:hidden,然后根據(jù)外框的大小,和圖片的寬高,動態(tài)設(shè)置<img>的margin或者left,top來產(chǎn)生位移。

          這里的核心是如何根據(jù)外框的寬高來動態(tài)計算出圖片的位移,我們可以封裝一個方法來計算,具體的邏輯可以看注釋:

          getImagePosition(img, cW, cH) {
              // cW為外框?qū)挾龋?/ cW為外框高度,
              img.marginTop = img.marginLeft = 0;
          
              // img.h表示圖片本身高度,img.height表示計算設(shè)置之后的高度
              // img.w表示圖片本身高度,img.width表示計算設(shè)置之后的高度
          
              img.width = cW;
              img.height = cH;
          
              // 長圖 優(yōu)先設(shè)置寬度,然后長圖居中
              if (img.h * cW / img.w > cH) {
                  img.height = img.h * cW / img.w;
                  img.marginTop = (cH - img.height) * 0.5 // 0.5表示居中
              } else {// 寬圖 優(yōu)先設(shè)置高度度,然后寬圖居中
                  img.width = img.w * cH / img.h;
                  img.marginLeft = (cW - img.width) * 0.5 // 0.5表示居中
              }
          
              return img;
          }
          

          在計算出圖片位移后,外框的寬高也可以使用JavaScript來動態(tài)設(shè)置,例如屏幕寬度的三分之一或者是圖片寬度的三分之二,代碼如下:

          document.body.clientWidth * 0.5
          document.body.clientWidth * 2 / 3
          

          在眾多的移動web技能中,圖片居中處理是一個非常重要的技能,也是用的比較多的一種技能,當(dāng)然還有一些極端情況例如遇到面條圖,或者是長寬小于10px的這種非常小的圖片,可能需要單獨特殊邏輯處理了。

          白郁悶的找到老朱說道:“朱哥,我想讓一個塊容器在一個容器里面垂直居中怎么這么難啊!”

          老朱:“你是怎么實現(xiàn)的?”

          小白說:“比如一個容器的高度是400px,子容器的高度是300px,我就把子容器CSS上邊距設(shè)置成50px。”

          “那要是父容器高度發(fā)生變化你的子容器豈不是很麻煩”

          小白郁悶的說道:“你可說吧!頭疼的很!怎么才能輕松的設(shè)置垂直居中啊?”

          老朱說:“如果一個容器只有一行文字和圖片,我們可以設(shè)置容器的高度和line-height一致就可以保證文字和圖片居中,但是多行圖片,或者容器里面嵌套了其他塊元素就很麻煩了。還有一種情況就像你剛剛兩個div嵌套,子容器也是個塊元素,垂直居中直接用CSS會很麻煩,正好今天想跟你說說怎么給jQuery添加擴展方法,索性咱就以這個為例子進行討論吧!”

          小白高興的說道:“又有新知識學(xué)了,什么事給jQuery添加擴展方法呢?”

          “我們使用$(選擇器)生成的對象有很多默認jQuery方法,你應(yīng)該知道吧?”

          小白說道:“知道啊!獲取和修改容器html內(nèi)容的html()方法、獲取和修改屬性的attr()方法、修改元素css樣式的css()方法、獲取元素高度的height()方法、還有控制容器顯示的show()方法……”

          “停~!差不多了,這些都是jQuery自帶的方法,假如我們想自己增加一個方法可以用$.fn添加。我現(xiàn)在給你寫一個能夠輸出當(dāng)前容器高度和父容器高度的方法你看看!”

          “子容器和父容器的高度在CSS中都有過設(shè)定,因此我通過$.fn添加mid方法以后,再通過選擇器找到sun容器就可以直接使用mid方法了。”

          小白突然靈光一現(xiàn),說道:“朱哥我知道怎么設(shè)置一個讓塊容器基于父容器垂直居中了,你稍等我一會,我再你的代碼基礎(chǔ)上改一下!”

          也就兩分鐘的時間,小白就把代碼拿到了老朱面前,“你看,我寫好了!”

          “現(xiàn)在我想讓sun容器基于main垂直居中只需要使用一下$("#sun").mid()就可以實現(xiàn)了,以后父容器不管怎么變化,它都是基于父容器居中的。”

          老朱說道:“如果有多行塊容器,或者多行文本、圖片怎么辦?”

          小白說道:“那就給他們外面再嵌套一個塊容器就可以了么!對不對啊?”

          “不錯,通過給他們嵌套一個塊容器,然后再讓這個塊容器基于父容器垂直居中就可以了!小白我相信你還能再寫一個基于底部對齊的方法吧?”

          小白自信的說道:“再這個方法上改一下就可以了,稍等~”

          “嗯,不錯,如果你發(fā)現(xiàn)以后經(jīng)常會用到這兩種居中方式,可以把他們放到一個js文件里面,以后用的時候把這個js文件引入,就可以直接使用mid和bottom方法了。”

          “$.fn確實是個好東西!看來我以后得經(jīng)常添加自己的方法了,哈哈,我去練習(xí)了~”


          想學(xué)H5的朋友可以關(guān)注老爐,您的關(guān)注是我持續(xù)更新《小白HTML5成長之路》的動力!

          平居中方案:

          水平居中設(shè)置

          1、行內(nèi)元素

          設(shè)置 text-align:center

          2、定寬塊狀元素

          設(shè)置 左右 margin 值為 auto

          3、不定寬塊狀元素

          a:在元素外加入 table 標(biāo)簽(完整的,包括 table、tbody、tr、td),該元素寫在 td 內(nèi),然后設(shè)置 margin 的值為 auto

          b:給該元素設(shè)置 displa:inine 方法

          c:父元素設(shè)置 position:relative 和 left:50%,子元素設(shè)置 position:relative 和 left:50%

          垂直居中設(shè)置

          1、父元素高度確定的單行文本

          設(shè)置 height = line-height

          2、父元素高度確定的多行文本

          a:插入 table (插入方法和水平居中一樣),然后設(shè)置 vertical-align:middle

          b:先設(shè)置 display:table-cell 再設(shè)置 vertical-align:middle

          在前端面試中,大都會問你div居中的方法:

          文筆不好,就隨便寥寥幾句話概括了,希望大家能夠輕拍

          不過以后文筆肯定會變得更好一些的。

          開始這些東西之前也可以測試一下你對html了解多少,讓我們測試一下吧,小測驗:你對HTML5了解有多少?

          今天我們就細數(shù)一下幾種方法:

          1,使用position:absolute,設(shè)置left、top、margin-left、margin-top的屬性

          .one{

          position:absolute;

          width:200px;

          height:200px;

          top:50%;

          left:50%;

          margin-top:-100px;

          margin-left:-100px;

          background:red;

          }

          這種方法基本瀏覽器都能夠兼容,不足之處就是需要固定寬高。

          2,使用position:fixed,同樣設(shè)置left、top、margin-left、margin-top的屬性

          .two{

          position:fixed;

          width:180px;

          height:180px;

          margin-top:-90px;

          margin-left:-90px;

          background:orange;

          }

          大家都知道的position:fixed,IE是不支持這個屬性的

          3,利用position:fixed屬性,margin:auto這個必須不要忘記了。

          .three{

          position:fixed;

          width:160px;

          height:160px;

          top:0;

          right:0;

          bottom:0;

          left:0;

          margin:auto;

          background:pink;

          }

          4,利用position:absolute屬性,設(shè)置top/bottom/right/left

          .four{

          position:absolute;

          width:140px;

          height:140px;

          background:black;

          }

          5,利用display:table-cell屬性使內(nèi)容垂直居中

          .five{

          display:table-cell;

          vertical-align:middle;

          text-align:center;

          width:120px;

          height:120px;

          background:purple;

          }

          6,最簡單的一種使行內(nèi)元素居中的方法,使用line-height屬性

          .six{

          width:100px;

          height:100px;

          line-height:100px;

          text-align:center;

          background:gray;

          }

          這種方法也很實用,比如使文字垂直居中對齊

          7,使用css3的display:-webkit-box屬性,再設(shè)置-webkit-box-pack:center/-webkit-box-align:center

          .seven{

          width:90px;

          height:90px;

          display:-webkit-box;

          -webkit-box-pack:center;

          -webkit-box-align:center;

          background:yellow;

          color:black;

          }

          8,使用css3的新屬性transform:translate(x,y)屬性

          .eight{

          position:absolute;

          width:80px;

          height:80px;

          transform:translate(-50%,-50%);

          -webkit-transform:translate(-50%,-50%);

          -moz-transform:translate(-50%,-50%);

          -ms-transform:translate(-50%,-50%);

          background:green;

          }

          這個方法可以不需要設(shè)定固定的寬高,在移動端用的會比較多,在移動端css3兼容的比較好

          9、最高大上的一種,使用:before元素

          .nine{

          position:fixed;

          display:block;

          background:rgba(0,0,0,.5);

          }

          .nine:before{

          content:'';

          display:inline-block;

          vertical-align:middle;

          height:100%;

          }

          .nine .content{

          width:60px;

          height:60px;

          line-height:60px;

          color:red;

          總而言之所有的居中的方法就是你必須要掌握css屬性的這個概念HTML DIV+CSS,你掌握了就可以好好的運用這些居中的東西了

          限時!!免費送Dreamweaver、js等前端教程

          ↓↓↓


          主站蜘蛛池模板: 国产自产在线视频一区| 一区二区三区视频网站| 文中字幕一区二区三区视频播放| 精品少妇人妻AV一区二区三区 | 亚洲一区二区三区久久久久| 一区二区三区四区无限乱码| 国精产品一区一区三区免费视频| 中文字幕一区二区视频| 久久精品国产一区二区电影| 国内偷窥一区二区三区视频| 久久久精品人妻一区二区三区四| 国产一区二区在线观看麻豆 | 99精品久久精品一区二区| 国产一区二区三区在线2021| 鲁丝丝国产一区二区| 国产成人片视频一区二区| 极品人妻少妇一区二区三区| 久久中文字幕无码一区二区| 日韩一区二区三区免费播放| 国产激情视频一区二区三区| 无码av中文一区二区三区桃花岛| 日本免费一区二区三区四区五六区| 秋霞鲁丝片一区二区三区| 亚洲第一区视频在线观看| 国产精品成人99一区无码| 国产激情з∠视频一区二区| 国产精品一区二区av不卡| 在线播放一区二区| 亚洲电影一区二区三区| 精品一区二区无码AV| 久久毛片一区二区| 国产精品福利一区二区久久| 久久国产一区二区三区| 日本免费一区尤物| 久久精品一区二区国产| 老鸭窝毛片一区二区三区| 国产日韩精品一区二区三区| 无码精品黑人一区二区三区| 能在线观看的一区二区三区| 国产大秀视频在线一区二区 | 国产美女在线一区二区三区|