Open8
Angular+TailwindのOptimizationメモ
ベース: ngneat/tailwind https://github.com/ngneat/tailwind/
どこにどう書かれたクラスが最適化時にどう扱われるかをまとめたい
テンプレートHTML
普通のclass属性
<div class="block">
普通にPurgeCSSに認識される。使用したクラスはグローバルCSSに残る
バインディング + 文字列リテラル
<div [class]="'block'">
PurgeCSSは '
もデリミタに含まれるので正しく認識される
バインディング + プロパティ参照
<div [class]="classStr">
export class AppComponent {
classStr = 'block';
}
Tailwindの purge
コンフィグの content
にtsファイルが含まれていれば正しく認識される。
purge: {
content: ['./apps/**/*.{html,ts}', './libs/**/*.{html,ts}'],
},
クラスバインディング
<div [class.block]="true">
認識された。
クラスバインディング(Key-Value)
<div [class]="{ block: true }">
と :
がデリミタに含まれるのでこれは block
が認識される
クラスバインディング(配列)
<div [class]="['block']">
これもクォートで囲まれていれば認識される
ホストバインディング
host
メタデータ + class
属性 + インライン
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss'],
host: {
class: 'h-screen max-h-screen',
},
})
export class AppComponent {}
認識された。デリミタ的に当然
host
メタデータ + クラスバインディング
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss'],
host: {
'[class.h-screen]': 'true',
},
})
export class AppComponent {}
認識された
HostBinding
+ クラスバインディング
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss'],
})
export class AppComponent {
@HostBinding('class.h-screen') hScreen = true;
}
認識された
interpolationなど使った動的なクラス文字列生成は当然無理として、これ以外にクラスを指定する手段があれば検証したい
最適化メモ
コンポーネントスタイルとの併用について
-
*.component.css
などで@apply
を使うとビルド時に指定したクラスのスタイルがマージされる(インライン化される) -
@apply
でも参照され、テンプレートからもクラスとして参照されるとバイナリ的には重複が発生する- 重複した分だけトータルのCSSペイロードサイズが増える
-
@apply
を使った構造化を行うならば、ビルド時の解決側に倒し切る(HTMLからは参照しない)ほうがバンドルサイズの観点からは望ましいか- とはいえ複数のコンポーネントが同じクラスをapplyするとそれぞれのコンポーネントスタイルにインライン化されるので、これもバンドルサイズ的には望ましくない。
- 同一部分はある程度gzipなどの圧縮は効くだろうが...
- ユーティリティクラスセットとスコープ化CSSの噛み合わせはあまりよくなさそう。
- コンポーネントスタイルでのapplyの多用を防ぐためにも、Angular CLIのComponent Style Budgetと併用して防御しておくのがいいだろう
- とはいえ複数のコンポーネントが同じクラスをapplyするとそれぞれのコンポーネントスタイルにインライン化されるので、これもバンドルサイズ的には望ましくない。
@apply
について
コンポーネントCSSと 大体ここに書いてある
- やはりコンポーネントCSS内で
@apply
は避けるべきだろう- 複数のコンポーネントCSSにインライン化された同じスタイルがCSSサイズを肥大化する
- 再利用可能にする単位はAngularコンポーネントにする
-
.btn
クラスが欲しくなったということはButtonComponent
を作る時が来たということ
-
- どうしても再利用可能なクラスセットを
@apply
で定義したい場合はグローバルCSS(styles.css
)を使おう - Tailwindをがっつり使うプロジェクトではAngularが用意するコンポーネントCSSはほとんど使わないほうがスタイリングの情報源が一貫するだろう
- 強いて言うなら
:host { display: block;}
程度か - コンポーネントCSSを使うときには、Tailwindには依存せずピュアなCSSを書く
- 強いて言うなら