Fork me on GitHub
#clojurescript
<
2023-04-18
>
Joseph Graham04:04:20

Is there an elegant way to cycle through an HTMLCollection? Only idea I can think of is to re-implement the for (i = 0; i < coll.length; i++) way in Clojure.

grav04:04:32

You can use Array.from to create a js-array. From there you can do the usual map, for, doseq` etc.

cjohansen05:04:30

(extend-type js/NodeList
  ISeqable
  (-seq [array] (array-seq array 0)))
(extend-type js/HTMLCollection
  ISeqable
  (-seq [array] (array-seq array 0)))

👏 3
cjohansen05:04:06

Put this somewhere, and they can be used like any other collection

❤️ 2
🙀 4
👌 3
Joseph Graham05:04:36

I mean that should be included as standard

cjohansen05:04:23

It's one of the first things I include in any project

Joseph Graham05:04:10

I also always put

(defn byid
  "shortcut for getting element by id"
  [id]
  (.getElementById js/document id))

(defn byclass
  "shortcut for getting element by class"
  [name]
  (.getElementsByClassName js/document name))

p-himik07:04:39

Don't extend built-in types. Definitely don't do it if you're writing a library and probably avoid it if you're writing an app. It makes it way too easy to shoot yourself in the foot - and the gun might not even be in your hand. Or you could shoot someone else's foot off.

cjohansen07:04:31

For libraries this is a terrible approach, agreed. I use it all the time for apps.

Roman Liutikov11:04:13

As long as a collection implements JS Iterable protocol, coercing explicitly is not required, because cljs is able to unwind JS iterables since a couple of years now. I’d recommend to try to “seq” html collection or upgrade cljs version on your side if it’s too old.

👍 3
Roman Liutikov11:04:27

I’m pretty sure DOM objects are relying on iterables these days

Joseph Graham17:04:02

🙀 true! I can access it by

(doseq [v (seq elements)]
    (log v))

p-himik17:04:07

And you don't even need seq in there. :)

🙀 4
thheller06:04:53

array-seq also works, but beware that the underlying seq is mutable. so mutating the DOM while iterating may have unexpected results

teodorlu18:04:01

out of curiosity, what are people using for visualizing different states of UI components? 1️⃣ https://github.com/bhauman/devcards (cljs, #devcards) 2️⃣ https://storybook.js.org/ (js) 3️⃣ https://github.com/cjohansen/portfolio (cljs, #portfolio) 4️⃣ https://github.com/nubank/workspaces (cljs, #workspaces) 5️⃣ https://github.com/nextjournal/viewers/tree/main/modules/devcards (cljs) 6️⃣ https://github.com/nextjournal/clerk (clj/cljs, #clerk) 7️⃣ “I’m building my own” Not using a dedicated tool for that! other? please explain in thread!

1️⃣ 8
12
7️⃣ 9
2️⃣ 6
3️⃣ 2
isak19:04:32

Nothing yet 😬

teodorlu19:04:34

cool, added nubank/workspaces to the list!

teodorlu20:04:40

The list keeps growing 😄

phronmophobic20:04:01

One feature that seems like it would be useful is allowing users to spec the data a component accepts and automatically generate different variations. You could even have alternate generators similar to https://fakerjs.dev/guide/ to visually exercise a component. It doesn't seem like any of the listed options offer this. Has anyone tried something similar?

3
phronmophobic20:04:29

Where's the "I'm building my own" option in the poll?

7️⃣ 4
😁 4
🙏 2
teodorlu20:04:38

Is your work on your own thing public yet, @U7RJTCH6J?

cjohansen20:04:15

@U7RJTCH6J Interesting suggestion! Putting it on the Portfolio todo list 🙂

👍 2
🎉 2
phronmophobic20:04:32

Not yet. I'm still figuring things out. This poll is really useful. There's quite a lot of prior art that I wasn't aware of 😄

gratitude 2
cjohansen20:04:30

I built Portfolio to be extensible, this idea to have generative UI examples sounds like a very cool optional addon

🙌 1
cjohansen20:04:05

Could generate data for specs using test.check. And I’m guessing someone already made a ChatGTP topical lorem ipsum-generator? 😄

phronmophobic20:04:17

Yea, and there are libraries like faker.js that would let you produce examples in a more typical range (eg. addresses, names, profile images, icons, dates, emails, colors, etc.)

cjohansen20:04:53

Definitely will look into adding this, sounds super helpful

timrichardt20:04:23

"Not using a dedicated tool for that!" yet. Great idea, thank you!

🙌 4
lilactown22:04:14

Storybook is great for long-lived docs, but the separate build chain sucks. IMO there's a number of different use cases that you want to visualized different states of a component: 1. Docs: Engineering guide ("How do I build <type of experience>?") 2. Docs: Reference for eng/PM/design ("What does component <x> do?") 3. Development: Exploring ("I'm building component <x>, what does it do if I...?") 4. Development: Tests ("When I do <something>, does component <x> still do the expected thing?") (there could be more) I think things that are "card" or "story" centric, where you have code in a file that renders a component on a site somewhere in various states, can be OK for references (2) and tests (4) but poor for guides (1) and exploring (3). IMO exploring would be better addressed by an actual REPL that rendered a component on evaluation, and guides I don't even know, maybe storybook is OK for this since it just has a lot more features.

👍 4
phronmophobic23:04:51

@U4YGF4NGM, what's missing for 3)exploration? I can see how guides might want a different feature set, but exploring components in isolation seems useful.

lilactown23:04:34

I don't want to have to open another file and write up a card, that I'm going to then have to decide if I keep it or delete it, and navigate to that place in my browser. it's the difference between writing some forms out in a comment block inside the file I'm working in, versus creating and running tests. I want to be able to stay in the flow of working on my component in my editor, and be able to iterate and explore in an ad-hoc way

phronmophobic23:04:43

Would it help if the card metadata was next to the component in the source file? You could then have the viewer automatically create cards.

lilactown23:04:11

that might help

lilactown23:04:32

I'm obviously biased because I'm building my own tool 😄 I do intend to open source it some time in the future

😄 4
lilactown23:04:20

here's an example of the kind of workflow I want.

👀 2
💯 2
lilactown23:04:08

Clojure's super power is the REPL; any language that compiles to JS these days can reload files and reflect it in the browser. But we have forms!

lilactown23:04:26

This is just an example of the workflow, I think it could be accomplished in different ways. Rendering elements inside of a popup has issues, so I'm not sure if that's the final form of this tool. But it's the workflow that is important to me. I should be able to stay in the flow of my editor and isolate a single element or component and visualize it with as little ceremony as possible, just like when we evaluate functions at the REPL and can view their result without interrupting our flow to move to a different context

clojure-spin 9
💯 9
3