Fix select multiple default value (#3953)

* Fix select multiple default value

* Add a playwright test for select multiple
This commit is contained in:
Evan Almloff authored and GitHub committed 2025-04-07 17:28:26 -07:00
1 parent cbb91d694f
commit 5e9a505465
6 files changed
+73 -13

No files matched your search

+28 -10
View File
@@ -1,7 +1,12 @@
// A unified interface for setting attributes on a node
// this function should try and stay fast, if possible
export function setAttributeInner(node: HTMLElement, field: string, value: string, ns: string) {
export function setAttributeInner(
node: HTMLElement,
field: string,
value: string,
ns: string
) {
// we support a single namespace by default: style
if (ns === "style") {
node.style.setProperty(field, value);
@@ -11,7 +16,7 @@ export function setAttributeInner(node: HTMLElement, field: string, value: strin
// If there's a namespace, use setAttributeNS (svg, mathml, etc.)
if (!!ns) {
node.setAttributeNS(ns, field, value);
return
return;
}
// A few attributes are need to be set with either boolean values or require some sort of translation
@@ -53,18 +58,31 @@ export function setAttributeInner(node: HTMLElement, field: string, value: strin
node.innerHTML = value;
break;
// The presence of a an attribute is enough to set it to true, provided the value is being set to a truthy value
// Again, kinda ugly and would prefer this logic to be baked into dioxus-html at compiile time
default:
// https://github.com/facebook/react/blob/8b88ac2592c5f555f315f9440cbb665dd1e7457a/packages/react-dom/src/shared/DOMProperty.js#L352-L364
if (!truthy(value) && isBoolAttr(field)) {
node.removeAttribute(field);
} else {
node.setAttribute(field, value);
case "multiple":
setAttributeDefault(node, field, value);
// reset the selected value whenever multiple changes
// @ts-ignore
let options = node.options;
for (const option of options) {
option.selected = option.defaultSelected;
}
break;
default:
setAttributeDefault(node, field, value);
}
}
function setAttributeDefault(node: HTMLElement, field: string, value: string) {
// The presence of a an attribute is enough to set it to true, provided the value is being set to a truthy value
// Again, kinda ugly and would prefer this logic to be baked into dioxus-html at compile time
// https://github.com/facebook/react/blob/8b88ac2592c5f555f315f9440cbb665dd1e7457a/packages/react-dom/src/shared/DOMProperty.js#L352-L364
if (!truthy(value) && isBoolAttr(field)) {
node.removeAttribute(field);
} else {
node.setAttribute(field, value);
}
}
function truthy(val: string | boolean) {
return val === "true" || val === true;