Liveview: clear input and keep focus issue?

Liveview is so enticing – but I keep encountering some really weird things that keep hammering me down.

For instance, trying to write a multiselect dropdown with autosuggest:

I’d just like to clear the input field on a selection while maintaining focus on the element (so I can enter multiple values).

If I add an “id” attribute to the input: it keeps focus but won’t update the value in the input.
if i use just a “name” attribute: it updates the value but won’t keep focus.

I can bind other elements to the value i’d like to assign to the input, so I know the value is present and accessible during the render.

One other weirdness – in the Chrome inspector, the value I expect shows up in the inspected HTML as the value attribute for the input tag… but the rendered screen shows the old value…?!?

I now believe this is because LiveView blocks changes to inputs with focus – unless in the form submission process

so – does anyone know of a way to force an input update or trigger the phx-submit process manually?

This seems like a needed override in the library?

You may want to consider using a hook here?

Yeah, that’s probably my best hope, thanks!

I was hoping I could stay in Elixir to write a self-contained component. I think the requirement to work through the form via phx-submit for things like this pushes people to JavaScript – and makes it harder to write isolated Elixir code :frowning:

You can include form elements using JS Hooks which submit through phx-submit. Most of my form inputs are handled as pure Elixir LiveView components but my autocomplete dropdown component is a React component rendered by GitHub - fidr/phoenix_live_react: Render React.js components in Phoenix LiveView views · GitHub (which uses hooks). As long as the id and name are as Phoenix expects it works great validating through phx-validate (throttled by phx-debounce) and submitting through phx-submit!

It took a little work maintaining form state with some helper code to only render the changeset errors on first success or blur or attempted submit… but at this point it works smoothly with a LOT less code than the React SPA talking to REST or GraphQL endpointl

After implementing a simple chat/ demo application with LiveView, I noticed that the input where the user types the messages wasn’t resetting upon submission. This behavior seemed slightly different from the last time I used LiveView (at least in my memory), so I got a little bit confused at first…

I couldn’t find documentation on why this was happening, but this thread helped me understand how the focus was impacting the form submission.

So, if anyone by any chance encounters this thread as well, I’m going to leave this here for posterity: LiveView Tips and Tricks · GitHub. I’ve created a gist where I’ll be saving tips and tricks while I’m learning how to navigate LiveView workings.

BTW: This is the hook I configured that helped me solve the issue with the input not being cleaned:

/*
* Resets a input to a value when a form is updated by LiveView.
* Add phx-hook="FormReset" to the form and phx-reset="" to the input you want to reset.
* The attribute phx-reset must contain the value that the input value will be reseted to.
*/
Hooks.FormReset = {
  updated() {
    let input = this.el.querySelector('[phx-reset]:not(.invalid-feedback)')
    let value = input.getAttribute('phx-reset')
    input.value = value
  }
}

Is this not solved yet?
It’s really hard for a chat ui, where you are focused on the input. and liveview prevents updating of the focused input.

I believe this behaviour is by design to prioritize user experience and not override what they are currently inputting. An escape hatch would be to use a JS hook as prior comments here have shown examples of.

It’s such a common thing though there should be an easier way to opt-out.

  1. auto slugify
  2. chat input, needs to be cleared after form submission
  3. masked inputs
  4. etc

This is not the browser default behaviour it’s something that’s added by liveview without an easy escape hatch.

The easy escape hatch that hasn’t been mentioned is setting an ID on the input or form, and then changing that ID. Eg use a counter and if you want to reset the form you reset the changeset and increment the counter.