Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Garden Generated Inline-styles in Reagent's Hiccup

In reagent, one can specify inline CSS styles like this:

[:div {:style {:border "1px solid red"}} "My Text"]

garden can make such CSS properties containing several values in a list more generic. Vectors for comma separated lists and nested vectors (used here) for space separated lists:

(require '[garden.core :refer [style]])

(style {:border [[:1px :solid :black]]})
;= "border: 1px solid red;"

How can those things be combined? Reagent seems to be stubborn only accepting hash-maps for the style attribute. Accepting a string as well would be a solution here.

Generally, of inline-styles aren't a good choice in a long term. So one could solve that by attaching a class to the div and by specifying its style globally by gardens css function.

Class Example:

[:div.myclass "My Text"]

(css [:.myclass {:border [[:1px :solid :black]]}])
;= ".myclass {\n  border: 1px solid black;\n}"

However, sometimes it's good to start with inline styles, so: Is there a way to do it the way that is described above?

like image 718
Anton Harald Avatar asked Oct 30 '22 04:10

Anton Harald


1 Answers

The hash-map that can optionally be supplied to reagent's hiccup vectors is basically an abstraction over the HTML attributes of the specified html element. (As they are represented in the DOM) Additionally another hash-map can be nested when attached to the keyword :style. This is an abstraction of the element's style properties. Which is a different thing that the one above. For that reason one could argue that those two things would have better been kept apart, however it simpler like this in another way.

Manipulating an element's style properties by setting it's style attribute would mean that the whole style string has to be parsed when only one part changes. So having an extra-option for providing a style-string in hiccup wouldn't help that much.

It looks like garden can only render to strings. I'd suggest it could be helpful if it would also render to a hash-map.

Here however is a workaround, that lets reagent and garden work together:

(defn css-map [s]
  (->> (style s)
       (re-seq #"(.*): (.*);(?:\n|$)")
       (reduce (fn [m [_ k v]]
                 (assoc m k v))
               {})))

(css-map {:border [[:1px :solid :red]]
          :background-color (rgb 33 5 0)})
;= {"border" "1px solid red", "background-color" "#210500"}

The performance will suffer from this of course. If someone knows a better solution, I'd still be curious to know.

like image 175
Anton Harald Avatar answered Nov 09 '22 21:11

Anton Harald