forked from fixin.me/fixin.me
Stimulus controllers were reaching into Turbo.StreamElement.prototype to call disableElement/enableElement — tight coupling to Turbo internals. Extract both functions to app/javascript/element_helpers.js and import from there in application.js (which still assigns them to the Turbo prototype for server-driven Turbo Stream actions), details_controller, and readout_unit_controller. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
57 lines
1.5 KiB
JavaScript
57 lines
1.5 KiB
JavaScript
import { Controller } from "@hotwired/stimulus"
|
|
import { disableElement, enableElement } from "element_helpers"
|
|
|
|
export default class extends Controller {
|
|
static targets = ["countLabel", "submitButton", "list"]
|
|
|
|
connect() {
|
|
this._observer = new MutationObserver(() => {
|
|
this.element.dispatchEvent(new Event('change', { bubbles: true }))
|
|
})
|
|
this._observer.observe(this.listTarget, { subtree: true, attributeFilter: ['disabled'] })
|
|
}
|
|
|
|
disconnect() {
|
|
this._observer?.disconnect()
|
|
}
|
|
|
|
change() {
|
|
const count = this.element.querySelectorAll('input:checked:not([disabled])').length
|
|
if (count > 0) {
|
|
this.countLabelTarget.textContent = count + ' selected'
|
|
enableElement(this.submitButtonTarget)
|
|
} else {
|
|
this.countLabelTarget.textContent = this.countLabelTarget.dataset.prompt
|
|
disableElement(this.submitButtonTarget)
|
|
}
|
|
}
|
|
|
|
close(event) {
|
|
if (!event.relatedTarget ||
|
|
event.relatedTarget.closest("details") != this.element) {
|
|
this.element.removeAttribute("open")
|
|
}
|
|
}
|
|
|
|
processKey(event) {
|
|
switch (event.key) {
|
|
case "Escape":
|
|
if (this.element.hasAttribute("open")) {
|
|
this.element.removeAttribute("open")
|
|
event.stopPropagation()
|
|
}
|
|
break
|
|
case "Enter": {
|
|
const button = this.element.querySelector("button:not([disabled])")
|
|
if (button) {
|
|
button.click()
|
|
event.target.blur()
|
|
event.preventDefault()
|
|
event.stopPropagation()
|
|
}
|
|
break
|
|
}
|
|
}
|
|
}
|
|
}
|