HTMLElement class 裡提供了幾個如上述的 callback function,通常我們會在 connectedCallback() 裡設定 Shadow DOM 並將其掛載到 Custom Element 中。
在 Custom Element class 裡,我們可以使用 var shadowRoot = this.attachShadow({mode: "open"}); 來掛載一個 Shadow DOM , 如果 mode 選 open ,則 Shadow DOM 可以被外界用 CustomElement.shadowRoot 的方式存取,也就是 Shadow DOM 會以 shadowRoot 的屬性名被設定到 Custom Element class 上, 即 this.shadowRoot 等於剛剛 var shadowRoot = this.attachShadow({mode: "open"}); 返回的 shadowRoot。
說明: 在這次的例子中,先以只修正 div 和 p 為例,有需要修正其他的 tag 的話可自行補充到 tagsToFix 變數中 (用 | 符號分隔)。 實現的邏輯很簡單,首先我們要找出所有要修正的 tag 的 openTag 和 closeTag, 尋找 tag 使用了如下的正規表達示: <(\/?(?:div|p))(?:\s+?(?:.*?))?>
找到了以後, 1. 我們依序看找到的 tag,如果每個 tag 都看過了,就進到第2步,否則進到第1步。
2. 當每個 tag 都看過了,此時 closeTag 都處理完畢了,但堆疊中可能還留有未處理的 openTag,例如如果 HTML 是 <div><div> 的話,因為沒有 closeTag,所以上述步驟執行完後會發現堆疊中還留有未處理的 openTag,而此時堆疊中的 openTag 都是缺少成對結尾 tag 的, 所以我們可以一個個把 openTag 取出,並對其修正 HTML,在 HTML 的尾端補上缺少的結尾 tag 。
<div>
<div class="hidden-text">
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst. Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur neque.
</div>
<div class="wrapper">
<div>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst. Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur neque.
</div>
<input type="text" placeholder="" />
<label>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst. Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur neque.
</label>
</div>
</div>
說明: HTML 中是我們主要的設計結構,下面這一串文字是用來展示的 Floating
Label 測示文字,只是一個 Lorem ipsum:
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies
urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst.
Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur
neque.
注意到在 HTML 上我們的三個 Lorem ipsum 內容是完全一樣的。 然後為了讓各元件的 width 寬度一致,我們在 css 設定了一個 --wrapper-width 變數給各元件共用:
<div class="wrapper">
<div>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst. Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur neque.
</div>
<input class="line2" type="text" placeholder=" " />
<label>
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst. Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur neque.
</label>
</div>
<div class="hidden-text">
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus ultricies urna nulla, sed viverra purus elementum ut. In hac habitasse platea dictumst. Integer ut dui ligula. Morbi in velit eu urna finibus elementum id consectetur neque.
</div>
-- 先建立測試用 Table
DECLARE @tempTable TABLE (
id int not null,
amount int not null,
PRIMARY KEY (id)
)
-- 塞入測試資料
INSERT INTO @tempTable(id, amount) VALUES(1, 10)
INSERT INTO @tempTable(id, amount) VALUES(2, 25)
INSERT INTO @tempTable(id, amount) VALUES(3, 45)
-- 檢查一下
SELECT *
FROM @tempTable
ORDER BY id DESC;
-- 進行差值計算,
-- 利用 ROW_NUMBER() 來為每行標上序號值 (rowNumber),
-- 得到的 Table 自己跟自己用 JOIN,JOIN 規則是 Table 的某行 (假設序號是 i) 和上一行 (序號是 i - 1) 做 JOIN
WITH romNumberTable AS (
SELECT *, ROW_NUMBER() OVER (ORDER BY id DESC) AS rowNumber
FROM (
SELECT id, amount
FROM @tempTable
) romNumberTable
)
SELECT T1.id, T1.amount AS 'current amount', ISNULL(T2.amount, 0) AS 'previous amount', T1.amount - ISNULL(T2.amount, 0) AS 'increase'
FROM romNumberTable T1 LEFT JOIN romNumberTable T2 ON T1.id = T2.id + 1
ORDER BY id DESC