Tailwind CSS + Laravel Mix で CSS を書かないコーディングを開始してみた

# Tailwind CSS とは？

**Tailwind CSS** とは、ユーティリティ・ファーストなCSSフレームワーク。CSSフレームワークというと、Twitter Bootstrapがとみに有名であるが、完成品ができあがっているイメージの Bootstrap と比較して、ローレベルなCSSフレームワークとして設計されており、どんなデザインにも使えるカスタマイズのしやすさが特徴。詳しくは[公式サイト](https://tailwindcss.com/)を見てください。

# Laravel Mix とは？

**Laravel Mix** とは、webpackを使いやすくしてくれるラッパーツール。その名の通り [Laravel](https://laravel.com/) で開発するアプリで真価を発揮しますが、Laravel を使用しない場合でも便利です。

# セットアップ

## npm イニシャライズ

まずプロジェクトディレクトリを作成し、npmプロジェクトを初期化しましょう。 

```console
$ mkdir tailwind-laravel-mix
$ cd tailwind-laravel-mix
$ npm init -y
```

`package.json` が自動的に生成されます。

## Laravel Mix をインストール

```console
$ npm install laravel-mix@4.x --save-dev
$ cp node_modules/laravel-mix/setup/webpack.mix.js ./
$ mkdir src && touch src/app.{js,scss}
```

`node_modules/` ディレクトリ内に Laravel Mix がインストールされます。
プロジェクトディレクトリルートに `webpack.mix.js` が作成されます。
`src/` ディレクトリ内に空の `app.js` と `app.scss` の２ファイルが作成されます。

### Laravel Mix を使って Sass ファイルをコンパイルしてみる

```console
$ node_modules/.bin/webpack --config=node_modules/laravel-mix/setup/webpack.config.js
```

まだ `app.js` と `app.scss` に何も書いていないので、単に空の `app.js` と `app.css` が `dist/` ディレクトリに作成されるはずです。

長いので npm scripts に登録しておくと便利ですね。

```package.json
  "scripts": {
    "build": "node_modules/.bin/webpack --config=node_modules/laravel-mix/setup/webpack.config.js"
  },
```

次の短いコマンドで実行できるようになります。

```console
$ npm run build
```

エラーなく実行できればOKです。

## Tailwind CSS をインストール

```console
$ npm install tailwindcss
```

`node_modules/` 内に Tailwind CSS がインストールされます。

### Tailwind CSS 用のconfigファイルを作成

```console
$ npx tailwind init
```

`tailwind.config.js` ファイルが自動で生成されます。

`webpack.mix.js` 内で生成した `tailwind.config.js` ファイルを読み込むように設定しましょう。

```webpack.mix.js
const mix = require('laravel-mix');
const tailwindcss = require('tailwindcss');

mix.js('src/app.js', 'dist/')
    .sass('src/app.scss', 'dist/')
    .options({
        processCssUrls: false,
        postCss: [ tailwindcss('./tailwind.config.js') ],
    });
```

### Tailwind CSS を使用する

`src/app.scss` で Tailwind CSS をインポートしてみましょう。

```src/app.scss
@tailwind base;

@tailwind components;

@tailwind utilities;
```

ビルドしてみましょう。

```console
$ npm run build
```

`dist/app.css` 内に Tailwind CSS のスタイルが書き込まれたら成功です。

HTML を作成してみて、実際の表示も確認してみましょう。

```dist/index.html
<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <title>Tailwind CSS Example</title>
    <link href="https://fonts.googleapis.com/css?family=Sawarabi+Gothic&display=swap" rel="stylesheet">
    <link rel="stylesheet" href="app.css">
</head>
<body class="bg-gray-100">
    <div class="max-w-sm mx-auto p-6 bg-white rounded-lg shadow-xl">
        <h1 class="block text-xl font-bold leading-normal font-sans">ユーティリティ・ファースト</h1>
        <p class="block text-base font-normal leading-relaxed font-sans">プリミティブなユーティリティの固定されたセットから複雑なコンポーネントを構築します。</p>
    </div>
    <script src="app.js"></script>
</body>
</html>
```

こんな感じで、まだ何もCSSを書いていないですが、スタイルが適用されたWebページが見えるはずです。

<img width="789" alt="Screen Shot 2019-11-07 at 2.30.39.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/8033/789340b1-15f8-efec-05ec-1f26a2303221.png">

### Tailwind CSS の設定を変更してみる

Tailwind CSS は、設定ファイルでフォントファミリーやカラーリングなどの変更ができます。

```tailwind.config.js
module.exports = {
  theme: {
    fontFamily: {
      sans: ['"Sawarabi Gothic"', 'sans-serif'],
    },
    extend: {
      colors: {
        white: 'red',
      },
    }
  },
  variants: {},
  plugins: []
}
```

ビルドしてみると、HTMLもSCSSも変更していないのに、表示が変わったことが分かります。

<img width="789" alt="Screen Shot 2019-11-07 at 2.34.40.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/8033/5ed11a46-7a3b-3e4a-1695-ab7bbceb18d2.png">

### `@apply` を使ってみる

用意されたクラスを組み合わせることでも Tailwind CSS を使いこなせますが、`@apply` を使うことで、既存のCSSクラスや要素に対して Tailwind CSS で用意されているスタイルを使用することができます。

```dist/index.html
<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <title>Tailwind CSS Example</title>
    <link href="https://fonts.googleapis.com/css?family=Sawarabi+Gothic&display=swap" rel="stylesheet">
    <link rel="stylesheet" href="app.css">
</head>
<body>
    <div class="section">
        <h1>ユーティリティ・ファースト</h1>
        <p>プリミティブなユーティリティの固定されたセットから複雑なコンポーネントを構築します。</p>
    </div>
    <script src="app.js"></script>
</body>
</html>
```

```src/app.scss
@tailwind base;

@tailwind components;

body {
    @apply font-sans bg-gray-100;
}

.section {
    @apply max-w-sm mx-auto p-6 bg-white rounded-lg shadow-xl;

    h1 {
        @apply block text-xl font-bold leading-normal;
    }

    p {
        @apply block text-base font-normal leading-relaxed;
    }
}

@tailwind utilities;
```

先ほどと同じ見た目になればOKです。

<img width="789" alt="Screen Shot 2019-11-07 at 2.34.40.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/8033/5ed11a46-7a3b-3e4a-1695-ab7bbceb18d2.png">

### Purify CSS を有効にする

[公式ドキュメントにも記載のある](https://tailwindcss.com/docs/controlling-file-size)ように、Tailwind CSS はファイルサイズが大きいのが欠点です。ドキュメントでは Purgecss を使ったファイルサイズ節約法が載っていますが、今回は Laravel Mix で使える Purify CSS を使って、使われていないセレクタを削除し、ついでに Minify もかけてみます。

```webpack.mix.js
const path = require('path');
const glob = require('glob');
const mix = require('laravel-mix');
const tailwindcss = require('tailwindcss');

mix.js('src/app.js', 'dist/')
    .sass('src/app.scss', 'dist/')
    .options({
        processCssUrls: false,
        postCss: [ tailwindcss('./tailwind.config.js') ],
        purifyCss: {
            purifyOptions: {
                minify: true,
            },
            paths: glob.sync(path.join(__dirname, 'dist/*.html'))
        }
    });
```

コンパイルしてみると、使っていないCSSの記述が削除され、app.cssのファイルサイズが大幅に減りました。

とりあえず、これでコーディングはスタートできそうですね。

Tailwind CSS は弊社CTOが採用を推進しているので、知見がたまればまたぼちぼちメモを残していければと思います。