diff options
-rw-r--r-- | lib/js/urweb.js | 101 | ||||
-rw-r--r-- | src/monoize.sml | 39 | ||||
-rw-r--r-- | tests/dtable.ur | 6 | ||||
-rw-r--r-- | tests/dtable.urp | 3 | ||||
-rw-r--r-- | tests/dtable.urs | 1 |
5 files changed, 77 insertions, 73 deletions
diff --git a/lib/js/urweb.js b/lib/js/urweb.js index dd66b55e..4d8418b6 100644 --- a/lib/js/urweb.js +++ b/lib/js/urweb.js @@ -228,79 +228,87 @@ function parent() { } function addNode(node) { - if (thisScript) { - thisScript.parentNode.appendChild(node); - thisScript.parentNode.removeChild(thisScript); - } else { + if (thisScript) + thisScript.parentNode.replaceChild(node, thisScript); + else lastParent().appendChild(node); - } } -function setHTML(html) { - var x = document.createElement("span"); - x.dead = false; - x.signal = null; - x.sources = null; - x.closures = null; - x.innerHTML = html; - addNode(x); - runScripts(x); -} - var thisScript = null; function runScripts(node) { - var savedScript = thisScript; - - var scripts = node.getElementsByTagName("script"), scriptsCopy = []; - var len = scripts.length; - for (var i = 0; i < len; ++i) - scriptsCopy[i] = scripts[i]; - for (var i = 0; i < len; ++i) { - thisScript = scriptsCopy[i]; - try { - eval(thisScript.textContent); - } catch (v) { - doExn(v); + if (node.getElementsByTagName) { + var savedScript = thisScript; + + var scripts = node.getElementsByTagName("script"), scriptsCopy = []; + var len = scripts.length; + for (var i = 0; i < len; ++i) + scriptsCopy[i] = scripts[i]; + for (var i = 0; i < len; ++i) { + thisScript = scriptsCopy[i]; + try { + eval(thisScript.textContent); + } catch (v) { + doExn(v); + } + if (thisScript.parentNode) + thisScripts.parentNode.removeChild(thisScript); } - } - thisScript = savedScript; + thisScript = savedScript; + } } // Dynamic tree entry points function dyn(s) { - var x = parent(); + var x = document.createElement("div"); + x.style.display = "inline"; x.dead = false; x.signal = s; x.sources = null; x.closures = null; + + var first = null; + x.recreate = function(v) { for (var ls = x.closures; ls; ls = ls.next) freeClosure(ls.data); - var doKind = function(kind) { - var arr = x.getElementsByTagName(kind); - for (var i = 0; i < arr.length; ++i) { - var span = arr[i]; - span.dead = true; - for (var ls = span.sources; ls; ls = ls.next) - ls.data.dyns = remove(span, ls.data.dyns); - for (var ls = span.closures; ls; ls = ls.next) - freeClosure(ls.data); + for (var node = first; node && node != x; ) { + if (node.getElementsByTagName) { + var arr = node.getElementsByTagName("div"); + for (var i = 0; i < arr.length; ++i) { + var span = arr[i]; + span.dead = true; + for (var ls = span.sources; ls; ls = ls.next) + ls.data.dyns = remove(span, ls.data.dyns); + for (var ls = span.closures; ls; ls = ls.next) + freeClosure(ls.data); + } } - }; - doKind("span"); - doKind("tbody"); + var old = node; + node = node.nextSibling; + old.parentNode.removeChild(old); + } var cls = {v : null}; - x.innerHTML = flatten(cls, v); + var dummy = document.createElement("table"); + dummy.innerHTML = flatten(cls, v); x.closures = cls.v; - runScripts(x); + runScripts(dummy); + + for (first = dummy.firstChild; first && first.tagName == "TBODY"; first = first.firstChild); + for (var node = first; node; ) { + var old = node; + node = node.nextSibling; + x.parentNode.insertBefore(old, x); + } }; + + addNode(x); populate(x); } @@ -310,8 +318,8 @@ function input(t, s, recreate) { x.signal = ss(s); x.sources = null; x.recreate = recreate(x); - populate(x); addNode(x); + populate(x); return x; } @@ -332,7 +340,6 @@ function sel(s, content) { sv(s, x.value); x.onchange = function() { sv(s, x.value) }; - return x; } diff --git a/src/monoize.sml b/src/monoize.sml index 488f3b20..f0491198 100644 --- a/src/monoize.sml +++ b/src/monoize.sml @@ -2646,24 +2646,11 @@ fun monoExp (env, st, fm) (all as (e, loc)) = | "dyn" => (case attrs of [("Signal", e, _)] => - let - val inTable = case targs of - (L.CRecord (_, ctx), _) :: _ => - List.exists (fn ((L.CName "Table", _), _) => true - | _ => false) ctx - | _ => false - - val tag = if inTable then - "tbody" - else - "span" - in - ((L'.EStrcat - ((L'.EPrim (Prim.String ("<" ^ tag ^ "><script type=\"text/javascript\">dyn(")), loc), - (L'.EStrcat ((L'.EJavaScript (L'.Script, e), loc), - (L'.EPrim (Prim.String (")</script></" ^ tag ^ ">")), loc)), loc)), loc), - fm) - end + ((L'.EStrcat + ((L'.EPrim (Prim.String ("<script type=\"text/javascript\">dyn(")), loc), + (L'.EStrcat ((L'.EJavaScript (L'.Script, e), loc), + (L'.EPrim (Prim.String (")</script>")), loc)), loc)), loc), + fm) | _ => raise Fail "Monoize: Bad dyn attributes") | "submit" => normal ("input type=\"submit\"", NONE, NONE) @@ -2683,9 +2670,9 @@ fun monoExp (env, st, fm) (all as (e, loc)) = loc)), loc), fm) end | SOME (_, src, _) => - (strcat [str "<span><script type=\"text/javascript\">inp(", + (strcat [str "<script type=\"text/javascript\">inp(", (L'.EJavaScript (L'.Script, src), loc), - str ")</script></span>"], + str ")</script>"], fm)) | _ => (Print.prefaces "Targs" (map (fn t => ("T", CorePrint.p_con env t)) targs); raise Fail "No name passed to textbox tag")) @@ -2760,9 +2747,9 @@ fun monoExp (env, st, fm) (all as (e, loc)) = str ")"] val sc = setAttrs sc in - (strcat [str "<span><script type=\"text/javascript\">", + (strcat [str "<script type=\"text/javascript\">", sc, - str "</script></span>"], + str "</script>"], fm) end) @@ -2783,9 +2770,9 @@ fun monoExp (env, st, fm) (all as (e, loc)) = str ")"] val sc = setAttrs sc in - (strcat [str "<span><script type=\"text/javascript\">", + (strcat [str "<script type=\"text/javascript\">", sc, - str "</script></span>"], + str "</script>"], fm) end) @@ -2813,9 +2800,9 @@ fun monoExp (env, st, fm) (all as (e, loc)) = str ")"] val sc = setAttrs sc in - (strcat [str "<span><script type=\"text/javascript\">", + (strcat [str "<script type=\"text/javascript\">", sc, - str "</script></span>"], + str "</script>"], fm) end) diff --git a/tests/dtable.ur b/tests/dtable.ur new file mode 100644 index 00000000..3a87b7bb --- /dev/null +++ b/tests/dtable.ur @@ -0,0 +1,6 @@ +fun main () = + s <- source <xml><tr><td>A</td><td>A'</td></tr></xml>; + return <xml><body> + <button value="Click me!" onclick={set s <xml><tr><td>B</td><td>B'</td></tr><tr><td>C</td><td>C'</td></tr></xml>}/><br/> + <table><tr><td>Pre</td><td>Pre'</td></tr><dyn signal={signal s}/><tr><td>Post</td><td>Post</td><td>Post'</td></tr></table> + </body></xml> diff --git a/tests/dtable.urp b/tests/dtable.urp new file mode 100644 index 00000000..9a35d287 --- /dev/null +++ b/tests/dtable.urp @@ -0,0 +1,3 @@ +debug + +dtable diff --git a/tests/dtable.urs b/tests/dtable.urs new file mode 100644 index 00000000..6ac44e0b --- /dev/null +++ b/tests/dtable.urs @@ -0,0 +1 @@ +val main : unit -> transaction page |