読者です 読者をやめる 読者になる 読者になる

Arantium Maestum

プログラミング、囲碁、読書の話題

Clojure Web Development勉強 - Garden(その3)lein-gardenとfigwheelでgarden/CSS自動コンパイル&ロード

前々々回のfigwheelによるCSS自動ロードと前回のlein-gardenによるgarden→CSS自動コンパイルを合わせると、gardenデータ構造をcljファイルに記述・変更すると即時にブラウザで表示が更新されるような環境が出来上がる。

project.clj

leiningen及びlein-garden、figwheel、lein-cljsbuildへの指示は以下の通り:

(defproject figwheel-garden "0.0.1"
  :dependencies [[org.clojure/clojure "1.8.0"]
                 [org.clojure/clojurescript "1.9.293"]
                 [reagent "0.6.0"]
                 [garden "1.3.2"]]

  :plugins [[lein-cljsbuild "1.1.4"]
            [lein-figwheel "0.5.7"]
            [lein-garden "0.3.0"]]

  :garden
  {:builds [{:source-paths ["src"]
             :stylesheet figwheel-garden.styles/style
             :compiler {:output-to "resources/public/css/main.css"}}]}

  :figwheel
  {:css-dirs ["resources/public/css"]}

  :cljsbuild
  {:builds {:dev {:source-paths ["src"]
                  :figwheel true
                  :compiler {:output-to "resources/public/js/main.js"
                             :output-dir "resources/public/js/out/"}}}})

今回はgardenはfigwheel-garden.stylesという名前空間に定義していく。こちらは.cljファイルなのでfigwheelが間違ってJavaScriptコンパイルするようなこともない。

figwheelとcljsbuildの設定は前々々回どおり。(cljsbuildのcompilerオプションがデフォルトで:optimizations :noneにしてくれるので今回は横着して明示的に指示していない)

Reagentによるコンテンツの定義

core.cljsでいつもどおり文書のコンテンツを定義していく:

(ns figwheel-garden.core
  (:require
    [reagent.core :as r]))

(defn my-app []
  [:div
   [:h1 "Hello Reagent!"]
   [:p "Hello Garden!"]
   [:p.my-class "Hello My-Class!"]])

(r/render
  [my-app]
  (js/document.getElementById "app"))

とりあえず普通のHTMLタグと一緒に、my-classというclassのp要素も定義してある。

Styleの定義

GardenでHTML要素の見た目を定義:

(ns figwheel-garden.styles
  (:require
    [garden.def :refer [defstyles]]))

(defstyles style
  [:body {:background "#ddd"}]
  [:h1 {:color "#f00"}]
  [:p {:font "18px \"Century Gothic\", Futura, sans-serif"}]
  [:.my-class {:font-size "20px" :background "#ddf"}])

いつもながらセンスのないスタイル。

HTMLとディレクトり構造

index.htmlでCSSとJSを呼び出し。ReactがDOM要素を挿入するためのdiv#appも忘れずに作っておく。

<html>
    <head>
        <link href="css/main.css" rel="stylesheet" type="text/css">
    </head>
    <body>
        <div id="app"></div>
        <script src="js/out/goog/base.js"></script>
        <script src="js/main.js"></script>
        <script>goog.require('figwheel_garden.core')</script>
    </body>
</html>

上記4つのファイルをこんな感じのディレクトリ構造に配置する:

.
├── project.clj
├── resources
│   └── public
│       └── index.html
└── src
    └── figwheel_garden
        ├── core.cljs
        └── styles.clj

あとはlein garden autoとlein figwheelを、順番に別々のシェルウィンドウで実行し、ブラウザでlocalhost:3449を開けば環境設定完了。

これでcore.cljsとstyles.cljのどちらをいじっても、保存した時点で変更が自動的にブラウザに送られる。例えばmy-appのトップレベルの:divを:div.my-classに変えることで、my-app内の背景の色をすべて薄い青にしてみたり。簡単なことでもけっこう遊びがいがある。お試しあれ。

次回はこの設定を使ってgardenの構文などを探ってみる。

今回のコード:

gist.github.com