Clojurians
# om

This page is not created by, affiliated with, or supported by Slack Technologies, Inc.

sophiago 02:18:04

@levitanong almost certain i would actually bypass all the svg parts for this and go straight canvas. tho still makes sense to use a library rather than thinking i could do charting by hand if that's what you mean. having looked into recharts, it seems ideal

sophiago 02:23:04

anyway, i went through the om-next tutorial yesterday and really love it. not only does it seem to fit the way i use react perfectly, but the backend integration should end up being amazing when it reaches that

sophiago 02:23:57

i am wondering if there's a way to add inline styles to defui? i don't see it in the documentation, but would imagine so

cjmurphy 02:27:09

@sophiago: this is some work done on mixing styles with om: https://github.com/untangled-web/om-css. I haven't looked at it myself, just know of it.

sophiago 02:28:09

oh...that's the meetup i decided to skip that's going on literally right now...

sophiago 02:28:20

untangled?

keatondunsford 02:28:24

That’s awesome. No more massive styling lines like in regular React components.

sophiago 02:29:01

at first i thought it was a general full stack clojure thing then realized i probably wouldn't be using their modules

keatondunsford 02:29:01

Here are the regular Facebook docs for React component styling:
https://facebook.github.io/react-native/docs/style.html

sophiago 02:29:19

that's react native

sophiago 02:29:40

i use in-line styles with createElement always. it's fine

sophiago 02:29:50

i figured it would be part of the defui macro, but i guess not?

sophiago 02:31:04

that's a huge deal for me...it's what allows you to map a factory pattern to locations in the viewport

keatondunsford 02:32:21

Oops I thought that was React. Same concept though.

keatondunsford 02:32:25

Unless you just use regular CSS.

sophiago 02:32:45

uh...that defeats the purpose of factories though

keatondunsford 02:32:55

Yeah totally.

keatondunsford 02:33:27

I think the components are the same though. I’ve definitely seen styling in Om stuff somewhere. Or maybe it was Reagent.

sophiago 02:33:31

since in om-next everything has to be a factory then how is it imagined you position them without some amount of inline styles?

keatondunsford 02:33:35

Sorry I’m not being very helpful :stuck_out_tongue:

sophiago 02:34:23

yeah, i'm in the om channel

sophiago 02:34:33

not developing javascript apps for mobile

sophiago 02:34:36

or whatever else

sophiago 02:36:04

i would imagine you can just do this with om-next and it hasn't been documented yet because it's in alpha

sophiago 02:36:31

something like {:style :top "100px"}

keatondunsford 03:36:37

I literally think it’s just something like this:

(defui AppRoot static om/IQuery (query [this] '[:app/msg]) Object (render [this] (let [{:keys [app/msg]} (om/props this)] (view {:style {:flexDirection "column" :margin 40 :alignItems "center"}} (text {:style {:fontSize 30 :fontWeight "100" :marginBottom 20 :textAlign "center"}} msg) (image {:source logo-img :style {:width 80 :height 80 :marginBottom 30}}) (touchable-highlight {:style {:backgroundColor "#999" :padding 10 :borderRadius 5} :onPress #(alert "HELLO!")} (text {:style {:color "white" :textAlign "center" :fontWeight "bold"}} "press me"))))))

keatondunsford 03:38:04

I know that’s for React Native via Re-Natal (#cljsrn), but I’m almost positive the Om.Next components are the same for web because both React and React Native use JSX and its built-in styling I believe.

keatondunsford 03:38:26

But I’m probably crazy. I’d just say play with it until the documentation comes out like you said.

keatondunsford 03:38:55

Hope it works.

sophiago 03:47:36

that works for you? i was thinking something like that, but ending up needlessly tinkering with my config instead for a while

sophiago 03:47:40

:confused:

sophiago 03:51:37

@keatondunsford i'm getting a bunch of errors on my first pass through this. not sure how much is really specific to om-next?

keatondunsford 03:52:12

Let me try messing with the source in the Om Tutorial and see if anything works.

keatondunsford 03:52:20

I might be totally wrong but just trying to help.

sophiago 03:52:51

@sophiago uploaded a file: Untitled

sophiago 03:53:13

no, i'm saying i doubt my errors are from the css part

sophiago 03:53:23

i'm new to om in general

sophiago 03:53:36

so might be obvious

sophiago 03:54:22

oh, wow. tired...i didn't edit the map values

sophiago 03:54:44

but the errors shouldn't be specific to that. lo

sophiago 04:07:52

ok...i edited that snipped make myself seem slightly less brain dead

sophiago 04:08:31

i'm not getting any errors...it's just not rendering. pretty usual story for first pass through a framework after the tutorial :stuck_out_tongue:

sophiago 04:10:07

may have to wait for the morning crowd

keatondunsford 04:11:25

Yeah totally. The code I shared has React-Native specific UI variables like View and Touchable-Highlight. I was only pointing it out for the syntax as it related to how the maps worked and stuff.

sophiago 04:11:53

that's fine. it was pretty much how i was imagining

sophiago 04:12:09

as mentioned, guessing my problems are due to other things

sophiago 04:12:31

not sure how reconcilers work, for example

keatondunsford 04:12:39

Basically what I was getting at was if you looked at the React docs for the right vars to style your JSX (or Om equivalent), and then just copied the order of things, it might work. But idk

sophiago 04:14:20

this looks about right to me

sophiago 04:14:26

there are a few things i'm uncertain of

sophiago 04:16:16

mainly the reconciler and using add-root! for that as well as js to render instead of using another defui. i've been shown the latter both ways

sophiago 04:17:16

@anmonteiro was very helpful pointing me in the right direction with factories so perhaps i'll catch him when timezones line up

keatondunsford 04:17:42

Yeah he’s the man

keatondunsford 04:18:01

What project are you working on? Curious:)

sophiago 04:19:45

right now just porting some components from js. eventually realtime financial charting, although i think the client i'm contracting for is delaying it :confused:

sophiago 04:21:10

it's too bad because i know i'll kill it on benchmarks, we have prior work history together that can't be beat, and my hope is this will lead to a permanent job, but seems that's really entirely dependent on his success more than my ability...and i'm just not used to being in that position

sophiago 04:23:35

although i also think he imagines paying me much more than i'd accept if we were negotiating so it's kind of hilarious in that sense

keatondunsford 04:28:56

That’s awesome!! I hope you get it. All this Om mastery will just up your chances like crazy if you can wow him with Lispiness.

sophiago 04:33:07

it's really not that... i wanted to close the deal based on benchmarking it being magnitudes faster than his previous code, but very clearly he's already sold on me and just doesn't need the frontend immediately and also wouldn't pay someone less than what he deemed standard. where we used to work payed developers a shitload (i wasn't a developer there...) and is basically in a startup phase although not in an industry that depends on investor capital. so it's a timeframe thing mainly and further off than i was hoping

sophiago 04:33:14

but i can still use this for plenty of my own stuff

sophiago 04:34:39

i just ported peter henderson's picture language to clojure for canvas interop, which was rather difficult due to the nature of functional code and hardware graphics apis. it's super boring right now drawing stick men though so i had planned to do some react stuff with it

sophiago 04:34:59

so that's one example

keatondunsford 04:35:14

That’s legit.

sophiago 04:36:22

i'd love some people to clone it...

sophiago 04:36:42

i didn't even put up the project file tho

sophiago 04:36:48

i was really tired that day

sophiago 04:37:27

will hopefully clean up the repo this week and add an example with om :slightly_smiling_face:

hlolli 10:04:46

@mitchelkuijpers yes, ctrl+click is lost. Wow, I needed to know this fact! Thanks, be shameless about possible bad practices that I may let out here :slightly_smiling_face:

mitchelkuijpers 10:05:16

I will :slightly_smiling_face: @hlolli

anmonteiro 11:13:17

@sophiago: props needs to be a JS object. E.g: (dom/div #js {:className "foo" :style #js {:color "red"}})

sophiago 17:13:54

@anmonteiro ah, thanks. i fixed that, but still think i must be doing something wrong with rendering here?

sophiago 17:14:11

@sophiago uploaded a file: Untitled

anmonteiro 17:14:51

@sophiago your render code doesn't look correct

sophiago 17:15:03

yeah, i was confused between different examples

sophiago 17:15:08

so figured that must be it

anmonteiro 17:15:24

```

(defui slider Object (render [this] (dom/input #js {:type "range" :id (get (om/props this) :id) :min 5 :max 100 :step 1 :style #js {:width "360px" :left (get (om/props this) :left) :top (get (om/props this) :top) :position "absolute"} :onChange (fn [e] (swap! num-sliders assoc :n e.target.value))}))) ```

anmonteiro 17:16:04

(you need to include a key for the :id)

anmonteiro 17:16:19

and I spliced :onChange too

sophiago 17:16:28

ah, and probably the styles as well

anmonteiro 17:16:37

yeah, I didn't see that

anmonteiro 17:18:01

also, (get (om/props this) :x) becomes repetitive. I would do (let [{:keys [id left top]} (om/props this)])

anmonteiro 17:18:04

but that's just nitpicking

sophiago 17:22:00

wait, you didn't just mean that render did you? i assumed the factory render at the end? because i still don't see anything

sophiago 17:22:34

i had seen that part done with js interop and also in a separate defui was what i meant

atdixon 17:23:09

om.next app design question

  • my defui component renders based on window properties like scroll position and width/height etc--i imagine this is a very common thing for ppl to do
  • it seems silly to capture these and try to manage the state yourself--given that the browser's already doing the job!
  • ...but which means instead of updating your state on resize/scroll/etc events, you instead simply need to call (.forceUpdate this)

does this sound like the right approach/idiomatic way to render based on dynamic browser window properties?

anmonteiro 17:25:13

@sophiago oh I didn't even see that part :slightly_smiling_face:

anmonteiro 17:25:28

yeah you don't want to js/ReactDOM.render

anmonteiro 17:25:35

add-root! will do it for you

sophiago 17:27:54

because right now it's like i'm rendering to two parent elements

anmonteiro 17:28:27

you'll want an explicit Root component too

anmonteiro 17:28:42

what you're passing to ReactDOM.render should be its own defui that you pass to add-root!

sophiago 17:39:39

so it's as simple as having the generator for my factory as its own defui and then adding that as the root component, right?

anmonteiro 17:40:14

should be, unless you're doing something else not quite right that I haven't seen :slightly_smiling_face:

sophiago 17:40:35

ha, maybe...

sophiago 17:40:39

let me update

sophiago 17:42:19

okay, updated the snippet above. must be doing something else wrong

anmonteiro 17:43:19

probably (range :state) should be (range (:n @num-sliders))?

anmonteiro 17:43:59

or :n should even be in props

sophiago 17:44:07

ah, see i just ran through the quickstart and was unsure how reconcilers worked. i thought part of it was managing state so you didn't need an explicit call like that

anmonteiro 17:44:34

you don't, it should be in props

sophiago 17:44:35

oh, it does... i just want the actual value

sophiago 17:57:30

hmm.. well that doesn't seem to be it

sophiago 17:57:58

(sorry, moving a little slowly because today is the day everyone in my country is going a little off...woman got pushed in front of the subway right near me? people think it could be the end of the world)

sophiago 19:08:06

@anmonteiro i feel bad bothering, but tried recompiling figwheel even and can't tell what i'm doing wrong with this first component since i'm not even getting error messages...just no rendering :stuck_out_tongue:

sophiago 19:08:23

@sophiago uploaded a file: Untitled

anmonteiro 19:09:03

@sophiago (range :n) = ()

anmonteiro 19:09:05

empty list

anmonteiro 19:09:18

you probably want (range (:n (om/props this)))

anmonteiro 19:09:28

:n is just a keyword

sophiago 19:09:29

that's what you meant

sophiago 19:09:37

and same for the others

sophiago 19:09:40

okay lemme see

sophiago 19:15:19

okay...getting something, errors from figwheel and an infinite loop. good sign at least :slightly_smiling_face: seems to possibly be due to string conversion inside props instead of the UI component itself

sophiago 19:24:31

huh, fixed that and back where i started. looking in the chrome devtools inspector now to see if i'm missing something and should be breaking this down further

sophiago 19:28:17

ah, ok. it's my call to js/window.innerWidth and js/window.innerHeight that are bad syntax

sophiago 19:34:20

i think om.next got me thinking back in terms of prototypal syntax because of how it mixes some things up, but then i also got the sense that wiki is a work in progress and some of that js interop has been supplanted as best practice (like how i was initially rendering...guessing you probably don't want to do that even in the simplest cases where it works fine?)

sophiago 19:38:50

bam, got it :slightly_smiling_face:

sophiago 19:39:09

thanks @anmonteiro !

anmonteiro 19:39:33

np, glad it works

sophiago 19:40:02

two fairly trivial follow-ups if you don't mind:

sophiago 19:40:11

i get one error i think i can ignore?

sophiago 19:40:34

"react.inc.js:20483 Warning: Constructor is changing an uncontrolled input of type range to be controlled. Input elements should not switch from uncontrolled to controlled (or vice versa). Decide between using a controlled or uncontrolled input element for the lifetime of the component."

anmonteiro 19:41:29

I think you just need to provide a :value to the input

sophiago 19:41:53

oh, yeah i think in porting it i omitted an init value

sophiago 19:42:15

that's a shitty error message though

anmonteiro 19:43:07

yeah, take it up with the React people :slightly_smiling_face:

sophiago 19:43:37

ha. they could start by writing a tutorial that's accurate as of two years ago for starters

sophiago 19:43:47

considering they're at a what? 300bb company?

anmonteiro 19:44:37

I think they just revamped the docs a few days/weeks ago

sophiago 19:44:47

wow...never thought i'd see the day

sophiago 19:45:05

i mean, their api docs are fine. it's the tuts people coming straight to it use that were that old

sophiago 19:45:38

just the bar for open source is continually lowered i think at those large companies, for which i'd blame zero open source apple

sophiago 19:45:59

react was only open by accident when they bought instagram and it had a different backend

sophiago 19:46:20

now it's the best thing out there...

sophiago 19:46:59

anyway, my second question was not particular to om, so feel free if you don't have an answer offhand. but i'm wondering about the ideal way to benchmark cljs vs. js, obviously because i'd like to compare this to the js version

sophiago 19:54:14

oh, i guess maybe i should also ask you as a contributor: one thing i'll probably want to port to om.next in a bit is a react component for hot swapping glsl shaders from template literals so should probably check whether something like that already exists and then if not if it would be something worth integrating to the library or how that would even work? or just as an example maybe? it's basically just a utility component and then i've toyed with doing actual glsl bindings for clojurescript, which i know some other people have been at various stages of working on as well. not sure whether i'd want to undertake that latter part, though

sophiago 20:06:05

ah, and see there's a problem with specifying :value in the UI element because it essentially acts as its own constructor? in general since i start with a certain number in the atom those don't track the rest due to that. i can't imagine i'm explaining this well, but can't think of a better way without digging into how om.next wraps the react api, which i'd rather not because i'm quite pleased in having gone this route over the reagant api directly