iT邦幫忙

2021 iThome 鐵人賽

DAY 11
0
Modern Web

關於 UI 元件你所該知道的事系列 第 11

Day 11 - Design System x 實作 — Transition

https://ithelp.ithome.com.tw/upload/images/20210926/20120754IlSw3UyWl1.png

今天要介紹的是網頁元件會用到的動畫,在 Day 07 已經介紹過過渡動畫這邊主要就是三大重點要定義:過渡類型( Transition Type)、持續時間(Duration)和 緩速效果(Easing)。

想先看 Code 或是 Demo 的由此去

Github Repo: ithelp-ui-demo

Live Demo:Storybook

React Transition Group

在實作上,有個現成的好用東西叫 React Transition Group 可以用,而在 Vue 那邊則是直接有 Transition Mode 可以用。

它主要提供 Transition、CSSTransition、SwitchTransition 和 TransitionGroup 這四大元件給我們用。

Transition:最基本的 Transition 元件,用 style Attribute 操作 CSS。

CSSTransition:以 Transition 元件為基礎,進一步讓你可針對 CSS 做客製化。

SwitchTransition:可讓你運用 State 去切換想呈現的 Transition 效果。

TransitionGroup:讓你一次管理一整組元件的 Transition 特效。

在這邊會採用的是第二種 CSSTransition 元件,因為可以客製化 CSS,並運用 Tailwind Utility Class 的可以讓原生 CSS 去 Apply 的特性,可以更好地去定義 Transition 的效果,再加上使用 className 的效能會比 Style 好很多,所以選擇使用 CSSTransition。

但 Transition 的自由度一定是比較高的,這邊我可能日後會在修正,到時候也會補上新版的 Code,但今天先這樣 Demo!

元件的過場(Transition)都是由一個 Trigger 觸發(可能是點擊按鈕),並會定義起始狀態跟結束狀態(點擊前後的元件的狀態,像是 按鈕點擊後相應的元件會出現跟消失),依此可以再區分出以下四個時機點:

  • 'entering' :正要進入起始狀態的時間點(按鈕點擊後,元件準備出現的瞬間),像是 Modal 正準備出現。
  • 'entered':起始狀態過渡完成的時間點(元件出現的過渡動畫結束時的瞬間),像是 Modal 出現後的那個時間點。
  • 'exiting':與 entering 相反,正要進入結束狀態的時間點(按鈕再次點擊後,元件準備消失的瞬間),像是 Modal 正準備消失。
  • 'exited':與 enter 相反,結束狀態過渡完成的時間點(元件結束的過渡動畫結束的瞬間),像是 Modal 消失後的那個時間點。

以下圖來說,元件要出現時,先是 entering 狀態什麼都沒有, Opacity 是 0,到 entered 元件出現後,opacity 變 1,並附上相應的 transition 屬性。

而元件要消失時,先進入 exiting 狀態,元件還存在所以opacity 是 1,到 exited 元件消失後, opacity 是 0,並也有相應的 transition 屬性。

而 CSSTransition 需要引入的 CSS 設定會是這樣:

.className-enter {
  opacity: 0;
}
.className-enter-active {
  opacity: 1;
  transition: opacity 200ms;
}
.className-exit {
  opacity: 1;
}
.className-exit-active {
  opacity: 0;
  transition: opacity 200ms;
}

Interface

接下來就介紹在 React Transition Group 為 Transition 設計了怎樣的介面,提供了哪些 Props,除了下圖以外還有一些 Props (像 appear, addEnd Listener 等等),但這邊沒用到就先不贅述。

https://ithelp.ithome.com.tw/upload/images/20210926/201207540ajEO1sN7w.png

元件實作

元件的實作就這樣直接使用套件,但只有這樣的話就太沒誠意了,因此在這邊會實作 Fade 來 Demo 給大家看!

Fade

import { CSSTransition } from "react-transition-group";
import { CSSTransitionProps } from "react-transition-group/CSSTransition";

import './fade.css';

export interface FadeProps extends CSSTransitionProps {
}

export const Fade: React.FC<CSSTransitionProps> = (props) => {
  const {
    children,
    ...rest
  } = props;

  return (
    <CSSTransition
      timeout={300}
      unmountOnExit
      classNames="fade"
      {...rest}
    >
    {children}
  </CSSTransition>
  )
}
.fade-enter {
  opacity: 0;
  transform: scale(0.9);
}
.fade-enter-active {
  opacity: 1;
  transform: translateX(0);
  transition: opacity 300ms, transform 300ms;
}
.fade-exit {
  opacity: 1;
}
.fade-exit-active {
  opacity: 0;
  transform: scale(0.9);
  transition: opacity 300ms, transform 300ms;
}

這邊其實還是把 TransitionType、Duration 跟 Easing 寫死,但如之前所說,這部份應該是要在 Design System 中會定義出幾個固定的值,讓整個網頁的過渡效果都一致,但這次 Demo 做得比較趕沒時間去做更彈性的處理,等這系列的文章都發完後還有空的話,會再上來重構一下的!

小結

今天的東西可能有點水,但重點在介紹 React-Transition-Group 這個好東西給大家,跟 Design System 更有關聯的許多客製化希望能再日後會再補上更好的版本,這邊就先請讀者見諒了!

那 Design System 的篇章就到今天結束了,對於設計還想知道的話可以參考 Material Design ,而實作的部分真的是透過 Tailwind 就能實現大部分了,這邊是透過 Color 給大家感受一下,Typography 是比較特別也有趣的實作,而 Icon 跟 Transition 則是提供給大家一種作法,其實還有很多種其他的實作方式的!

明天開始會進入 元件們的 UML 環節,談談 UI 元件們彼此之間的關係,理解網頁中 UI 元件的階層關係,像是哪些元件是最先需要實作的 、哪些元件是怎麼被組成的等等,而這些關係在軟體設計中是可以透過 UML 的元件圖來呈現的。

那就明天見囉!


上一篇
Day 10 - Design System x 實作 — Icon 元件
下一篇
Day 12 - UML — 系統設計不可不知的 UML
系列文
關於 UI 元件你所該知道的事30

尚未有邦友留言

立即登入留言