diff --git a/lib/hyperscript/runtime.sx b/lib/hyperscript/runtime.sx
index b3284eac..a356d826 100644
--- a/lib/hyperscript/runtime.sx
+++ b/lib/hyperscript/runtime.sx
@@ -1180,7 +1180,17 @@
(if
(host-get node "multiple")
(hs-select-multi-values node)
- (host-get node "value")))
+ (let
+ ((idx (host-get node "selectedIndex"))
+ (opts (host-get node "options"))
+ (raw-val (host-get node "value")))
+ (if
+ (and (not (nil? raw-val)) (not (= raw-val "")))
+ raw-val
+ (if
+ (and (not (nil? opts)) (>= idx 0))
+ (host-get (if (list? opts) (nth opts idx) (host-get opts idx)) "value")
+ "")))))
((or (= typ "checkbox") (= typ "radio"))
(if (host-get node "checked") (host-get node "value") nil))
(true (host-get node "value"))))))
diff --git a/shared/static/wasm/sx/hs-runtime.sx b/shared/static/wasm/sx/hs-runtime.sx
index b3284eac..a356d826 100644
--- a/shared/static/wasm/sx/hs-runtime.sx
+++ b/shared/static/wasm/sx/hs-runtime.sx
@@ -1180,7 +1180,17 @@
(if
(host-get node "multiple")
(hs-select-multi-values node)
- (host-get node "value")))
+ (let
+ ((idx (host-get node "selectedIndex"))
+ (opts (host-get node "options"))
+ (raw-val (host-get node "value")))
+ (if
+ (and (not (nil? raw-val)) (not (= raw-val "")))
+ raw-val
+ (if
+ (and (not (nil? opts)) (>= idx 0))
+ (host-get (if (list? opts) (nth opts idx) (host-get opts idx)) "value")
+ "")))))
((or (= typ "checkbox") (= typ "radio"))
(if (host-get node "checked") (host-get node "value") nil))
(true (host-get node "value"))))))
diff --git a/spec/tests/test-hyperscript-behavioral.sx b/spec/tests/test-hyperscript-behavioral.sx
index e739487b..8315a315 100644
--- a/spec/tests/test-hyperscript-behavioral.sx
+++ b/spec/tests/test-hyperscript-behavioral.sx
@@ -3817,11 +3817,15 @@
)
(deftest "converts multiple selects with programmatically changed selections"
(let ((_node (dom-create-element "form")))
- (dom-set-inner-html _node "")
- (let ((_result (eval-hs-locals "x as Values" (list (list (quote x) _node)))))
- (assert= (nth (host-get _result "animal") 0) "cat")
- (assert= (nth (host-get _result "animal") 1) "raccoon")
- ))
+ (dom-set-inner-html _node "")
+ (let ((_sel (dom-query _node "select")))
+ (let ((_opts (host-get _sel "options")))
+ (host-set! (nth _opts 0) "selected" false)
+ (host-set! (nth _opts 1) "selected" true)
+ (let ((_result (eval-hs-locals "x as Values" (list (list (quote x) _node)))))
+ (assert= (nth (host-get _result "animal") 0) "cat")
+ (assert= (nth (host-get _result "animal") 1) "raccoon")
+ ))))
)
(deftest "converts nested array as Flat"
(assert= (eval-hs "[[1,2],[3,4]] as Flat") (list 1 2 3 4))
diff --git a/tests/playwright/generate-sx-tests.py b/tests/playwright/generate-sx-tests.py
index c8205bcf..a8e9c586 100644
--- a/tests/playwright/generate-sx-tests.py
+++ b/tests/playwright/generate-sx-tests.py
@@ -128,6 +128,18 @@ SKIP_TEST_NAMES = {
# Manually-written SX test bodies for tests whose upstream body cannot be
# auto-translated. Key = test name; value = SX lines to emit inside deftest.
MANUAL_TEST_BODIES = {
+ "converts multiple selects with programmatically changed selections": [
+ ' (let ((_node (dom-create-element "form")))',
+ ' (dom-set-inner-html _node "")',
+ ' (let ((_sel (dom-query _node "select")))',
+ ' (let ((_opts (host-get _sel "options")))',
+ ' (host-set! (nth _opts 0) "selected" false)',
+ ' (host-set! (nth _opts 1) "selected" true)',
+ ' (let ((_result (eval-hs-locals "x as Values" (list (list (quote x) _node)))))',
+ ' (assert= (nth (host-get _result "animal") 0) "cat")',
+ ' (assert= (nth (host-get _result "animal") 1) "raccoon")',
+ ' ))))',
+ ],
"iterate cookies values work": [
' (hs-cleanup!)',
' (host-set! (host-global "cookies") "foo" "bar")',