are children not merged into props by default? or are we meant to do {:children value}
trying to do something like this:
(defnc txt [{:keys [children]] children)
(txt "Hello")
you’re calling txt
like a function
ah you’re right :face_palm: have to get used to not doing that
FWIW… it’s currently behind an experimental feature flag that I haven’t documented, but you can have defnc
create a factory function instead of a component if you want
(defnc txt
[{:keys [children]}]
{:helix/features {:define-factory true}}
children)
(txt "Hello")
(should work, haven’t tested that case specifically)
will try it out, thanks
before you mentioned that you couldn’t get that working with macros, did anything change?
I decided that if you want to explicitly enable it, you probably understand the differences between a factory function and a macro
the two biggest differences are that
• performance wise, the factory function will construct a hash map you pass in as props, not a JS object
• you can’t/don’t use &
for spread props
by props, you mean a cljs map of props, right? so does that mean we should still construct our primitive components with :define-factory false
but others ones we can just use factories
I’m not sure. what I mean is that:
(txt {:foo "bar"} "baz")
will not compile {:foo "bar"}
to a JS obj, but instead will actually do what it says: create a new CLJS map and pass it to the component.
the way that helix extracts passes these props and extracts them is smart. it will pass {:foo "bar"}
as a single React prop
(react/createElement #js {"helix/props" {:foo "bar"}} "baz")
and then when you read props in defnc
, it will check for that before defaulting to wrapping the whole props object in a bean:
https://github.com/Lokeh/helix/blob/master/src/helix/core.cljs#L125I’m not completely sure how this impacts performance
on the one hand, creating CLJS maps is more expensive than creating a JS obj. but by how much? ¯\(ツ)/¯
some people who are sensitive to code size might see more keywords created as well
anyway, I guess the only confusing thing people will really care about is that you can’t use &
hm, would it be possible for a component to know how it’s being called, so it could toggle :define-factory
appropriately?
i haven’t used macros much yet so no idea if that’s possible but i could see it being useful to decide that when you’re calling the component rather than upfront
^ by that I mean whether it’s being called by $
or as a regular function
I haven’t looked into it deeply, but it might be difficult
yea I imagine. might be best to just keep using $
😅
can confirm this works
👏
Good Day @lilactown, How are you? I ask me, What resources did you use to get to know Clojure as you know it now?, maybe you could give me any recommendation
hey Luis. I’ve been working with Clojure and ClojureScript for a couple years now, so time and experience is a lot of it!
I also have enjoyed watching the talks Rich Hickey and David Nolen have given over the years
mostly just keep experimenting, building software, and asking questions 🙂
Neat! Thank you!
if the second argument of helix’s use-effect hook is the body of a function, how is cleanup handled? I’m trying to get something like this working:
(h/use-effect
:always
(fn []
(js/console.log "starting...")
(fn []
(js/console.log "cleanup...."))))
ah, helix’s use-effect
doesn’t require you to wrap it in a 0-arity function
(h/use-effect
:always
(js/console.log "starting...")
(fn []
(js/console.log "cleanup..."))
oh ok, so last function returned is one that gets called for cleaning up. cool thanks