shahryarjb

shahryarjb

When proposing or suggesting something please consider:

As my experience implementing getBoundingClientRect as Phoenix.LiveView.JS function and returns all the parameters of this JS function I mean (height, top, left and etc size) can be help full for complex client side component.

It keeps the ecosystem more clear and integrated. It can prevent the use of other client frameworks or js hook.


For example we have an accordion that is created with Phoenix component and Phoenix.LiveView.JS:

Show or open the accordion:

  def show_accordion_content(js \\ %JS{}, id) when is_binary(id) do
    js
    |> JS.show(to: "##{id}")
    |> JS.show(
      to: "##{id}-content",
      time: 500,
      transition:
        {
           "transition-all transform ease-out duration-300", 
           "will-change-[opacity] opacity-0 h-0",
           "will-change-auto opacity-100 h-[400px]"
        }
    )
  end

As you see I use hard coded height h-[400px] because browsers do not accept transition for h-auto, we have all the commands to open an accordion in Phoenix liveView as you see except some information about the element. It forces me to use hook or something like AlpineJS.

It can be an option for JS.show, JS.hide and (before or after doing operation) etc.

Thank you in advance


Refs:

First 10 of 16 Posts Switch mode

KP123

KP123

They actually do but it’s experimental technology and the how is subject to change. Here’s another tutorial. It’s worth pointing out that this has been possible for years already with CSS grid but it’s kinda hacky because you have to wrap the component in a grid.

shahryarjb

shahryarjb OP

I think adding a function for Phoenix.LiveView.JS to return getBoundingClientRect parameters can be very useful because this is going to be very cheap and has a good Browser compatibility. even it is used many times in Phoenix LiveView js source and fix all the problems.

An update for css will not come soon, and if it does, it will take a long time to be supported in all browsers

Link: Code search results · GitHub

KP123

KP123

FWIW I agree with you. I’ve been thinking for a while Phoenix could provide a sort of standard library for common JS functions. Another big one is updating whatever structure is tracking changes on the front end. Perhaps declaring default values and types like attrs in components but they can be manipulated by JS functions client side (with all the code written in LiveView/Elixir/Plug style). A use case for this is optimistic renders on form submissions.

My point with the comment above is more so for people interested in CSS that have yet to be exposed to modern capabilities

shahryarjb

shahryarjb OP

Based on my experience, if such things are not done especially (what you said) in the client side. People’s interest in bringing JS ecosystem frameworks is increasing.

And this is exactly the point where I have to say that like js, everyone creating something rather than solving the previous problem. I hope it doesn’t happen like this

KP123

KP123

I’m imagining something like Alpine but instead of updating the DOM directly it updates dynamic assigns on LiveViews existing change tracker, and then LiveView updates the DOM like normal.

shahryarjb

shahryarjb OP

I do not want to send from server to client, I need some tools client to client even have a global state for client or access to service worker client to client etc

garrison

garrison

The JS commands are pre-computed and transformed into a JSON format (you can literally see it in the DOM). There is no mechanism to send information from the client back to the server to re-compute the JS command with the bounding rect, and doing so would represent a substantial increase in both complexity and latency (two round trips to render).

You could instead redesign JS commands to support some sort of variable system, which would again be a substantial increase in complexity and in the limit would inevitably converge on a turing complete system (i.e. JS commands would become an ad-hoc programming language), which sounds to me like a very bad idea. We already have a programming language for the client (JavaScript).

I think a much better path forward would be to continue to improve hooks for use cases like these. In particular, I don’t understand why there’s no good API for setting sticky attributes/classes the way JS commands do via the client-side hooks APIs. There is a somewhat-hacky way to do it (which I have used, and it works) by executing a pre-computed JS command stored in an attribute but I think we could do a lot better than that :slight_smile:

P.S. You should just use the grid trick for this, I’ve used it extensively and it works just fine with JS.toggle_class. You don’t even need the JS transition for this, you can just use CSS (the element never leaves the DOM).

shahryarjb

shahryarjb OP

Hmmm, I did not understand much. I am looking for the client-to-client part, not to the server.

But … Can you create just with css, this accordion open and close? very slow and smooth effect? Accordion | Mantine

If yes please share the code!

garrison

garrison

I did not elaborate because the grid trick in question was linked above :slight_smile: Here is a StackOverflow question with more details:

Honestly you probably could find a way to do it with radio buttons and pure CSS, but I wouldn’t. What I meant was that the animation can all be done with CSS (no JS.transition needed), and then all you need is JS.toggle_class to trigger the CSS animations.

First, you wrap each item in a grid container, and then you use CSS to toggle grid-template-rows between 0fr and 1fr. You set overflow: hidden on the child (the accordion content in your case) so that it’s not visible when closed.

The CSS would look like this:

.container {
  display: grid;
  grid-template-rows: 0fr;
  transition: grid-template-rows 100ms;
}
.container.open {
  grid-template-rows: 1fr;
}

.content {
  overflow: hidden;
}

The HEEx would look like this:

<div>
  <div class="container" phx-click={@open}>
    <div class="content">Foo</div>
  </div>
  <div class="container" phx-click={@open}>
    <div class="content">Bar</div>
  </div>
</div>

And then, if you want all of the other items to close when you open one, you would do this (otherwise you could just use JS.toggle_class("open")):

open =
  JS.remove_class("open", to: ".container.open")
  |> JS.add_class("open")

This is just a minimal demonstration of the mechanism, obviously you would also need some sort of title for each item to actually click on :slight_smile:

sezaru

sezaru

Yes, In the last month I was wondering the same (and was thinking about creating a proposal to add that). I created a local fork of live view locally where I exposed the sticky API in the socket to try it out and that made my hooks way easier to implement and reason about.

For me it seems like a win-win situation, but maybe there is some corner case that I’m not aware that would justify not exposing it. Maybe some dev from the LiveView team could bring more light to this.

I love LiveView, but I have to admit that, in my experience, it is a pain and hard to get it right when you need to create some more “complex” components with the current hook solution.

Where Next? Top

Trending in Proposals: Ideas Top

Other Trending Topics Top

JesseHerrick
Hey, I’m Jesse and I’m the main contributor behind Dexter, a full-featured, lightning-fast Elixir LSP optimized for large codebases. It s...
New
jimsynz
Beam Bots (or just BB for short) is a framework for building fault-tolerant robotics applications in Elixir using familiar OTP patterns. ...
New
Damirados
Hello everyone. After busy few months I am happy to announce v0.1.0 of Emerge &amp; Solve. They are GUI (Emerge) and State management (S...
New
netoum
Corex is an accessible, unstyled UI component library for Phoenix that integrates Zag.js state machines using Vanilla JavaScript and Live...
New
ausimian
Emily is an Elixir library that runs Nx computations on Apple’s MLX. Install it as the default Nx backend and Nx, defn, Axon, Nx.Serving,...
New
juhalehtonen
There has been a thread to discuss the Stack Overflow Developer Survey on this forum every year since 2018, so here’s yet another one for...
New

We're in Beta

About us Mission Statement