1. 程式人生 > 前端設計 >手寫一個簡單的響應式柵格

手寫一個簡單的響應式柵格

前言

前段時間一衝動搞了個騰訊雲主機,最簡單的配置那種。買完之後一陣折騰,想著不如整個部落格,於是各種部落格搭建方案,看著好多漂亮的部落格,毅然決定搭建一個自己的部落格,正好自己是一個前端新手,寫一個這樣的部落格,正好能鍛鍊自己,說幹就幹,開始逐個解決技術難點。這次我解決的自制響應式柵格。

什麼是柵格系統

在許多前端框架裡,我們都能見到css柵格系統,如Bootstrap,pure等等,通過柵格系統可以實現多種裝置的響應式佈局。那啥是柵格系統?話不多說直接引用。

柵格系統(CSS Grids)是一種運用固定的格子設計版面佈局,在報刊雜誌上尤為常見。 如今響應式設計大行其道,對於前端開發,柵格系統可以:

  • 提高生產力,通過在網格的劃分,元素更容易堆放而且在跨瀏覽器上面具有一致性,使我們可以專心的注意佈局而不是相容上。
  • 具有靈活性,無論是什麼樣的佈局,都可以拆分到粒度為一個網格的大小。
  • 支援響應式設計,柵格系統本身能很好的和響應式設計結合在一起,或者說,我們的柵格系統是基於響應式設計的。

著作權歸作者所有。 商業轉載請聯絡作者獲得授權,非商業轉載請註明出處。 原文: liaokeyu.com/技術/2017/01/…

響應式實現方案

響應式實現方案有許多種,大家也可以去查查,我的實現想法主要有三個關鍵點。

  • 媒體查詢
  • 浮動
  • 流式佈局

媒體查詢

媒體查詢(Media Query)是CSS提出來的一個新的屬性,通過媒體查詢可以查詢到screen的寬度,從而指定某個寬度區間的網頁佈局。

具體實現方式如下:

/*查詢螢幕*/
@media screen and 條件 {
}
/*條件的寫法*/
/*min-width:只要螢幕寬度超過這個值的裝置樣式就能生效*/
/*max-width:只要螢幕寬度小於這個值的裝置樣式就能生效*/

/* 表示可見區域大於1200px樣式生效 */
@media screen and (min-width: 1200px) {
  .container {
    width: 1170px;
    background-color: red;
  }
}
/* 表示可見區域大於992px小於1200px樣式生效 */
@media screen and (min-width: 992px
) and (max-width: 1200px) { .container { width: 970px; background-color: blue; } } 複製程式碼

流式佈局

流式佈局,也叫百分比佈局,是移動端開發中經常使用的佈局方式之一。

流式佈局的特徵:

  • 寬度自適應,高度寫死,並不是百分百還原設計圖
  • 圖示都是固定死大小的,包括字型等也是固定死的。並不是所有的東西都是自適應的。
  • 一些大的圖片,設定寬度為百分比自適應即可,隨著螢幕大小進行變化

比如,以下程式碼能實現子盒子在可視區中各佔四分之一:

<body>
    <div class="container">
        <div class="child-one"></div>
        <div class="child-two"></div>
        <div class="child-three"></div>
        <div class="child-four"></div>
    </div>
</body>
複製程式碼
.container {
  width: 100%;
}
.child-one {
  width: 25%;
}
.child-two {
  width: 25%;
}
.child-three {
  width: 25%;
}
.child-four {
  width: 25%;
}
複製程式碼

程式設計實現

定義

當前的主流裝置的螢幕從大概尺寸如下:

  • 大屏裝置(>1200px)
  • 中屏裝置(992-1200)
  • 小屏裝置(768-992)
  • 超小屏裝置(<768px)

為了自己的部落格的佈局不需要適配那麼多裝置,根據實際需求,於是就採用三個寬度來定義大、中、小屏和超大屏

  • 小於768px的小屏(sm)
  • 大於768px小於960px的中屏(md)
  • 大於960px小於1280px的大屏(lg)
  • 大於1280px的超大屏

跟隨大眾採用 12 欄形式的柵格,所以-sm--md--lg-形式的樣式表示小、中、大屏的樣式。

  • 小屏隱藏: 表示在小屏隱藏,其他屏顯示 hidden-sm
  • 中屏隱藏: 表示在中屏隱藏,其他屏顯示 hidden-md
  • 大屏隱藏: 表示在大屏隱藏,其他屏顯示 hidden-lg
  • 小屏顯示: 表示在小屏顯示,其他屏隱藏 visible-sm
  • 中屏顯示: 表示在小屏顯示,其他屏隱藏 visible-md
  • 大屏顯示: 表示在小屏顯示,其他屏隱藏 visible-lg

初始化樣式

為了節省計算於是使用了less,只是簡單應用了巢狀和變數。直接看程式碼註釋?

/* 設定單位寬度 */
@unit-width: 100%/12;
/* 設定容器居中,寬100% */
.container {
	width: 100%;
	margin-left: auto;
	margin-right: auto;
	/* 盒子內減,減少不必要的寬高計算 */
	* {
		box-sizing: border-box;
	}
}
/* 設定行寬100% */
.row {
	position: relative;
	width: 100%;
	padding: 15px;
}
/*設定各列浮動,以及間隔*/
.row [class^="col"] {
	float: left;
	padding: 15px;
	min-height: 1px;
}
/* 清除浮動 */
.row::after {
	content: "";
	display: table;
	clear: both;
}
複製程式碼

小屏樣式

小屏樣式表示在小於768px情況下的樣式

  • col-1表示在大屏以上的螢幕佔 1/12
  • col-1-md表示在中屏以上的螢幕佔 1/12
  • col-1-sm表示在小屏以上的螢幕佔 1/12
/* 大屏和中屏的樣式初始樣式,
小屏情況下,擁有這些樣式的元素會佔據一整行,
簡而言之,就是依次橫著排列變成依次豎著排列 */
.col-1,.col-2,.col-3,.col-4,.col-5,.col-6,.col-7,.col-8,.col-9,.col-10,.col-11,.col-12,.col-1-md,.col-2-md,.col-3-md,.col-4-md,.col-5-md,.col-6-md,.col-7-md,.col-8-md,.col-9-md,.col-10-md,.col-11-md,.col-12-md {
	width: 12 * @unit-width;
}

/*使用這些樣式的元素在小屏情況下*/
.col-1-sm {
	width: @unit-width;
}
.col-2-sm {
	width: 2 * @unit-width;
}
.col-3-sm {
	width: 3 * @unit-width;
}
.col-4-sm {
	width: 4 * @unit-width;
}
.col-5-sm {
	width: 5 * @unit-width;
}
.col-6-sm {
	width: 6 * @unit-width;
}
.col-7-sm {
	width: 7 * @unit-width;
}
.col-8-sm {
	width: 8 * @unit-width;
}
.col-9-sm {
	width: 9 * @unit-width;
}
.col-10-sm {
	width: 10 * @unit-width;
}
.col-11-sm {
	width: 11 * @unit-width;
}
.col-12-sm {
	width: 12 * @unit-width;
}
/* 隱藏 和顯示樣式*/
.hidden-sm,.visible-lg,.visible-md {
	display: none;
}
/* 小屏可見 */
.hidden-md,.hidden-lg,.visible-sm {
	display: block;
}
複製程式碼

中屏樣式

/* 媒體查詢 大於768px生效*/
@media only screen and (min-width: 768px) {
    /* 中屏的容器,版心 */
	.container {
		width: 96%;
	}
	/* 中屏時,該樣式會覆蓋之前的樣式,實現中屏的樣式 */
	.col-1-md {
		width: @unit-width;
	}
	.col-2-md {
		width: 2 * @unit-width;
	}
	.col-3-md {
		width: 3 * @unit-width;
	}
	.col-4-md {
		width: 4 * @unit-width;
	}
	.col-5-md {
		width: 5 * @unit-width;
	}
	.col-6-md {
		width: 6 * @unit-width;
	}
	.col-7-md {
		width: 7 * @unit-width;
	}
	.col-8-md {
		width: 8 * @unit-width;
	}
	.col-9-md {
		width: 9 * @unit-width;
	}
	.col-10-md {
		width: 10 * @unit-width;
	}
	.col-11-md {
		width: 11 * @unit-width;
	}
	.col-12-md {
		width: 12 * @unit-width;
	}
	.hidden-sm,.visible-md {
		display: block;
	}
	.hidden-md,.visible-sm,.visible-lg {
		display: none;
	}
}
複製程式碼

大屏樣式

/* 媒體查詢 大於960px生效*/
@media only screen and (min-width: 960px) {
    /* 大屏的容器,版心 */
	.container {
		width: 90%;
	}
	/* 大屏時,該樣式會覆蓋之前的樣式,實現大屏的樣式 */
	.col-1 {
		width: @unit-width;
	}
	.col-2 {
		width: 2 * @unit-width;
	}
	.col-3 {
		width: 3 * @unit-width;
	}
	.col-4 {
		width: 4 * @unit-width;
	}
	.col-5 {
		width: 5 * @unit-width;
	}
	.col-6 {
		width: 6 * @unit-width;
	}
	.col-7 {
		width: 7 * @unit-width;
	}
	.col-8 {
		width: 8 * @unit-width;
	}
	.col-9 {
		width: 9 * @unit-width;
	}
	.col-10 {
		width: 10 * @unit-width;
	}
	.col-11 {
		width: 11 * @unit-width;
	}
	.col-12 {
		width: 12 * @unit-width;
	}
	.hidden-lg,.visible-md {
		display: none;
	}
	.hidden-md,.visible-lg {
		display: block;
	}
}
複製程式碼

超大屏樣式

/* 超大屏沒有適配,直接給個版心就好 */
@media only screen and (min-width: 1280px) {
	.container {
		width: 85%;
		max-width: 1280px;
	}
}
複製程式碼

效果展示

寫完樣式要做個測試,來看看效果,demo 程式碼如下:

<style>
        div [class^="col"] {
            border: 2px solid #000;
        }

        .row {
            border: 2px solid red;
        }
</style>
/************************************/
<div class="container">
        <div class="row">
            <div class="col-4">
                <h5>大屏樣式</h5>
            </div>
            <div class="col-4-md">
                <h5>中屏樣式</h5>
            </div>
            <div class="col-4-sm">
                <h5>小屏樣式</h5>
            </div>
        </div>
        <div class="row">
            <div class="col-4-sm hidden-lg">
                <h5>大屏隱藏</h5>
            </div>
            <div class="col-4-sm hidden-md">
                <h5>中屏隱藏</h5>
            </div>
            <div class="col-4-sm hidden-sm">
                <h5>小屏隱藏</h5>
            </div>
        </div>
        <div class="row">
            <div class="col-4-sm visible-lg">
                <h5>大屏顯示</h5>
            </div>
            <div class="col-4-sm visible-md">
                <h5>中屏顯示</h5>
            </div>
            <div class="col-4-sm visible-sm">
                <h5>小屏顯示</h5>
            </div>
        </div>
    </div>

複製程式碼

大功告成!

參考文章和開源專案: