From dc7c0ff59974736846f8dd56ac88d04eca42244b Mon Sep 17 00:00:00 2001 From: Johannes Raggam Date: Fri, 17 Nov 2023 19:52:12 +0100 Subject: [PATCH 1/3] maint(pat subform): Modernize code. --- src/pat/subform/subform.js | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) diff --git a/src/pat/subform/subform.js b/src/pat/subform/subform.js index 053cbec9d..131831bcf 100644 --- a/src/pat/subform/subform.js +++ b/src/pat/subform/subform.js @@ -32,14 +32,14 @@ export default Base.extend({ }, scopedSubmit($el) { - var $form = $el.parents("form"), - $exclude = $form.find(":input").filter(function () { - return !$(this).is($el.find("*")); - }); + const $form = $el.parents("form"); + const $exclude = $form.find(":input").filter(function () { + return !$(this).is($el.find("*")); + }); // make other controls "unsuccessful" log.debug("Hiding unwanted elements from submission."); - var names = $exclude.map(function () { - var name = $(this).attr("name"); + const names = $exclude.map(function () { + const name = $(this).attr("name"); return name ? name : 0; }); $exclude.each(function () { @@ -63,8 +63,8 @@ export default Base.extend({ submit(ev) { ev.stopPropagation(); - var $this = $(ev.target), - $button = $this.find("button[type=submit][formaction]").first(); + const $this = $(ev.target); + const $button = $this.find("button[type=submit][formaction]").first(); if ($button.length) { $button.trigger("click"); } else { @@ -78,7 +78,7 @@ export default Base.extend({ if (ev.keyCode != 13) { return; } - var $subform = $(ev.target).parents(".pat-subform"); + const $subform = $(ev.target).parents(".pat-subform"); if (!$subform.is(".pat-autosubmit")) { return; } @@ -90,14 +90,14 @@ export default Base.extend({ ev.stopPropagation(); ajax.onClickSubmit(ev); // make sure the submitting button is sent with the form - var $button = $(ev.target), - $sub = $button.parents(".pat-subform").first(), - formaction = $button.attr("formaction"); + const $button = $(ev.target); + const $sub = $button.parents(".pat-subform").first(); + const formaction = $button.attr("formaction"); if (formaction) { // override the default action and restore afterwards if ($sub.is(".pat-inject")) { - var previousValue = $sub.data("pat-inject"); + const previousValue = $sub.data("pat-inject"); $sub.data("pat-inject", inject.extractConfig($sub, { url: formaction })); this.scopedSubmit($sub); $sub.data("pat-inject", previousValue); From 8252014a8bfc2f8da0a1e18b4b930e2abd3ed51b Mon Sep 17 00:00:00 2001 From: Johannes Raggam Date: Fri, 17 Nov 2023 19:51:56 +0100 Subject: [PATCH 2/3] fix(pat subform): Correctly unregister the submit event on Pattern destroy. --- src/pat/subform/subform.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/pat/subform/subform.js b/src/pat/subform/subform.js index 131831bcf..ac2f3e3f8 100644 --- a/src/pat/subform/subform.js +++ b/src/pat/subform/subform.js @@ -28,7 +28,7 @@ export default Base.extend({ }, destroy($el) { - $el.off("submit"); + events.remove_event_listener($el[0], "pat-subform--submit"); }, scopedSubmit($el) { From bd191548992aa04ececadf750b08e1821617540a Mon Sep 17 00:00:00 2001 From: Johannes Raggam Date: Fri, 17 Nov 2023 19:49:51 +0100 Subject: [PATCH 3/3] fix(core dom find_form, pat autosubmit): Add support for pat-subform. Subform was recently lost when introducing dom.find_form. Now subform support is back in pat-autosubmit. --- src/core/dom.js | 7 ++--- src/core/dom.test.js | 14 ++++++++++ src/pat/auto-submit/auto-submit.test.js | 36 ++++++++++++++++++++++++- 3 files changed, 53 insertions(+), 4 deletions(-) diff --git a/src/core/dom.js b/src/core/dom.js index 378809811..706b81c82 100644 --- a/src/core/dom.js +++ b/src/core/dom.js @@ -569,11 +569,12 @@ const element_uuid = (el) => { const find_form = (el) => { // Prefer input.form which allows for input outside form elements and fall // back to search for a parent form. - return ( + const form = + el.closest(".pat-subform") || // Special Patternslib subform concept has precedence. el.form || el.querySelector("input, select, textarea, button")?.form || - el.closest("form") - ); + el.closest("form"); + return form; }; const dom = { diff --git a/src/core/dom.test.js b/src/core/dom.test.js index 3bd03c90e..1283e8e29 100644 --- a/src/core/dom.test.js +++ b/src/core/dom.test.js @@ -1002,4 +1002,18 @@ describe("find_form", function () { const form = document.querySelector("#the-form"); expect(dom.find_form(el)).toBe(form); }); + + it("example 9 - subform support", function () { + // Subform support. Subforms have precedence over forms. + document.body.innerHTML = ` +
+
+ +
+
+ `; + const el = document.querySelector("button"); + const subform = document.querySelector(".pat-subform"); + expect(dom.find_form(el)).toBe(subform); + }); }); diff --git a/src/pat/auto-submit/auto-submit.test.js b/src/pat/auto-submit/auto-submit.test.js index 63cfe3b63..941512b22 100644 --- a/src/pat/auto-submit/auto-submit.test.js +++ b/src/pat/auto-submit/auto-submit.test.js @@ -187,7 +187,7 @@ describe("pat-autosubmit", function () { expect(submit_form_dispatched).toBe(true); }); - it("2.6 - when pat-autosubmit is defined not on aform element", async function () { + it("2.6 - when pat-autosubmit is defined not on a form element", async function () { document.body.innerHTML = `
+
+ +
+ + `; + const input = document.querySelector("input"); + const subform = document.querySelector(".pat-subform"); + const autosubmit = document.querySelector(".pat-autosubmit"); + new Pattern(autosubmit); + + // The submit event should be invoked on the subform. + let submit_subform_dispatched = false; + subform.addEventListener("submit", () => { + submit_subform_dispatched = true; + }); + + // The submit event should also bubble up to the form. + let submit_form_dispatched = false; + document.querySelector("form").addEventListener("submit", () => { + submit_form_dispatched = true; + }); + + input.dispatchEvent(events.input_event()); + await utils.timeout(1); + expect(submit_subform_dispatched).toBe(true); + expect(submit_form_dispatched).toBe(true); + }); }); describe("3 - Parsing of the delay option", function () {