Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[POST] Codrops Collective Cover CSS version note #41

Open
Rplus opened this issue Apr 28, 2019 · 0 comments
Open

[POST] Codrops Collective Cover CSS version note #41

Rplus opened this issue Apr 28, 2019 · 0 comments
Labels

Comments

@Rplus
Copy link
Owner

Rplus commented Apr 28, 2019

前些天抽空參考 Codrops Collective 的封面做了個 CSS 動畫版的
https://codepen.io/Rplus/pen/YMBmOK
要看錄的示範影片請到 Twitter

Codrops 原圖
image

因為最近寫 code 都沒在錄影
而且這玩意算數學也稍微花了一些時間
錄起來應該會像停格一樣吧 XD

下面回憶/記錄一下自己的製作思路:

1 基板

看到圖形時
就大概有個概念弄個一堆點點
然後配上不同的 scale 數值,讓它們有不同的尺寸

主要的思考是在於需不需要使用 CSS Grid
因為其實主要圖案的排版也不難
Grid 似乎有些大材小用的感覺
原本是想直接用 inline-block
後來想想,算了,得需要 gap,那就用 Grid 吧…

因為參數都在 pug 那邊就用 CSS variables 傳到上層了
所以 grid columns 也就直接吃參數了

另外說一下自己的(偷懶)命名習慣
這類沒什麼語意的基礎單元,
我是滿喜歡用 .o 來當 class name 的
兩個 o .oo 代表小組件,常見的是線形,
而這邊因為沒有單軸向的單元
所以 .oo 就代表兩軸向的平面
三個 o 的 .ooo 就單純懶得想上層命名,嗯,就是這樣 XD

而稍後用到的 --oi 是指該單元(.o)的 index
-ooi => .ooindex
很懶~ 但我覺得這樣還算直觀好記 XDD

2 單元點

因為對這類點的規則悟性不夠
並不像 Ana Tudor 一樣可以很迅速地推出參數與方程 XDD
所以最一開始我是做觀察
方法就是把 index, col index, row index 全部列上去
然後再慢慢去想該怎麼搭配組合出我想要的大小變化

image

就寫個 pseudo-element 塞一些 index 來看
看著上面這圖,再看看圖源
先找出規律性

2-1 單元點的尺寸

整體一起看會有點難想
那就一排排往下看;或先看邊界條件:看頭尾

第一排看起來是依照 col index 逐一遞增 1
最後一排剛好相反,依 col index 遞減

PS: 要看之前,得記得先定義 絕對大小
不然看第二排就大概忘記第一排的大小了 XD
這邊我是把第一排當作基準,最小的當 0 ,最大的當 15 (一排 16 顆)

看完頭尾兩列,再來看同樣是邊界的兩欄
第一欄也是很直觀地,依 row index 遞增 1;最末欄相反

不在邊線、中間的點點,看起來似乎不是單純整數的關係
雖然單看左上角,似乎有點像 x = y 的線性關係
但看 中央部份 跟 右上、左下的尺寸就明顯不同
所以應該沒那麼簡單~

接下來就是要算聯立方程了
嘿嘿嘿~ 正好我線性代數重修了三次

教授,抱歉,我全忘光了呢~ XDDD

線代不會沒關係~
幸好我還記得國中的二元方程怎麼列 XD

若有人看不下去的,歡迎回覆救援~ XDD

這些點點的大小若化作座標點
每列連成線的話,大概就會長得像這圖:

image

先看第一列的線性函數(紅色那條)
左下座標 (0, 0) => { col:0, size:0 }
右上座標 (15, 15) => { col:15, size: 15 }

代入二元來解 a, b
ax + b = y

row1: (0, 0), (15, 15)
	0a + b = 0
	15a + b = 15
		=> a = 1, b = 0
		=> row1: 1x + 0 = y
		=> row1: 15x/15 + 0 = y

row2: (0, 1), (15, 14)
	0a + b = 1
	15a + b = 14
		=> b = 1, a = 13 / 15
		=> 13x/15 + 1 = y

…

row16: (0, 15) (15, 0)
	0a + b = 15
	15a + b = 0
		=> b = 15, a = -1
		=> row15: -1x + 15 = y
		=> row15: -15x/15 + 15 = y

歸納出

y = x * (15 - 2 * row-index) / 15 + row-index

將 x, y 用參數代入

y : size
x : col-index(ci)
row-index(ri)

=> size = ci * (15 - ri * 2) / 15 + ri

15 = col count - 1 = col gap count

嗯~ 好吧
我刻完那張一堆線的圖
再打完上面那堆解聯立
我也不曉得到底有用到了什麼數學原理
數學能力大概只剩下:直觀感覺不出來的話,那就算了吧 XDD

不管如何~
總算得到了圓點尺寸了呢~

而用在 CSS 裡的話,最好再處理一次數值
免得 CSS 裡還要寫一堆 normalization 算式
在 pug 裡有另外寫了一支 shiftNumber() 來處理數值轉換
裡頭也就只是簡單的線代
反正就是 x0-y0 線段上的 n 點映射到 x1-y1 線段後的座標點
當然這邊只用了單維,所以當作伸縮平移也就可以了~
這段主要是輸出 CSS 要的數值範圍與格式
因為 CSS 那邊不太需要過多的小數點
算個大概就好,反正最小刻度也不能低於 1px,
一般狀況下精度不用太在意

很好,圓點大小就到這邊哩~

2-2 圓點對齊

原圖的對齊方式還挺奇妙的
我原本比為只是很普通地對齊正中心
結果細看之下,哇~ 這麼坑呀…
垂直對齊都是一致的正中心,很好
水平對齊方式真的奇葩:左邊的靠左、右邊的靠右…

我看了就碎念為什麼不弄成一樣的對齊方式…

不過後來想了一想,
覺得這設計還是有它的道理在
忘了是人眼是水平向的緣故、還是地平線的關係
人眼對於水平線的對齊會較為敏感
所以如果水平的對齊不一致的話,就會很突兀
垂直向就大概是設計師個人品味了吧(?

這邊就還滿簡單的
依據 col index,然後比例平移到 [0, 1] 之間即可
之後到 CSS 裡設定 transform-origin

2-3 圓點顏色

這邊看圖片
顏色分佈大概是右上到左下漸變
算式就比較簡單: col-index 與 row-index 的差值
因為套色會用算式來處理
所以記得讓差值正規化到 [1, -1] 區間

而在計算這種漸變色
通常會用 HSL 表式法來定義色彩

作法也挺簡單
就挑個支援 HSL 的取色器(或直接用 Chrome devtool 取色也可
得到的兩組 HSL,兩值取均值再加差值的一半
而這兩組 HSL 中的 S & L 數值差不多
所以就直接寫死了
反正我辨色力不佳~ XDD
如果設計師比較在意的話再一併調整也沒問題 :P

顏色、大小
都妥妥了~

3 動畫

上面做完後已經跟原版一樣了
但海報跟網頁有所不同,
網頁可以有更多互動嘛~

辛苦兜這麼久
當然不能只滿足於復現啦
一定得加點自己的料進去才行 XDD

原本是想弄成個上一個一樣
加些 transition 就好
但總覺得讓它們可以自己動起來好像會比較好玩

所以就加了 animation 進去
delay 時間就用 size 處理一下,
某方面來說,我們算出的 size 就是該點的 變化參數

要記得 animation 想先觸發動畫的話,delay 要設定成負數~

加好了之後,嗯~ 棒棒的

3-1 互動性

動態的有人喜歡,但也有些人喜歡靜態
能動能靜,兩種都能滿足的話不是更棒嗎~

在以往的 codepen 裡,
有些 CSS animation 我都是習慣讓滑鼠 :hover 過去後再啟動動畫
開發的時候也習慣先上一個 play-state: paused
一直動,很暈的…

所以在這邊用了 CSS variables + variables fallback
animation-play-state: var(--animation-play-state, paused)
預設就先停止
滑過親代層時再啟動動畫,享受眼花撩亂
:hover { --animation-play-state: running }

但其中有個問題是
若滑鼠移入再移出,畫面就不再是初始狀態
會跟原本的圖源長得不一樣

這邊有用到另一個 CSS 小技巧來重設動畫

&:active { --animation-name: gg }

點擊時指派另外的動畫名稱(不一定要真實存在)
點擊狀態不再時,動畫就會回到初始狀態了

本來只是想記錄一下算數學那段 XDD
不過寫就寫了
就順便記錄一些有用到的小東西 :P


註:CSS custom property 使用習慣的變化

近來用的 CSS custom property(CSS variabls)
寫作習慣是有些些的不太一樣

以前會喜歡讓 HTML 完全乾淨,只有 class name
然後在 SCSS 裡下些迴圈生些 nth-of-type() 之類的選擇器
再配與相應的 index 或是 計算用參數

而最近有些作品,我會選擇直接將參數以 inline style 的方式刻在 DOM 上
像這例我就直接將 CSS 要用到的三個參數先算完再擺進 style 裡

前者用法的好處是,樣式就真的歸樣式處理
不會因為 DOM 因為 JS 新塞新的元件進去就 gg 沒套用到

但缺點就是 SCSS/CSS 會變得比較醜
比如說,這次的例子裡,pug 裡那些算式其實也可以放在 SCSS 裡處理
都只是一些四則運算而已,
在 CSS 裡單純用 --ci, --ri 加減乘除也是完全能處理過來的
但就真的是變得醜醜的 XD
SCSS + calc + var() 的醜不是說說而已 XDD

另個原因是我覺得參數這類東西在 DOM 出來時就確立了
基本上不太會異動
這樣的情況我會比較喜歡直接在 pug 裡算完
然後在 CSS 裡寫比較明確與易懂的算式
CSS 算式寫太長,維護時讀起來有時會有點晃神 XDD


大概就這樣~
支持的話可以到 codepen 點個 ♥️ 或是 follow ~

@Rplus Rplus added the 筆記 label Apr 28, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

1 participant