I have a LiveView form where an error message is displayed along with the form if the form was invalid. Pretty standard stuff. I am trying to implement a hook on this element to scroll to the top of the page when it is mounted. The hook is being called, it just won’t scroll the page. Is this a limitation? I’ve tried both this.el.scrollIntoView
as well as window.scrollTo(0, 0)
. Neither moves the page at all.
I just tried your code on a DOM element that appears conditionally and the window is scrolled to the top:
def mounted() { window.scrollTo(0, 0); }
Can you share more code?
Sure.
The element is:
<%= if @changeset.action do %>
<div
id="complaint-form-errors"
class="alert alert-danger"
phx-hook="formScrollToError">There was a problem saving this complaint!</div>
<% end %>
And the formScrollToError
hook is:
export const formScrollToError = {
mounted () {
window.scrollTo(0, 0);
}
} as Hook;
this looks fishy… can you make it look like:
https://hexdocs.pm/phoenix_live_view/Phoenix.LiveView.html#module-js-interop-and-client-controlled-dom
eg:
let Hooks = {}
Hooks.PhoneNumber = {
mounted() {
this.el.addEventListener("input", e => {
let match = this.el.value.replace(/\D/g, "").match(/^(\d{3})(\d{3})(\d{4})$/)
if(match) {
this.el.value = `${match[1]}-${match[2]}-${match[3]}`
}
})
}
}
let liveSocket = new LiveSocket("/live", Socket, {hooks: Hooks, ...})
I have a separate hooks script that imports all of the hooks and adds them.
The hook is definitely being called…if I change the content to alert("TESTING")
the alert appears when I would expect it to. It just won’t scroll the window for whatever reason.
If you open the browser’s dev console and manually run the command what happens?
Another idea: try calling it with a timeout and see if it makes a difference: setTimeout(() => { window.scrollTo(0,0) }, 1000)
That was a good thought! The timeout works. Strangely, it also works using setTimeout if the time is 0. I wasn’t going to be happy with a delay but as long as I can set the timeout to 0, it’s just a curiosity why it won’t work directly.
I appreciate the help.