diff --git a/app/javascript/controllers/duplicate_items_controller.js b/app/javascript/controllers/duplicate_items_controller.js index f341a20c61..e2b2e7632b 100644 --- a/app/javascript/controllers/duplicate_items_controller.js +++ b/app/javascript/controllers/duplicate_items_controller.js @@ -6,10 +6,10 @@ export default class extends Controller { connect() { this.boundHandleSubmit = this.handleSubmit.bind(this) this.element.addEventListener("submit", this.boundHandleSubmit) - + // Disable Rails UJS for this form to prevent "Saving" state this.element.removeAttribute('data-remote') - + // Remove data-disable-with from all submit buttons const buttons = this.element.querySelectorAll('input[type="submit"], button[type="submit"]') buttons.forEach(button => { @@ -23,9 +23,9 @@ export default class extends Controller { if (!this.itemSubmitButtonTargets.includes(submitter)) return event.preventDefault() - + const duplicates = this.findDuplicates() - + if (duplicates.length > 0) { this.showModal(duplicates, submitter.name) } else { @@ -100,10 +100,10 @@ export default class extends Controller { document.getElementById('duplicateItemsModal')?.remove() document.body.insertAdjacentHTML('beforeend', modalHtml) - + const modal = new bootstrap.Modal(document.getElementById('duplicateItemsModal')) modal.show() - + document.getElementById('confirmMerge').addEventListener('click', () => { this.mergeAndSubmit(duplicates, buttonName) }) @@ -115,29 +115,29 @@ export default class extends Controller { // Separate the first entry from remaining entries const [firstEntry, ...remainingEntries] = item.entries - + // Update the first entry with the merged total firstEntry.section.querySelector('input[name*="[quantity]"]').value = total - + // Remove all duplicate entries from the form submission remainingEntries.forEach(entry => entry.section.remove()) }) const modal = new bootstrap.Modal(document.getElementById('duplicateItemsModal')) modal.hide() - + this.submitForm(buttonName) } submitForm(buttonName) { this.element.removeEventListener('submit', this.boundHandleSubmit) - + const input = document.createElement('input') input.type = 'hidden' input.name = buttonName input.value = '1' this.element.appendChild(input) - + this.element.submit() } } diff --git a/app/javascript/controllers/kit_confirmation_controller.js b/app/javascript/controllers/kit_confirmation_controller.js new file mode 100644 index 0000000000..c086bc9e10 --- /dev/null +++ b/app/javascript/controllers/kit_confirmation_controller.js @@ -0,0 +1,98 @@ +import { Controller } from "@hotwired/stimulus" + +/** + * Connects to data-controller="kit-confirmation" on the new/edit Kit form. + * Shows a preview of the kit's name, value, and item composition when the + * user clicks Save, before the form is actually submitted. Composed with + * the (shared, kit-agnostic) duplicate-items controller: confirming here + * re-submits the form so duplicate-items can run its own check afterward. + */ +export default class extends Controller { + static targets = ["submitButton"] + + openModal(event) { + const submitter = event.currentTarget + + if (!this.submitButtonTargets.includes(submitter)) return + + event.preventDefault() + + this.showConfirmationModal(submitter) + } + + collectLineItems() { + const items = [] + + this.element.querySelectorAll('select[name*="[item_id]"]').forEach(select => { + const itemId = select.value + const itemText = select.options[select.selectedIndex]?.text + const section = select.closest('.line_item_section') + const quantityInput = section?.querySelector('input[name*="[quantity]"]') + const quantity = parseInt(quantityInput?.value) || 0 + + if (!itemId || itemText === "Choose an item" || quantity === 0) return + + items.push({ name: itemText, quantity }) + }) + + return items + } + + showConfirmationModal(submitter) { + const name = this.element.querySelector('#kit_name')?.value || '' + const value = parseFloat(this.element.querySelector('#kit_value_in_dollars')?.value || 0).toFixed(2) + const items = this.collectLineItems() + + const itemRows = items.map(item => + `