Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
51 changes: 27 additions & 24 deletions src/cljss/builder.clj
Original file line number Diff line number Diff line change
Expand Up @@ -8,30 +8,33 @@
(map? value)))

(defn build-styles [cls styles]
(c/reset-env! {:cls cls})
(let [pseudo (filterv utils/pseudo? styles)
nested (->> styles
(filterv (comp not utils/pseudo?))
(filterv utils/nested?))
[mstatic mvals] (some-> styles :cljss.core/media build-media)
styles (dissoc styles :cljss.core/media)
styles (filterv #(and (not (utils/pseudo? %)) (not (utils/nested? %))) styles)
[static vals] (c/collect-styles cls styles)
pstyles (->> pseudo
(reduce
(fn [coll [rule styles]]
(conj coll (c/collect-styles (str cls (subs (name rule) 1)) styles)))
[]))
nstyles (->> nested
(reduce
(fn [coll [rule styles]]
(conj coll (c/collect-styles (str cls " " rule) styles)))
[]))
vals (->> pstyles
(mapcat second)
(into vals)
(concat mvals)
(into []))
(let [rule-index 0
pseudo (filterv utils/pseudo? styles)
nested (->> styles
(filterv (comp not utils/pseudo?))
(filterv utils/nested?))
[mstatic mvals mrule-index] (some-> styles :cljss.core/media ((partial build-media cls rule-index)))
rule-index (or mrule-index rule-index)
styles (dissoc styles :cljss.core/media)
styles (filterv #(and (not (utils/pseudo? %)) (not (utils/nested? %))) styles)

[static vals rule-index] (c/collect-styles cls styles rule-index)
[pstyles rule-index] (c/collect-dynamic-styles
rule-index
pseudo
cls
(fn [rule] (subs (name rule) 1)))
[nstyles rule-index] (c/collect-dynamic-styles
rule-index
nested
cls
(fn [rule] (str " " rule)))

vals (->> pstyles
(mapcat second)
(into vals)
(concat mvals)
(into []))
vals (->> nstyles
(mapcat second)
(into vals))
Expand Down
54 changes: 30 additions & 24 deletions src/cljss/collect.clj
Original file line number Diff line number Diff line change
@@ -1,34 +1,40 @@
(ns cljss.collect
(:require [cljss.utils :refer [build-css]]))

(def env* (atom {:id 0
:cls nil}))

(defn reset-env! [v]
(reset! env* (merge {:id 0 :cls nil} v)))

(defn dynamic? [[_ value]]
(not (or (string? value)
(number? value))))

(defn varid [cls idx [rule]]
[rule (str "--var-" cls "-" idx)])

(defn collect-styles [cls styles]
(let [id (:cls @env*)
dynamic (filterv dynamic? styles)
static (filterv (comp not dynamic?) styles)
vars
(reduce
(fn [vars ds]
(let [ret (conj vars (varid id (:id @env*) ds))]
(swap! env* update :id inc)
ret))
[]
dynamic)
vals (mapv (fn [[_ var] [_ exp]] [var exp]) vars dynamic)
static (->> vars
(map (fn [[rule var]] [rule (str "var(" var ")")]))
(concat static)
(build-css cls))]
[static vals]))
(defn collect-styles
([cls styles rule-index] (collect-styles cls styles rule-index nil))
([cls styles rule-index tail-class]
(let [dynamic (filterv dynamic? styles)
static (filterv (comp not dynamic?) styles)
[vars rule-index] (reduce
(fn [[vars idx] ds]
(let [ret (conj vars (varid cls idx ds))]
[ret (inc idx)]))
[[] rule-index]
dynamic)
vals (mapv (fn [[_ var] [_ exp]] [var exp]) vars dynamic)
static (->> vars
(map (fn [[rule var]] [rule (str "var(" var ")")]))
(concat static)
(build-css (str cls tail-class)))]
[static vals rule-index])))

(defn collect-dynamic-styles [rule-index rules cls tail-class-g]
(loop
[idx rule-index
acc []
coll rules]
(if (not (seq coll))
[acc idx]
(let [[rule styles] (first coll)
[static vals nxt-idx] (collect-styles cls styles idx (tail-class-g rule))]
(recur nxt-idx
(conj acc [static vals])
(rest coll))))))
33 changes: 15 additions & 18 deletions src/cljss/media.clj
Original file line number Diff line number Diff line change
Expand Up @@ -234,44 +234,41 @@
(clojure.string/join " ")
(str "@media "))))

(defn compile-media-dispatch [styles]
(defn compile-media-dispatch [styles _ _]
(cond
(contains? styles :media) :media
(contains? styles :styles) :styles))

(defmulti compile-media #'compile-media-dispatch)

(defmethod compile-media :media [{media :media}]
(defmethod compile-media :media [{media :media} cls rule-index]
(->> (seq media)
(reduce
(fn [[sstyles svalues] [query styles]]
(let [[static values] (compile-media {:styles styles})
(fn [[sstyles svalues nxt-idx] [query styles]]
(let [[static values nxt-idx] (compile-media {:styles styles} cls nxt-idx)
query (-compile-media-query query)]
[(str sstyles query static) (concat svalues values)]))
["" []])))
[(str sstyles query static) (concat svalues values) nxt-idx]))
["" [] rule-index])))

(defmethod compile-media :styles [{styles :styles}]
(defmethod compile-media :styles [{styles :styles} cls rule-index]
(let [pseudo (filterv utils/pseudo? styles)
pstyles (->> pseudo
(reduce
(fn [coll [rule styles]]
(conj coll (c/collect-styles (str (:cls @c/env*) (subs (name rule) 1)) styles)))
[]))
[pstyles rule-index] (c/collect-dynamic-styles rule-index pseudo cls (fn [rule] (subs (name rule) 1)))

styles (filterv (comp not utils/pseudo?) styles)
[static values] (c/collect-styles (:cls @c/env*) styles)
[static values rule-index] (c/collect-styles cls styles rule-index)
values (->> pstyles
(mapcat second)
(into values))]
[(str "{" (apply str static (map first pstyles)) "}")
values]))
values
rule-index]))

(defn build-media [styles]
(compile-media {:media styles}))
(defn build-media [cls rule-index styles]
(compile-media {:media styles} cls rule-index))

(comment
(c/reset-env! {:cls "class"})

(build-media
"class"
{[[:only :screen :and [:min-width "300px"]]
[:print :and [:color]]]
{:font-size 'p
Expand Down
11 changes: 2 additions & 9 deletions src/cljss/sheet.cljs
Original file line number Diff line number Diff line change
Expand Up @@ -26,15 +26,8 @@
(throw (js/Error. (str "A stylesheet can only have " limit " rules"))))
(when-not (@cache cls-name)
(swap! cache conj cls-name)
(let [rule (if (ifn? rule) (rule) rule)
rules-count (gobj/get (gobj/get sheet "cssRules") "length")]
(if dev?
(dom/appendChild tag (dom/createTextNode rule))
(try
(.insertRule sheet rule rules-count)
(catch :default e
(when dev?
(js/console.warn "Illegal CSS rule" rule))))))))
(let [rule (if (ifn? rule) (rule) rule)]
(dom/appendChild tag (dom/createTextNode rule)))))
(flush! [this]
(-> tag
.-parentNode
Expand Down