# HG changeset patch # User Adam Chlipala # Date 1292342122 18000 # Node ID 37eefd0a2ed44cfab0f211ea02b5fb43bd3a640c Import code from elsewhere diff -r 000000000000 -r 37eefd0a2ed4 .hgignore --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/.hgignore Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,6 @@ +syntax: glob + +*~ + +*.exe +*.sql diff -r 000000000000 -r 37eefd0a2ed4 LICENSE --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/LICENSE Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,25 @@ +Copyright (c) 2010, Adam Chlipala +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +- Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. +- Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. +- The names of contributors may not be used to endorse or promote products + derived from this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +POSSIBILITY OF SUCH DAMAGE. diff -r 000000000000 -r 37eefd0a2ed4 lib.urp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/lib.urp Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,2 @@ +timer +waitbox diff -r 000000000000 -r 37eefd0a2ed4 timer.ur --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/timer.ur Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,13 @@ +type t = source bool + +fun create r = + b <- source False; + spawn (sleep r.Milliseconds; + b <- get b; + if b then + return () + else + r.Action); + return b + +fun cancel b = set b True diff -r 000000000000 -r 37eefd0a2ed4 timer.urs --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/timer.urs Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,7 @@ +(** Cancelable delayed actions *) + +type t + +val create : {Milliseconds : int, + Action : transaction {}} -> transaction t +val cancel : t -> transaction {} diff -r 000000000000 -r 37eefd0a2ed4 waitbox.ur --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/waitbox.ur Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,47 @@ +type t = {Milliseconds : int, + Action : source (string -> transaction {}), + Timer : source (option Timer.t), + Text : source string} + +fun create n = + s <- source ""; + tmO <- source None; + f <- source (fn _ => return ()); + + return {Milliseconds = n, Action = f, Timer = tmO, Text = s} + +fun setAction r v = set r.Action v + +fun tickle r = + last <- get r.Timer; + (case last of + None => return () + | Some tm => Timer.cancel tm); + tm <- Timer.create {Milliseconds = r.Milliseconds, + Action = (set r.Timer None; + s <- get r.Text; + f <- get r.Action; + f s)}; + set r.Timer (Some tm) + +fun render r = + tickle r}/> + + +fun clear r = (set r.Text ""; + tm <- get r.Timer; + (case tm of + None => return () + | Some tm => Timer.cancel tm); + set r.Timer None) + +fun trigger r = + last <- get r.Timer; + (case last of + None => return () + | Some tm => Timer.cancel tm); + set r.Timer None; + s <- get r.Text; + f <- get r.Action; + f s diff -r 000000000000 -r 37eefd0a2ed4 waitbox.urs --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/waitbox.urs Tue Dec 14 10:55:22 2010 -0500 @@ -0,0 +1,18 @@ +(** Textboxes with an event for "no change in N milliseconds" *) + +type t + +val create : int -> transaction t + +val setAction : t -> (string -> transaction {}) -> transaction {} + +val render : t -> xbody + +val clear : t -> transaction {} + +val tickle : t -> transaction {} +(* Simulate the effect of the user making a change, which restarts the timer. *) + +val trigger : t -> transaction {} +(* Like [tickle], but triggering the action immediately, without waiting for + * quiescence *)