iT邦幫忙

2025 iThome 鐵人賽

DAY 3
0

為了讓後續開發更順利,開始實作前,還是得先長篇大論一下~

我在學習 Web Component 的過程中常常會陷入:這個 UI 該怎麼寫的思維陷阱。但其實,Web Component 應該是要設計一個 給別人套用的元件
我認為要思考: 我這個元件應該開放哪些設定?使用者要怎麼插入自定義內容?哪個邏輯要暴露呢?
接下來先一起探討一下,到底什麼是好用的 web component!

所有元件都能做成 Web Component 嗎?

其實就技術上來說,幾乎所有的 UI 元件都可以做成 Web Component,但是這些元件真的都適合做成 Web Component 嗎
我認為可以用幾點來判斷。

  1. 獨立性強:元件本身的功能、樣式、行為相對獨立,不依賴大量外部邏輯或狀態。
  2. 可重用性高:在不同專案、不同框架中都可能被多次使用,減少重複開發。
  3. 狀態單純:不需要大量的跨元件狀態同步,也不需要依賴全域狀態管理工具。
  4. 權責單純:元件職責單一,不會承擔複雜的業務邏輯,只專注在自己的 UI 邏輯。

適合封裝成 Web Component 的元件

獨立性強、單純、可重用性高

  • 按鈕(Button) 元件
  • 彈窗(Modal / Dialog)元件
  • 載入中(Loading Spinner)元件
  • 標籤(Tag / Badge)元件
  • 表單(Input) 元件
  • 開關(Toggle Switch)元件
  • 下拉選單(Dropdown)元件
  • Toast 元件

不建議封裝成 Web Component 的情況

  • 大型頁面容器(如整頁 layout):由於權責太複雜,狀態也並不單純
  • 太依賴框架狀態的元件:要將這些元件獨立抽離框架會有許多複雜的邏輯產生

Web Component 適合做獨立性強,可重用的元件,作為大型開發專案的積木。

該如何設計一個 Web Component?

元件就像是一個 Hub,提供了許多已經定義好的接口,而這些接口要接上 USB、鍵盤、滑鼠,還是電腦螢幕,都是由使用者決定。Web Component 就是一個「可重用的小套件」。你不應該替使用者決定它會被用在哪,而是要清楚規劃它的設定值(屬性、事件、插槽),讓使用者能自由決定內容與用途。

  • 設計者:負責決定 Hub 的 孔位與內部運作的方法
  • 使用者:負責決定怎麼接、接什麼

為了後續的可維護性及可擴充性,進入設計前都可以先思考一下:

  1. 這個元件應該開放哪些設定:例如按鈕是否 disabled 或是大小、顏色
  2. 哪些是必要的設定點,哪些可以預設,哪些要讓使用者自由決定
  3. 如何插入自定義內容:允許使用者在元件中放入自定義的 HTML,像是文字或是 icon
  4. 如何透過方法、事件,讓使用者在需要時能與元件互動:像是是否正在 loading...
  5. 先定義核心功能再考慮擴充

Web Component 的第一個核心: Custom Element

元件命名方式注意事項:

  1. 元件命名方式要使用複合式命名(必須包含一個連字號 -
  2. 不能用瀏覽器已經保留的名稱(像是 head, table, img ...)
  3. 盡量語意化,一看到標籤可以知道這個元件大致使用功能

開始建立自定元件

身為一個愛貓人士,決定先取名叫 cat-spinner

先建立一個 class,並且繼承 HTMLElement

  • 既然我們稱它為 Web Component ,那他就要有 HTML 元素該有的功能:
  • 能放進 DOM 樹裡能夠接收屬性能觸發事件能被 CSS 選擇器選到,他需要有跟其他 HTML 標籤一樣的基礎能力!

記得要呼叫 super,不然你無法觸發 JS 的繼承機制

spinner.js

class CatSpinner extends HTMLElement {
  constructor() {
    super();
  }
}
  1. 使用 customElements.define 來註冊一個自訂元件
customElements.define(`元件名稱`, `class 名稱`);

完整程式碼

class CatSpinner extends HTMLElement {
  constructor() {
    super();

    this.innerHTML = `
      <style>
        .spinner {
          width: 40px; 
          height: 40px; 
          border: 4px solid #ccc; 
          border-top: 4px solid #333; 
          border-radius: 50%; 
          animation: spin 1s linear infinite;
        }
      
        @keyframes spin {
          0% { transform: rotate(0deg); }
          100% { transform: rotate(360deg); }
        }
      </style>
      
      <div class="spinner"></div>
    `;
  }
}

// 在這裡定義你的元件
customElements.define('cat-spinner', CatSpinner);

將元件呈現在畫面上

  1. 建立一個 index.html,引用剛剛建立的 spinner.js 檔案
  2. 加入你的自訂元件標籤
<body>
  <div style="display: flex; gap: 12px; padding: 20px">
    <h2>Web Component</h2>

    <!-- 加入你的自訂元件 -->
    <cat-spinner></cat-spinner>
  </div>

  <script src="spinner.js"></script>
</body>

接下來你就可以在瀏覽器中看見剛剛定義的 cat-spinner
就是這麼簡單,順利完成自訂元件了,恭喜你!已經學完了(誤 XD
custom-element
(我需要研究一下怎麼貼 gif 檔 இдஇ)

下一篇就一起往第二個核心 Shadow DOM 深入研究吧!


上一篇
Day 2: 所以 Web Component 是什麼?
下一篇
Day 4: Web Component 中的影子樹 Shadow DOM
系列文
原生元件養成計畫:Web Component6
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言