css flexbox模型
I shared how to build a calendar with CSS Grid in the previous article. Today, I want to share how to build a Flexbox fallback for the same calendar.
在上一篇文章中,我分享了如何使用CSS Grid構建日歷。 今天,我想分享如何為同一日歷構建Flexbox后備廣告。
如何提供支持 (How to provide support)
Generally, there are three ways to provide support when it comes to CSS.
通常,涉及CSS時,可以通過三種方式提供支持。
First method: Write fallback code. Overwrite fallback code.
第一種方法:編寫后備代碼。 覆蓋后備代碼。
.selector {property: fallback-value;property: actual-value;
}
Second method: Write fallback code. Overwrite fallback code in CSS Feature Queries (@supports
). Reset properties inside @supports
if you need.
第二種方法:編寫后備代碼。 覆蓋CSS功能查詢( @supports
)中的后備代碼。 如果需要,請在@supports
內重置屬性。
.selector {property: fallback-value;
}@supports (display: grid) {property: actual-value;
}
Third method: Write everything in @supports
.
第三種方法:在@supports
編寫所有@supports
。
@supports not (display: grid) {.selector {property: fallback-value;}
}@supports (display: grid) {.selector {property: actual-value;}
}
These three methods are listed in order of decreasing-complexity. (If you need to overwrite code, it's more complicated). This means writing everything in @supports
is the simplest of the three.
這三種方法按復雜度遞減的順序列出。 (如果您需要覆蓋代碼,則更為復雜)。 這意味著用@supports
編寫所有@supports
是這三個中最簡單的。
How you choose to support your project depends on browser support for:
選擇支持項目的方式取決于瀏覽器對以下方面的支持:
- The feature 功能
- The fallback feature 后備功能
- Support for Feature Queries 支持功能查詢
檢查支持 (Checking for support)
The best place to check for support is caniuse. Here, I see that support for CSS Grid is decent. Browsers I have to worry about are:
尋求支持的最佳地點是caniuse 。 在這里,我看到對CSS Grid的支持是不錯的。 我要擔心的瀏覽器是:
- Opera Mini: 1.42% global usage Opera Mini:1.42%的全球使用量
- Android Browsers 2.1 to 4.4.4: 0.67% global usage Android瀏覽器2.1至4.4.4:全球使用率為0.67%
- Blackberry browser: 0.02% global usage (Not gonna worry about this one). 黑莓瀏覽器:0.02%的全球使用率(不用擔心這一點)。
Support for the fallback (Flexbox) is also good.
對后備(Flexbox)的支持也很好。
But we have a problem: Flexbox fallback wouldn't work for Android 2.1 to 4.3 (it doesn't support wrapping). Global usage for Android 2.1 to 4.3 is 0.37%.
但是我們有一個問題:Flexbox后備廣告在Android 2.1到4.3上不起作用(它不支持換行)。 Android 2.1至4.3的全球使用率為0.37%。
Here, I have to decide:
在這里,我必須決定:
- Is providing Flexbox fallback for Opera Mini (1.42%), Android 4.4.4 (0.3%), and Blackberry (0.02%) worth the effort? 為Opera Mini(1.42%),Android 4.4.4(0.3%)和Blackberry(0.02%)提供Flexbox后備功能值得嗎?
- Should I change fallback from Flexbox to an older feature to support Android 2.1 to 4.3 (another 0.37%)? 我是否應該將Flexbox的后備功能更改為較舊的功能,以支持Android 2.1到4.3(另一個0.37%)?
Let's assume, for this project, I decide that Flexbox fallback is sufficient. I'm not going to worry about Android 2.1 to 4.3.
讓我們假設,對于這個項目,我認為Flexbox后備就足夠了。 我不會擔心Android 2.1至4.3。
Next, I want to check whether browsers support CSS Feature Queries.
接下來,我要檢查瀏覽器是否支持CSS功能查詢。
Here, I see:
在這里,我看到:
- Opera Mini supports Feature Queries Opera Mini支持功能查詢
- Android 4.4.4 supports Feature Queries Android 4.4.4支持功能查詢
- Blackberry browser doesn't support Feature Queries Blackberry瀏覽器不支持功能查詢
- IE 11 does't support Feature Queries IE 11不支持功能查詢
確定如何編寫后備代碼 (Deciding how to write fallback code)
Earlier, I mentioned there are three ways to write fallback code for CSS:
之前,我提到了為CSS編寫后備代碼的三種方法:
- Write fallback code. Overwrite fallback code. 編寫后備代碼。 覆蓋后備代碼。
Write fallback code. Overwrite fallback code in
@supports
.編寫后備代碼。 覆蓋
@supports
后備代碼。Write everything in
@supports
.將所有內容寫在
@supports
。
If I write everything inside @supports
, I can provide support for:
如果我在@supports
內編寫所有@supports
,則可以提供以下支持:
- Opera Mini (1.43%) Opera Mini(1.43%)
- Android 4.4.4 (0.3%) Android 4.4.4(0.3%)
But I lose support for:
但是我對以下方面失去支持:
- IE 11 (2.3%) IE 11(2.3%)
- Blackberry (0.02%) 黑莓(0.02%)
I do not want to forsake the 2.3% of IE users, which means Method 3 (write everything in @supports
) is out.
我不想放棄2.3%的IE用戶,這意味著方法3(將所有內容寫在@supports
)已經淘汰了。
If I use Method 2 (Write fallback code. Overwrite fallback code in @supports
), I can provide support for:
如果我使用方法2(寫回退代碼。覆蓋@supports
回退代碼),則可以提供以下支持:
- IE 11 (2.3%) IE 11(2.3%)
- Opera Mini (1.43%) Opera Mini(1.43%)
- Android 4.4.4 (0.3%) Android 4.4.4(0.3%)
- Blackberry browser (0.02%) 黑莓瀏覽器(0.02%)
That's everything I need. That's why I'm gonna go with Method 2.
這就是我所需要的。 這就是為什么我要使用方法2。
Note: If you want to code along, you can use demo from my previous article as the starting point.
注意:如果要一起編碼,則可以使用上一篇文章中的演示作為起點。
禁用網格代碼 (Disabling Grid code)
First, we park the CSS Grid code under @supports
(like we discussed above).
首先,我們將CSS Grid代碼停放在@supports
下(就像我們上面討論的那樣)。
@supports (display: grid) {.day-of-week,.date-grid {display: grid;grid-template-columns: repeat(7, 1fr);}.date-grid button:first-child {grid-column: 6;}
}
We can disable the CSS Grid code by setting display
to an invalid value (not grid
). This disables the entire block of code.
我們可以通過將display
設置為無效值(不是grid
)來禁用CSS Grid代碼。 這將禁用整個代碼塊。
(Thank Rachel Andrew for this neat trick. I believe I learned it from her ?).
(感謝Rachel Andrew的巧妙技巧。我相信我從她那里學到了嗎?)。
@supports (display: gridx) {/*...*/
}
編寫Flexbox代碼 (Writing Flexbox code)
We need to build the same seven-column grid with Flexbox. The first thing we need to do is acknowledge that Flexbox and Grid work differently. We won't be able to get a perfect replica, but we can get close.
我們需要使用Flexbox構建相同的七列網格。 我們需要做的第一件事是確認Flexbox和Grid的工作方式不同。 我們將無法獲得完美的復制品,但我們可以接近。
The first thing is set display
to flex
.
首先將display
設置為flex
。
.day-of-week,
.date-grid {display: flex;
}
We need the buttons in .date-grid
to wrap, so we set flex-wrap
to wrap
.
我們需要包裝.date-grid
的按鈕,所以我們將flex-wrap
設置為wrap
。
.date-grid {flex-wrap: wrap;
}
We need to replicate the seven-column grid. An easy way to do this is calculate the width of the grid according to the width of each button. Here, I have already set each button to 4.5ch. This means the width of the grid should be 7 x 4.5ch
.
我們需要復制七列網格。 一種簡單的方法是根據每個按鈕的寬度計算網格的寬度。 在這里,我已經將每個按鈕設置為4.5ch。 這意味著網格的寬度應為7 x 4.5ch
。
(We can use CSS Calc to do the math for us).
(我們可以使用CSS Calc為我們做數學運算)。
.day-of-week,
.date-grid {max-width: calc(4.5ch * 7);
}
We need the elements in .day-of-week
to spread out across the available width. One simple way is to set justify-content
to space-between
.
我們需要.day-of-week
的元素分布在可用寬度上。 一種簡單的方法是將justify-content
設置justify-content
space-between
。
.day-of-week {justify-content: space-between;
}
Here, we can see that elements in .day-of-week
extend past the grid. This extension happens because we let Flexbox calculate flex-basis
for us. If we want every element in .day-of-week
to be have the same width, we need to set flex-basis
ourselves.
在這里,我們可以看到.day-of-week
中的元素延伸到網格之外。 之所以發生這種擴展,是因為我們讓Flexbox為我們計算了flex-basis
。 如果我們希望.day-of-week
每個元素都具有相同的寬度,則需要自己設置flex-basis
。
In this case, the easiest way is to set flex-basis
to the width of one grid item (or 4.5ch
). Note: I adjusted font-size
of each item in .day-of-week
to 0.7em
(for visual aesthetics). We have to account for this change.
在這種情況下,最簡單的方法是將flex-basis
設置為一個網格項的寬度(或4.5ch
)。 注意:我將每個項目在.day-of-week
font-size
調整為0.7em
(出于視覺美感)。 我們必須考慮到這一變化。
.day-of-week > * {flex-basis: calc(4.5ch / 0.7);
}
Finally, we need to push the 1 February to Friday. (Five columns). Since column is 4.5ch
, we simply push it by 4.5ch x 5
.
最后,我們需要將2月1日推到星期五。 (五列)。 由于4.5ch
,我們只需將其推入4.5ch x 5
。
(Again, we can use CSS Calc to help us with this).
(同樣,我們可以使用CSS Calc來幫助我們)。
.date-grid button:first-child {margin-left: calc(4.5ch * 5);
}
修復CSS網格版本 (Fixing the CSS Grid version)
We can reactivate the CSS Grid code and make any necessary changes now.
我們現在可以重新激活CSS Grid代碼并進行任何必要的更改。
@supports (display: grid) {/* ... */
}
Here, we see some values fly far out to the right. This happens because we added margin-left
to the first grid item. We need to reset the added margin.
在這里,我們看到一些值向右飛走。 發生這種情況是因為我們向第一個網格項添加了margin-left
。 我們需要重置增加的保證金。
@supports (display: grid) {/* ... */.date-grid button:first-child {grid-column: 6;margin-left: 0;}
}
Another thing: We can remove max-width
because we don't need it in the CSS Code. (Even though this doesn't affect the CSS Code, we still want to remove it. Always better to have less properties).
另一件事:我們可以刪除max-width
因為CSS代碼中不需要它。 (即使這不會影響CSS代碼,我們仍然希望將其刪除。總是最好減少屬性)。
@supports (display: grid) {.day-of-week,.date-grid {display: grid;grid-template-columns: repeat(7, 1fr);max-width: initial;}/* ... */
}
Here's the visual difference between the Flexbox and CSS Grid versions. Not too bad!
這是Flexbox和CSS Grid版本之間的視覺差異。 還不錯!

一件事有趣 (One fun thing)
CSS Grid is cool because it follows writing direction. We can easily change the flow from left-to-right to right-to-left.
CSS Grid很酷,因為它遵循書寫方向。 我們可以輕松地將流程從左到右更改為從右到左。
Note: I don't know if calendars are read from right to left in rtl languages. I just thought it'll fun to mention this ?).
注意:我不知道日歷是否以rtl語言從右到左讀取。 我只是覺得提到這個會很有趣?)。

Our code for CSS Grid supports this behaviour naturally. If you want to support the same behaviour with Flexbox, you need to use CSS Logical Properties.
我們CSS Grid代碼自然支持此行為。 如果要使用Flexbox支持相同的行為,則需要使用CSS邏輯屬性 。
Since support for CSS Logical Properties is not-so-great, we need to provide fallback for it. (Best way is to through Method 1: Write fallback; overwrite fallback).
由于對CSS邏輯屬性的支持不太好,因此我們需要為其提供備用。 (最好的方法是通過方法1:寫回退;覆蓋回退)。
.date-grid button:first-child {margin-left: calc(4.5ch * 5);margin-inline-start: calc(4.5ch * 5);
}@supports (display: grid) {/* ... */.date-grid button:first-child {grid-column: 6;margin-left: 0;margin-inline-start: 0;}
}
That's it! Here's a Codepen for the final code:
而已! 這是最終代碼的Codepen:
See the Pen Building a Calendar with CSS Grid (and fallback with Flexbox) by Zell Liew (@zellwk) on CodePen.
請參閱CodePen上的Zell Liew( @zellwk ) 撰寫的 使用CSS網格構建日歷(以及使用Flexbox進行后退 )的筆 。
Thanks for reading. This article was originally posted on my blog. Sign up for my newsletter if you want more articles to help you become a better frontend developer.
謝謝閱讀。 本文最初發布在我的博客上 。 如果您想要更多的文章來幫助您成為更好的前端開發人員,請注冊我的時事通訊 。
翻譯自: https://www.freecodecamp.org/news/how-to-add-flexbox-fallback-to-css-grid/
css flexbox模型