on master help sign in
Merge branch 'dev'
af75972evancz
elm/Elm.cabal → Elm.cabalrenamed+53−9
@@ -1,6 +1,5 @@
1−
2Name: Elm
1Name: Elm
3−Version: 0.7.2
2+Version: 0.8
4Synopsis: The Elm language module.
3Synopsis: The Elm language module.
5Description: Elm aims to make client-side web-development more pleasant.
4Description: Elm aims to make client-side web-development more pleasant.
6 It is a statically/strongly typed, functional reactive
5 It is a statically/strongly typed, functional reactive
@@ -19,10 +18,11 @@ Copyright: Copyright: (c) 2011-2012 Evan Czaplicki
19
18
20Category: Compiler, Language
19Category: Compiler, Language
21
20
22−Build-type: Simple
21+Build-type: Custom
23
22
24Extra-source-files: changelog.txt
23Extra-source-files: changelog.txt
24+Data-dir: dist/data
25−Data-files: elm-runtime-0.7.2.js
25+Data-files: elm-runtime.js docs.json
26Cabal-version: >=1.8
26Cabal-version: >=1.8
27
27
28source-repository head
28source-repository head
@@ -32,7 +32,7 @@ source-repository head
32Library
32Library
33 exposed-modules: Language.Elm,
33 exposed-modules: Language.Elm,
34 Language.Elm.Quasi
34 Language.Elm.Quasi
35− Hs-Source-Dirs: src, src/Gen
35+ Hs-Source-Dirs: compiler, compiler/Gen, compiler/Model, compiler/Transform
36 other-modules: Ast,
36 other-modules: Ast,
37 Context,
37 Context,
38 CompileToJS,
38 CompileToJS,
@@ -41,6 +41,8 @@ Library
41 ExtractNoscript,
41 ExtractNoscript,
42 GenerateHtml,
42 GenerateHtml,
43 Guid,
43 Guid,
44+ Libraries,
45+ LoadLibraries,
44 Optimize,
46 Optimize,
45 Initialize,
47 Initialize,
46 Rename,
48 Rename,
@@ -65,10 +67,10 @@ Library
65 containers >= 0.3,
67 containers >= 0.3,
66 transformers >= 0.2,
68 transformers >= 0.2,
67 mtl >= 2,
69 mtl >= 2,
70+ deepseq,
68 parsec >= 3.1.1,
71 parsec >= 3.1.1,
69 blaze-html == 0.5.* || == 0.6.*,
72 blaze-html == 0.5.* || == 0.6.*,
70 blaze-markup == 0.5.1.*,
73 blaze-markup == 0.5.1.*,
71− deepseq,
72 text,
74 text,
73 template-haskell,
75 template-haskell,
74 shakespeare >= 1,
76 shakespeare >= 1,
@@ -76,11 +78,16 @@ Library
76 bytestring,
78 bytestring,
77 hjsmin,
79 hjsmin,
78 indents,
80 indents,
79− filepath
81+ filepath,
82+ template-haskell,
83+ json,
84+ directory
80
85
81Executable elm
86Executable elm
82 Main-is: Compiler.hs
87 Main-is: Compiler.hs
83− Hs-Source-Dirs: src, src/Gen
88+ Hs-Source-Dirs: compiler, compiler/Gen, compiler/Model, compiler/Transform
89+ extensions: CPP
90+ cpp-options: -DELM_COMPILEDATADIR="dist/data"
84 other-modules: Ast,
91 other-modules: Ast,
85 Context,
92 Context,
86 CompileToJS,
93 CompileToJS,
@@ -89,6 +96,8 @@ Executable elm
89 ExtractNoscript,
96 ExtractNoscript,
90 GenerateHtml,
97 GenerateHtml,
91 Guid,
98 Guid,
99+ Libraries,
100+ LoadLibraries,
92 Optimize,
101 Optimize,
93 Initialize,
102 Initialize,
94 Rename,
103 Rename,
@@ -113,15 +122,16 @@ Executable elm
113 containers >= 0.3,
122 containers >= 0.3,
114 transformers >= 0.2,
123 transformers >= 0.2,
115 mtl >= 2,
124 mtl >= 2,
125+ deepseq,
116 parsec >= 3.1.1,
126 parsec >= 3.1.1,
117 blaze-html == 0.5.* || == 0.6.*,
127 blaze-html == 0.5.* || == 0.6.*,
118 blaze-markup == 0.5.1.*,
128 blaze-markup == 0.5.1.*,
119− deepseq,
120 cmdargs,
129 cmdargs,
121 pandoc >= 1.10,
130 pandoc >= 1.10,
122 bytestring,
131 bytestring,
123 hjsmin,
132 hjsmin,
124 indents,
133 indents,
134+<<<<<<< .mine
125 filepath
135 filepath
126
136
127
137
@@ -154,3 +164,37 @@ test-suite Main
154
164
155 hs-source-dirs: src, tests
165 hs-source-dirs: src, tests
156 main-is: Main.hs
166 main-is: Main.hs
167+=======
168+ filepath,
169+ template-haskell,
170+ json,
171+ directory
172+
173+Executable elm-doc
174+ Main-is: Docs.hs
175+ Hs-Source-Dirs: compiler, compiler/Model, compiler/Transform
176+ other-modules: Ast,
177+ Context,
178+ Parse.Library,
179+ Parse.Modules,
180+ Rename
181+
182+ Build-depends: base >=4.2 && <5,
183+ containers >= 0.3,
184+ transformers >= 0.2,
185+ mtl >= 2,
186+ parsec >= 3.1.1,
187+ pandoc >= 1.10,
188+ cmdargs,
189+ indents
190+
191+
192+
193+
194+
195+
196+
197+
198+
199+
200+>>>>>>> .theirs
Examples/elm-happstack/Main.hsdeleted−71
@@ -1,71 +0,0 @@
1−{-# LANGUAGE QuasiQuotes, TemplateHaskell #-}
2−
3−import Control.Monad (msum)
4−import Happstack.Server
5−import Language.Elm
6−import Language.Elm.Quasi
7−
8−elmRuntime="elm-runtime.js"
9−elmRTPath='/':elmRuntime
10−
11−-- elmResponse is a "nice to have" helper function for compiling
12−-- Elm code when using Elm with Happstack. At some point this might
13−-- be moved to an elm-happstack package.
14−elmResponse :: ElmSource a
15− => String -- ^ Page title
16− -> a -- ^ elm source
17− -> Response
18−elmResponse title = toResponse . toHtml elmRTPath title
19−
20−-- embedding variables (in this case URLs)
21−rootHandler :: ServerPart Response
22−rootHandler = ok $ elmResponse "Welcome!" $ elmIndex
23− where
24− mouse = "/mouse" -- all three of these variables are used in elm_source/index.elm
25− clock = "/clock"
26− shapes = "/shapes"
27− elmIndex = $(elmFile "elm_source/index.elm")
28−
29−-- loading elm source from file
30−
31−mouseHandler :: ServerPart Response
32−mouseHandler = ok $ elmResponse "Mouse position demo"
33− $(elmFile "elm_source/mouse.elm")
34−
35−clockHandler :: ServerPart Response
36−clockHandler = ok $ elmResponse "A clock" $(elmFile "elm_source/clock.elm")
37−
38−-- embedding elm code inside Haskell using the QuasiQuoter:
39−shapesPage = [elm|
40−square = rect 200 200 (150,150)
41−circle = oval 140 140 (150,150)
42−pentagon = ngon 5 60 (150,150)
43−
44−main = collage 300 300
45− [ outlined black square
46− , filled green pentagon
47− , customOutline [8,4] blue circle
48− ]
49−|]
50−
51−shapesHandler :: ServerPart Response
52−shapesHandler = ok $ elmResponse "Simple shapes" $ shapesPage
53−
54−-- routing
55−elmExample :: String -> ServerPart Response
56−elmExample elmLoc = do
57− msum [ nullDir >> rootHandler
58− , dir elmRuntime $ nullDir >>
59− serveFile (guessContentTypeM mimeTypes) elmLoc
60− , dir "mouse" $ nullDir >>
61− mouseHandler
62− , dir "clock" $ nullDir >>
63− clockHandler
64− , dir "shapes" $ nullDir >>
65− shapesHandler
66− ]
67−
68−main :: IO ()
69−main = do
70− elmLoc <- Language.Elm.runtimeLocation
71− simpleHTTP nullConf {port = 3000} $ elmExample elmLoc
Examples/elm-happstack/elm_source/clock.elmdeleted−13
@@ -1,13 +0,0 @@
1−
2−import Time (every)
3−
4−hand clr len time =
5− let t = pi * time / 30 - pi / 2 in
6− solid clr $ line [(200,200), (200 + len * cos t, 200 + len * sin t)]
7−
8−clock t = collage 400 400 [ filled (rgb 96 176 224) $ ngon 12 110 (200, 200)
9− , hand red 100 t
10− , hand black 100 (t/60)
11− , hand black 60 (t/720) ]
12−
13−main = lift clock (every 1)
Examples/elm-happstack/elm_source/index.elmdeleted−44
@@ -1,44 +0,0 @@
1−title w = size w 60 . text . header . toText $ "Elm-Happstack"
2−
3−lightGrey = rgb 240 241 244
4−mediumGrey = rgb 216 221 225
5−heading outer inner =
6− color mediumGrey . size outer 61 .
7− color lightGrey . size outer 60 .
8− size inner 60 $ title inner
9−
10−skeleton body outer =
11− let inner = if outer < 820 then outer - 20 else 800 in
12− flow down [ heading outer inner
13− , body outer inner
14− ]
15−
16−----------------------
17−
18−section = text . bold . Text.height (5/4) . toText
19−
20−-- splicing of values works but literal substitution of strings
21−-- for this reason, we need to have quotes.
22−mouseLink = "#{mouse}"
23−clockLink = "#{clock}"
24−shapesLink = "#{shapes}"
25−
26−
27−info w = List.map (\f -> f ()) . List.intersperse (\x -> plainText "&nbsp;") . List.map ((\e x -> e) . width w) $
28− [ section "Written in Elm, served with Happstack"
29− , text $ toText "This page is written in " ++ Text.link "http://elm-lang.org/" (toText "Elm") ++
30− toText " and served using the " ++
31− Text.link "http://happstack.com/" (toText "Happstack Web Framework") ++
32− toText ". Since you are looking at this page it is safe to assume that you already have the example code. "
33− , text $ toText "URLs are rendered using simple QuasiQuoter variable interpolation."
34− , section "More examples:"
35− , text $ toText "- " ++ Text.link mouseLink (toText "A simple mouse input example")
36− , text $ toText "- " ++ Text.link clockLink (toText "An animated analog clock")
37− , text $ toText "- " ++ Text.link shapesLink (toText "Some simple rendered shapes")
38− ]
39−
40−-- The following line does not parse, replaced it something slightly different
41−-- body outer inner = width outer . flow down $ (:) (plainText "&nbsp;") $ info inner
42−body outer inner = width outer . flow down $ info inner
43−
44−main = lift (skeleton body) Window.width
Examples/elm-happstack/elm_source/mouse.elmdeleted−15
@@ -1,15 +0,0 @@
1−
2−-- Move your mouse around above the canvas!
3−
4−import Mouse (position)
5−import Window (dimensions)
6−
7−myBlue = rgb 0 85 170
8−myGreen = rgba 28 267 85 (1/2)
9−
10−scene (x,y) (w,h) =
11− collage w h [ rotate (toFloat (x+y) / 1000) $ filled myBlue $ ngon 4 100 (200,200)
12− , filled myGreen $ ngon 5 30 (x,y)
13− ]
14−
15−main = lift2 scene Mouse.position Window.dimensions
Examples/elm-js/GameSkeleton/GameSkeleton.elmdeleted−82
@@ -1,82 +0,0 @@
1−module GameSkeleton where
2−
3−
4−
5−{-- Part 1: Model the user input ----------------------------------------------
6−
7−What information do you need to represent all relevant user input?
8−
9−Task: Redefine `UserInput` to include all of the information you need.
10− Redefine `userInput` to be a signal that correctly models the user
11− input as described by `UserInput`.
12−
13−------------------------------------------------------------------------------}
14−
15−data UserInput = UserInput
16−
17−userInput = constant UserInput
18−
19−data Input = Input Float UserInput
20−
21−
22−
23−{-- Part 2: Model the game ----------------------------------------------------
24−
25−What information do you need to represent the entire game?
26−
27−Tasks: Redefine `GameState` to represent your particular game.
28− Redefine `defaultGame` to represent your initial game state.
29−
30−For example, if you want to represent many objects that just have a position,
31−your GameState might just be a list of coordinates and your default game might
32−be an empty list (no objects at the start):
33−
34− data GameState = GameState [(Float,Float)]
35− defaultGame = GameState []
36−
37−------------------------------------------------------------------------------}
38−
39−data GameState = GameState
40−
41−defaultGame = GameState
42−
43−
44−
45−{-- Part 3: Update the game ---------------------------------------------------
46−
47−How does the game step from one state to another based on user input?
48−
49−Task: redefine `stepGame` to use the UserInput and GameState
50− you defined in parts 1 and 2. Maybe use some helper functions
51− to break up the work, stepping smaller parts of the game.
52−
53−------------------------------------------------------------------------------}
54−
55−stepGame (Input delta (UserInput)) (GameState) = GameState
56−
57−
58−
59−{-- Part 4: Display the game --------------------------------------------------
60−
61−How should the GameState be displayed to the user?
62−
63−Task: redefine `display` to use the GameState you defined in part 2.
64−
65−------------------------------------------------------------------------------}
66−
67−display (w,h) gameState = asText gameState
68−
69−
70−
71−{-- That's all folks! ---------------------------------------------------------
72−
73−The following code puts it all together and show it on screen.
74−
75−------------------------------------------------------------------------------}
76−
77−delta = fps 60
78−input = sampleOn delta (lift2 Input delta userInput)
79−
80−gameState = foldp stepGame defaultGame input
81−
82−main = lift2 display Window.dimensions gameState
Examples/elm-js/Logging/Log.elmdeleted−17
@@ -1,17 +0,0 @@
1−
2−module Log where
3−
4−import Foreign.JavaScript
5−import Signal.Input
6−
7−
8−foreign export jsevent "logMessage"
9− messages :: Signal JSString
10−
11−(field, message) = textField ""
12−(butn , pressed) = button " Log "
13−
14−messages =
15− lift castStringToJSString $ keepWhen pressed "" message
16−
17−main = field `beside` butn
Examples/elm-js/Logging/LogHelp.jsdeleted−3
@@ -1,3 +0,0 @@
1−document.addEventListener('logMessage', function(e) {
2− console.log(e.value);
3− });
Examples/elm-js/Logging/README.mddeleted−16
@@ -1,16 +0,0 @@
1−
2−To compile this example yourself use:
3−
4− elm --import-js="LogHelp.js" Log.elm
5−
6−This compiles the Elm file and includes the necessary JavaScript code.
7−It produces a self-contained HTML file.
8−
9−
10−You can see the logged messages in the developer console of your browser.
11−The keyboard shortcut is F12 in many browsers.
12−
13−
14−Note: Not all browsers like reading the elm-runtime-x.y.z.js file from
15−an absolute path, so you may have to specify a relative path with
16−the --runtime flag (e.g. --runtime="../../../elm/elm-runtime-0.3.5.js").
Examples/elm-js/Maps/Map.elmdeleted−14
@@ -1,14 +0,0 @@
1−
2−module Map where
3−
4−import JavaScript.Experimental
5−
6−foreign import jsevent "provideMap"
7− (castElementToJSElement $ spacer 640 360)
8− jsMaps :: Signal JSElement
9−
10−
11−center (w,h) elem = container w h middle elem
12−maps = lift (castJSElementToElement 640 360) jsMaps
13−
14−main = lift2 center Window.dimensions maps
Examples/elm-js/Maps/MapHelp.jsdeleted−25
@@ -1,25 +0,0 @@
1−
2−document.body.onload = function() {
3−
4−var lib = document.createElement('script');
5−lib.addEventListener('load', function() {
6− var div = document.createElement('div');
7− div.id = "demoMap";
8− div.style.width = "640px";
9− div.style.height = "360px";
10−
11− var e = document.createEvent('Event');
12− e.initEvent('provideMap', true, true);
13− e.value = div;
14− document.dispatchEvent(e);
15−
16− setTimeout(function() {
17− var map = new OpenLayers.Map("demoMap");
18− map.addLayer(new OpenLayers.Layer.OSM());
19− map.zoomToMaxExtent();
20− }, 0);
21− });
22−lib.src = "http://www.openlayers.org/api/OpenLayers.js";
23−document.head.appendChild(lib);
24−
25−}
Examples/elm-js/Maps/README.mddeleted−15
@@ -1,15 +0,0 @@
1−
2−To compile this example yourself use:
3−
4− elm --import-js="MapHelp.js" Map.elm
5−
6−This compiles the Elm file and includes the necessary JavaScript code.
7−It produces a self-contained HTML file.
8−
9−
10−Note: Not all browsers like reading the elm-runtime-x.y.z.js file from
11−an absolute path, so you may have to specify a relative path with
12−the --runtime flag (e.g. --runtime="../../../elm/elm-runtime-0.3.5.js").
13−
14−Warning: I am not sure how stable the OpenLayers API is. This is for
15−example only!
Examples/elm-js/Pong/Pong.elmdeleted−263
@@ -1,263 +0,0 @@
1−
2−{----- Overview ------------------------------------------------------
3−
4− This game displays some of the strengths of Functional Reactive
5− Programming (FRP). By the end of this file we will have written an
6− entire GUI/game without any imperative code! No global mutable state,
7− no flipping pixels, no destructive updates. In fact, Elm disallows all
8− of these things at the language level. So good design and safe coding
9− practices are a requirement, not just self-inforced suggestions.
10−
11− This code neatly divides Pong into three major parts: modeling the
12− game, updating the game, and viewing the game. It may be helpful to
13− think of it as a functional variation on the Model-View-Controller
14− paradigm.
15−
16− The code for Pong is structured as follows:
17−
18− 1. MODEL:
19− First we need to define Pong. We do this by modelling Pong with
20− simple data structures. We need two categories of model:
21− - Inputs to the game. For Pong, this is keyboard input from
22− users and clock-ticks from the frame rate manager.
23− - A model of the game itself: paddles, ball, score, etc.
24− Without a model of the game we would have nothing to update
25− or display!
26− These models are the basis for the next two sections, holding
27− all of the information about Pong that we will need.
28−
29− 2. UPDATE:
30− When new inputs come in, we need to update the current state
31− of the game. Without updates, this version of Pong would be very
32− very boring! This section defines a number of 'step functions'
33− that step the game forward based on our inputs. By separating
34− this from the model and display code, we can change how the game
35− works (how it steps forward) without changing anything else: the
36− underlying model and the display code need not be touched.
37−
38− 3. VIEW:
39− Finally, we need a display function that defines the user's view
40− of the game. This code is separate from the game logic, so like
41− the update logic, it can be modified without affecting any other
42− part of the program. We can also define many different views
43− of the same underlying model. In Pong there's not much need for
44− this, but as your model becomes more complex this may be very
45− useful!
46−
47− If you would like to make a game or larger application in Elm, use
48− this structure! Maybe even use this file as a starting point for
49− playing around with your own ideas.
50−
51− Let's get started!
52−
53−-----------------------------------------------------------------------}
54−
55−
56−module Pong where
57−
58−import JavaScript
59−
60−
61−-- Set the frames per second (FPS) to 60, calculate the deltas (the
62−-- difference between the two latest times, the amount of time since
63−-- the last frame), and convert the time into a number of seconds.
64−
65−delta = lift inSeconds (fps 60)
66−
67−
68−------------------------------------------------------------------------
69−------ Modelling User Input ------
70−------------------------------------------------------------------------
71−
72−-- During gameplay, all keyboard input is about the position of the
73−-- two paddles. So the keyboard input can be reduced to two directions,
74−-- each represented by an integer in {-1,0,1}. Furthermore, the SPACE
75−-- key is used to start the game between rounds, so we also need a
76−-- boolean value to represent whether it is pressed.
77−
78−data KeyInput = KeyInput Bool Int Int
79−
80−defaultKeyInput = KeyInput False 0 0
81−
82−keyInput = lift3 KeyInput Keyboard.space
83− (lift .y Keyboard.wasd)
84− (lift .y Keyboard.arrows)
85−
86−
87−------------------------------------------------------------------------
88−------ Combining all inputs ------
89−------------------------------------------------------------------------
90−
91−-- The inputs to this game include a timestep (which we extracted from
92−-- JavaScript) and the keyboard input from the users.
93−
94−data Input = Input Float KeyInput
95−
96−-- Combine both kinds of inputs and filter out keyboard events. We only
97−-- want the game to refresh on clock-ticks, not key presses too.
98−
99−input = sampleOn delta (lift2 Input delta keyInput)
100−
101−
102−
103−------------------------------------------------------------------------
104−------ Modelling Pong / a State Machine ------
105−------------------------------------------------------------------------
106−
107−-- Pong has two obvious components: the ball and two paddles.
108−
109−data Paddle = Paddle Float -- y-position
110−data Ball = Ball (Float,Float) (Float,Float) -- position and velocity
111−
112−-- But we also want to keep track of the current score and whether
113−-- the ball is currently in play. This will allow us to have rounds
114−-- of play rather than just having the ball move around continuously.
115−
116−data Score = Score Int Int
117−data State = Play | BetweenRounds
118−
119−-- Together, this information makes up the state of the game. We model
120−-- Pong by using the inputs (defined above) to update the state of the
121−-- game!
122−
123−data GameState = GameState State Score Ball Paddle Paddle
124−
125−
126−-- I have chosen to parameterize the size of the board, so it can
127−-- be changed with minimal effort.
128−
129−gameWidth = 600
130−gameHeight = 400
131−halfWidth = gameWidth / 2
132−halfHeight = gameHeight / 2
133−
134−
135−-- Before we can update anything, we must first define the default
136−-- configuration of the game. In our case we want to start between
137−-- rounds with a score of zero to zero.
138−
139−defaultGame = GameState BetweenRounds
140− (Score 0 0)
141− (Ball (halfWidth, halfHeight) (150,150))
142− (Paddle halfHeight)
143− (Paddle halfHeight)
144−
145−
146−
147−------------------------------------------------------------------------
148−------ Stepping from State to State ------
149−------------------------------------------------------------------------
150−
151−-- Now to step the game from one state to another. We can break this up
152−-- into smaller components.
153−
154−-- First, we define a step function for updating the position of
155−-- paddles. It depends on our timestep and a desired direction (given
156−-- by keyboard input).
157−
158−stepPaddle delta dir (Paddle y) =
159− Paddle $ clamp 20 (gameHeight-20) (y - toFloat dir * 200 * delta)
160−
161−
162−-- We must also step the ball forward. This is more complicated due to
163−-- the many kinds of collisions that can happen. All together, this
164−-- function figures out the new velocity of the ball based on
165−-- collisions with the top and bottom borders and collisions with the
166−-- paddles. This new velocity is used to calculate a new position.
167−
168−-- This function also determines whether a point has been scored and
169−-- who receives the point. Thus, its output is a new Ball and points
170−-- to be added to each player.
171−
172−makePositive n = if n > 0 then n else 0-n
173−makeNegative n = if n > 0 then 0-n else n
174−within epsilon n x = x > n - epsilon && x < n + epsilon
175−
176−stepVelocity velocity lowerCollision upperCollision =
177− if lowerCollision then makePositive velocity else
178− if upperCollision then makeNegative velocity else velocity
179−
180−stepBall delta (Ball (x,y) (vx,vy)) (Paddle y1) (Paddle y2) =
181− let hitPaddle1 = within 20 y1 y && within 8 25 x
182− hitPaddle2 = within 20 y2 y && within 8 (gameWidth - 25) x
183− vx' = stepVelocity vx hitPaddle1 hitPaddle2
184− vy' = stepVelocity vy (y < 7) (y > gameHeight - 7)
185− scored = x > gameWidth || x < 0
186− x' = if scored then halfWidth else x + vx' * delta
187− y' = if scored then halfHeight else y + vy' * delta
188− in ( Ball (x',y') (vx',vy')
189− , if x > gameWidth then 1 else 0
190− , if x < 0 then 1 else 0 )
191−
192−
193−-- Finally, we define a step function for the entire game. This steps from state to
194−-- state based on the inputs to the game.
195−
196−stepGame (Input delta (KeyInput space dir1 dir2))
197− (GameState state (Score s1 s2) ball paddle1 paddle2) =
198− let (ball',s1',s2') = if state == Play then stepBall delta ball paddle1 paddle2
199− else (ball, 0, 0)
200− state' = case state of
201− Play -> if s1' /= s2' then BetweenRounds else state
202− BetweenRounds -> if space then Play else state
203− in GameState state'
204− (Score (s1+s1') (s2+s2'))
205− ball'
206− (stepPaddle delta dir1 paddle1)
207− (stepPaddle delta dir2 paddle2)
208−
209−
210−-- Now we put it all together. We have a signal of inputs that changes whenever there
211−-- is a clock tick. This input signal carries the all the information we need about
212−-- the keyboard. We also have a step function that steps from one game-state to the
213−-- next based on some inputs.
214−
215−-- The `gameState` signal steps forward every time a new input comes in. It starts
216−-- as the default game and progresses based on user behavior.
217−
218−gameState = foldp stepGame defaultGame input
219−
220−
221−
222−------------------------------------------------------------------------
223−------ Displaying the Game ------
224−------------------------------------------------------------------------
225−
226−-- These functions take a GameState and turn it into something a user
227−-- can see and understand. It is totally independent of how the game
228−-- updates, it only needs to know the current game state. This allows us
229−-- to change how the game looks without changing any of the logic of the
230−-- game.
231−
232−
233−-- This function displays the current score and directions.
234−
235−scoreBoard w inPlay p1 p2 =
236− let code = text . monospace . toText
237− stack top bottom = flow down [ code " ", code top, code bottom ]
238− msg = width w . centeredText . monospace $ toText "Press SPACE to begin"
239− board = flow right [ stack "W" "S", spacer 20 1
240− , text . Text.height 4 . toText $ show p1 ++ " " ++ show p2
241− , spacer 20 1, stack "&uarr;" "&darr;" ]
242− score = container w (heightOf board) midTop board
243− in if inPlay then score else score `above` msg
244−
245−
246−-- This function displays the entire GameState.
247−
248−display (w,h) (GameState state (Score p1 p2) (Ball pos _) (Paddle y1) (Paddle y2)) =
249− layers
250− [ let pongGreen = rgb 60 100 60 in
251− container w h middle $ collage gameWidth gameHeight
252− [ filled pongGreen (rect gameWidth gameHeight (halfWidth,halfHeight))
253− , filled white (oval 15 15 pos) -- ball
254− , filled white (rect 10 40 ( 20, y1)) -- first paddle
255− , filled white (rect 10 40 (gameWidth - 20, y2)) -- second paddle
256− ]
257− , scoreBoard w (state == Play) p1 p2
258− ]
259−
260−-- We can now define a view of the game (a signal of Elements) that changes
261−-- as the GameState changes. This is what the users will see.
262−
263−main = lift2 display Window.dimensions gameState
Examples/elm-js/Pong/README.mddeleted−11
@@ -1,11 +0,0 @@
1−
2−
3−To compile this example yourself use:
4−
5− elm Pong.elm
6−
7−It produces a self-contained HTML file called Pong.html.
8−
9−As of version 0.6 of the compiler, no external code is necessary
10−to make this work, so the code is slightly cleaner and simpler than
11−the "Pong in Elm" walkthrough.
Examples/elm-js/Redirect/README.mddeleted−12
@@ -1,12 +0,0 @@
1−
2−To compile this example yourself use:
3−
4− elm --import-js="RedirectHelp.js" Redirect.elm
5−
6−This compiles the Elm file and includes the necessary JavaScript code.
7−It produces a self-contained HTML file.
8−
9−
10−Note: Not all browsers like reading the elm-runtime-x.y.z.js file from
11−an absolute path, so you may have to specify a relative path with
12−the --runtime flag (e.g. --runtime="../../../elm/elm-runtime-0.3.5.js").
Examples/elm-js/Redirect/Redirect.elmdeleted−17
@@ -1,17 +0,0 @@
1−
2−module Redirect where
3−
4−import Foreign.JavaScript
5−import Signal.Input
6−
7−
8−foreign export jsevent "redirect"
9− redirectTo :: Signal JSString
10−
11−(butn, pressed) = button " Redirect to elm-lang.org "
12−
13−redirectTo =
14− lift castStringToJSString $
15− keepWhen pressed "" (constant "http://elm-lang.org/")
16−
17−main = butn
Examples/elm-js/Redirect/RedirectHelp.jsdeleted−3
@@ -1,3 +0,0 @@
1−document.addEventListener('redirect', function(e) {
2− if (e.value.length > 0) { window.location = e.value; }
3− });
Examples/elm-js/Title/ChangeTitle.elmdeleted−14
@@ -1,14 +0,0 @@
1−
2−module ChangeTitle where
3−
4−import Foreign.JavaScript
5−import Signal.Input
6−
7−
8−foreign export jsevent "changeTitle"
9− title :: Signal JSString
10−
11−(field, title) = let (f,t) = textField "" in
12− (f, lift castStringToJSString t)
13−
14−main = plainText "Change this page's title to: " `beside` field
Examples/elm-js/Title/ChangeTitleHelp.jsdeleted−3
@@ -1,3 +0,0 @@
1−document.addEventListener('changeTitle', function(e) {
2− document.title = e.value;
3− });
Examples/elm-js/Title/README.mddeleted−7
@@ -1,7 +0,0 @@
1−
2−To compile this example yourself use:
3−
4− elm --import-js="ChangeTitleHelp.js" ChangeTitle.elm
5−
6−This compiles the Elm file and includes the necessary JavaScript code.
7−It produces a self-contained HTML file.
Examples/elm-yesod/Main.hsdeleted−81
@@ -1,81 +0,0 @@
1−{-# LANGUAGE QuasiQuotes, TemplateHaskell, OverloadedStrings, TypeFamilies, MultiParamTypeClasses #-}
2−
3−import Language.Elm
4−import Language.Elm.Quasi
5−import Language.Elm.Yesod
6−import Yesod
7−import Text.Hamlet
8−
9−data ElmTest = ElmTest
10−
11−-- loading external elm code
12−mousePage = $(elmFile "elm_source/mouse.elm")
13−
14−clockPage = $(elmFile "elm_source/clock.elm")
15−
16−-- embedding elm code inside Haskell using the QuasiQuoter:
17−shapesPage = [elm|
18−square = rect 200 200 (150,150)
19−circle = oval 140 140 (150,150)
20−pentagon = ngon 5 60 (150,150)
21−
22−main = collage 300 300
23− [ outlined black square
24− , filled green pentagon
25− , customOutline [8,4] blue circle
26− ]
27−|]
28−
29−-- our Yesod App
30−mkYesod "ElmTest" [parseRoutes|
31−/ RootR GET
32−/mouse MouseR GET
33−/clock ClockR GET
34−/shapes ShapesR GET
35−|]
36−
37−-- Your App data type needs to have an instance of YesodElm (see line 75&76)
38−-- so that toWidget can work with QuasiQuoted elm code. All URL interpolation
39−-- is done automatically. (e.g. lines 28-30 in elm_source/index.elm)
40−getMouseR :: Handler RepHtml
41−getMouseR =
42− defaultLayout $ do
43− setTitle "Mouse position demo"
44− toWidget mousePage
45−
46−getClockR :: Handler RepHtml
47−getClockR =
48− defaultLayout $ do
49− setTitle "A clock"
50− toWidget clockPage
51−
52−getShapesR :: Handler RepHtml
53−getShapesR =
54− defaultLayout $ do
55− setTitle "Simple shapes"
56− toWidget shapesPage
57−
58−getRootR :: Handler RepHtml
59−getRootR =
60− defaultLayout $ do
61− setTitle "Welcome!"
62− toWidget $(elmFile "elm_source/index.elm")
63−
64−
65−-- Our Yesod instance contains the default layout, which inserts the elm-min.js
66−-- file in the site's <head> tag. The YesodElm instance defines the location of
67−-- elm-min.js
68−
69−instance Yesod ElmTest where
70− jsLoader _ = BottomOfHeadBlocking
71− defaultLayout widget = do
72− mmsg <- getMessage
73− pc <- widgetToPageContent $ do
74− $(whamletFile "templates/default-layout.hamlet")
75− hamletToRepHtml $(hamletFile "templates/default-layout-wrapper.hamlet")
76−
77−instance YesodElm ElmTest where
78− urlElmJs _ = Right $ "https://raw.github.com/evancz/Elm/master/elm/elm-runtime-0.7.2.js"
79−
80−main :: IO ()
81−main = warpDebug 3000 ElmTest
Examples/elm-yesod/elm_source/clock.elmdeleted−11
@@ -1,11 +0,0 @@
1−
2−hand clr len time =
3− let t = pi * inSeconds time / 30 - pi / 2 in
4− solid clr $ line [(200,200), (200 + len * cos t, 200 + len * sin t)]
5−
6−clock t = collage 400 400 [ filled (rgb 96 176 224) $ ngon 12 110 (200, 200)
7− , hand red 100 t
8− , hand black 100 (t/60)
9− , hand black 60 (t/720) ]
10−
11−main = lift clock (every second)
Examples/elm-yesod/elm_source/index.elmdeleted−35
@@ -1,35 +0,0 @@
1−title w = size w 60 . text . header . toText $ "Elm-Yesod"
2−
3−lightGrey = rgb 240 241 244
4−mediumGrey = rgb 216 221 225
5−heading outer inner =
6− color mediumGrey . size outer 61 .
7− color lightGrey . size outer 60 .
8− size inner 60 $ title inner
9−
10−skeleton body outer =
11− let inner = if outer < 820 then outer - 20 else 800 in
12− flow down [ heading outer inner
13− , body outer inner
14− ]
15−
16−----------------------
17−
18−section = text . bold . Text.height (5/4) . toText
19−
20−info w = List.map (\f -> f ()) . List.intersperse (\x -> plainText "&nbsp;") . List.map ((\e x -> e) . width w) $
21− [ section "Written in Elm, served with Yesod"
22− , text $ toText "This page is written in " ++ Text.link "http://elm-lang.org/" (toText "Elm") ++
23− toText " and served using the " ++
24− Text.link "http://yesodweb.com/" (toText "Yesod Web Framework") ++
25− toText ". Since you are looking at this page it is safe to assume that you already have the example code. "
26− , text $ toText "Type-safe URLs are rendered using simple QuasiQuoter variable interpolation."
27− , section "More examples:"
28− , text $ toText "- " ++ Text.link "@{MouseR}" (toText "A simple mouse input example")
29− , text $ toText "- " ++ Text.link "@{ClockR}" (toText "An animated analog clock")
30− , text $ toText "- " ++ Text.link "@{ShapesR}" (toText "Some simple rendered shapes")
31− ]
32−
33−body outer inner = width outer . flow down . (:) (plainText "&nbsp;") $ info inner
34−
35−main = lift (skeleton body) Window.width
Examples/elm-yesod/elm_source/mouse.elmdeleted−13
@@ -1,13 +0,0 @@
1−
2−-- Move your mouse around above the canvas!
3−
4−myBlue = rgb 0 85 170
5−myGreen = rgba 28 267 85 0.5
6−
7−scene (x,y) (w,h) =
8− collage w h
9− [ rotate (toFloat (x+y) / 1000) (filled myBlue (ngon 4 100 (200,200)))
10− , filled myGreen (ngon 5 30 (x,y))
11− ]
12−
13−main = lift2 scene Mouse.position Window.dimensions
Examples/elm-yesod/templates/default-layout-wrapper.hamletdeleted−8
@@ -1,8 +0,0 @@
1−$doctype 5
2−<html>
3− <head>
4− <meta charset="UTF-8">
5− <title>#{pageTitle pc}
6− ^{pageHead pc}
7− <body>
8− ^{pageBody pc}
Examples/elm-yesod/templates/default-layout.hamletdeleted−3
@@ -1,3 +0,0 @@
1−$maybe msg <- mmsg
2− <div .message>#{msg}
3−^{widget}
Examples/mario_mp/.gitignoredeleted−2
@@ -1,2 +0,0 @@
1−*.html
2−mario_mp
Examples/mario_mp/Clicks.elmdeleted−6
@@ -1,6 +0,0 @@
1−
2−module Clicks where
3−import WebSocket
4−msgs = show <~ count Mouse.clicks
5−main = asText <~ open "ws://localhost:8080/ws" msgs
6−
Examples/mario_mp/Mario.elmdeleted−91
@@ -1,91 +0,0 @@
1−
2−module Mario where
3−
4−import Dict
5−import JavaScript
6−import JSON
7−import Random
8−import WebSocket
9−
10−{- INPUT -}
11−
12−jumpStep isJump obj = if isJump && obj.y == 0 then { obj | vy <- 5 } else obj
13−gravityStep t obj = { obj | vy <- if obj.y > 0 then obj.vy - t/4 else obj.vy }
14−timeStep t obj = let {x,y,vx,vy} = obj in
15− { obj | x <- x + t * vx , y <- max 0 $ y + t * vy }
16−walkStep dir obj = { obj | vx <- dir, dir <- if | dir < 0 -> "left"
17− | dir > 0 -> "right"
18− | otherwise -> obj.dir }
19−
20−step t d j = timeStep t . gravityStep t . jumpStep j . walkStep d
21−
22−delta = lift (flip (/) 20) (fps 25)
23−leftRight = toFloat . .x <~ Keyboard.arrows
24−jump = (\{y} -> y > 0) <~ Keyboard.arrows
25−steps = sampleOn delta (lift3 step delta leftRight jump)
26−
27−{- LOCAL STATE -}
28−
29−initialMario = { x = 0, y = 0, vx = 0, vy = 0, dir = "right" }
30−stateSignal = foldp ($) initialMario steps
31−
32−encode obj id =
33− castJSStringToString . (toPrettyJSString "") . JSON.fromList $
34− [ ("id", JsonNumber id)
35− , ("x", JsonNumber obj.x)
36− , ("y", JsonNumber obj.y)
37− , ("vx", JsonNumber obj.vx)
38− , ("dir", JsonString obj.dir) ]
39−--encode obj id = show id ++ " " ++ show obj.x ++ " " ++ show obj.y
40−
41−clientID = inRange 0 99999
42−myStream = encode <~ stateSignal ~ clientID
43−
44−{- NETWORK LAYER -}
45−
46−worldMessageStream = open "ws://localhost:8080/ws" myStream
47−
48−-- :: String -> Maybe (Float, Record)
49−parsePlayer msg =
50− case fromString msg of
51− Nothing -> Nothing
52− Just json ->
53− let id = findNumber "id" json
54− x = findNumber "x" json
55− y = findNumber "y" json
56− vx = findNumber "vx" json
57− dir = findString "dir" json
58− in Just (id, { x = x, y = y, vx = vx, vy = 0, dir = dir })
59−
60−-- :: Maybe (Float, Record) -> Dict String Record -> Dict String Record
61−updateWorldPositions maybeMario marioDict = case maybeMario of
62− Just (id, mario) -> (Dict.insert) (show id) mario marioDict
63− Nothing -> marioDict
64−
65−-- :: Signal (Dict String Record)
66−worldPositions = foldp updateWorldPositions Dict.empty (parsePlayer <~ worldMessageStream)
67−--worldPositions = constant empty
68−
69−marios = Dict.values <~ worldPositions
70−
71−{- RENDER CODE -}
72−
73−-- :: Record -> Form
74−mario2Form (w,h) mario =
75− let verb = if mario.vx /= 0 then "walk" else "stand"
76− src = "/imgs/mario/" ++ verb ++ "/" ++ mario.dir ++ ".gif"
77− in toForm (mario.x, (h-63)-mario.y) (image 35 35 src)
78−
79−-- :: (Int,Int) -> [Record] -> Element
80−render (w,h) marios =
81− collage w h ( (filled cyan $ rect w h (w `div` 2, h `div` 2))
82− : (filled green $ rect w 50 (w `div` 2,h-25))
83− : List.map (mario2Form (w,h)) marios )
84−
85−{- PUTTING IT TOGETHER -}
86−
87−-- :: Signal Element
88−main = render <~ Window.dimensions ~ marios
89−--main = above <~ ((plainText . show) <~ (marios)) ~ (render <~ Window.dimensions ~ marios)
90−--main = (plainText . show) <~ (marios)
91−
Examples/mario_mp/Object.elmdeleted−8
@@ -1,8 +0,0 @@
1−
2−module Object where
3−
4−import JavaScript
5−import JSON
6−
7−main = plainText . castJSStringToString . (toPrettyJSString "") . fromList $ [ ("answer", JsonNumber 42) ]
8−
Examples/mario_mp/Values.elmdeleted−7
@@ -1,7 +0,0 @@
1−
2−module Values where
3−
4−import Dict
5−
6−main = constant . plainText . show . values $ empty
7−
Examples/mario_mp/conn.godeleted−43
@@ -1,43 +0,0 @@
1−package main
2−
3−import (
4− "code.google.com/p/go.net/websocket"
5−)
6−
7−type connection struct {
8− // The websocket connection.
9− ws *websocket.Conn
10−
11− // Buffered channel of outbound messages.
12− send chan string
13−}
14−
15−func (c *connection) reader() {
16− for {
17− var message string
18− err := websocket.Message.Receive(c.ws, &message)
19− if err != nil {
20− break
21− }
22− h.broadcast <- message
23− }
24− c.ws.Close()
25−}
26−
27−func (c *connection) writer() {
28− for message := range c.send {
29− err := websocket.Message.Send(c.ws, message)
30− if err != nil {
31− break
32− }
33− }
34− c.ws.Close()
35−}
36−
37−func wsHandler(ws *websocket.Conn) {
38− c := &connection{send: make(chan string, 256), ws: ws}
39− h.register <- c
40− defer func() { h.unregister <- c }()
41− go c.writer()
42− c.reader()
43−}
Examples/mario_mp/elm-runtime.jsdeleted−1
@@ -1 +0,0 @@
1−../../elm/elm-runtime.js
Examples/mario_mp/hub.godeleted−44
@@ -1,44 +0,0 @@
1−package main
2−
3−type hub struct {
4− // Registered connections.
5− connections map[*connection]bool
6−
7− // Inbound messages from the connections.
8− broadcast chan string
9−
10− // Register requests from the connections.
11− register chan *connection
12−
13− // Unregister requests from connections.
14− unregister chan *connection
15−}
16−
17−var h = hub{
18− broadcast: make(chan string),
19− register: make(chan *connection),
20− unregister: make(chan *connection),
21− connections: make(map[*connection]bool),
22−}
23−
24−func (h *hub) run() {
25− for {
26− select {
27− case c := <-h.register:
28− h.connections[c] = true
29− case c := <-h.unregister:
30− delete(h.connections, c)
31− close(c.send)
32− case m := <-h.broadcast:
33− for c := range h.connections {
34− select {
35− case c.send <- m:
36− default:
37− delete(h.connections, c)
38− close(c.send)
39− go c.ws.Close()
40− }
41− }
42− }
43− }
44−}
Examples/mario_mp/imgs/mario/stand/left.gifdeleted

Binary file not shown.

Examples/mario_mp/imgs/mario/stand/right.gifdeleted

Binary file not shown.

Examples/mario_mp/imgs/mario/walk/left.gifdeleted

Binary file not shown.

Examples/mario_mp/imgs/mario/walk/right.gifdeleted

Binary file not shown.

Examples/mario_mp/main.godeleted−24
@@ -1,24 +0,0 @@
1−package main
2−
3−import (
4− "code.google.com/p/go.net/websocket"
5− "flag"
6− "log"
7− "net/http"
8−)
9−
10−var addr = flag.String("addr", ":8080", "http service address")
11−
12−func fileHandler(w http.ResponseWriter, r *http.Request) {
13− http.ServeFile(w, r, r.URL.Path[1:])
14−}
15−
16−func main() {
17− flag.Parse()
18− go h.run()
19− http.HandleFunc("/", fileHandler)
20− http.Handle("/ws", websocket.Handler(wsHandler))
21− if err := http.ListenAndServe(*addr, nil); err != nil {
22− log.Fatal("ListenAndServe:", err)
23− }
24−}
Examples/mario_mp/makefiledeleted−19
@@ -1,19 +0,0 @@
1−all: mario_mp Mario.html Clicks.html Object.html Values.html
2−
3−mario_mp: *.go
4− go build
5−
6−Mario.html: Mario.elm
7− elm -r elm-runtime.js Mario.elm
8−
9−Clicks.html: Clicks.elm
10− elm -r elm-runtime.js Clicks.elm
11−
12−Object.html: Object.elm
13− elm -r elm-runtime.js Object.elm
14−
15−Values.html: Values.elm
16− elm -r elm-runtime.js Values.elm
17−
18−clean:
19− rm -rf *.html mario_mp
elm-server/LICENSE → LICENSErenamed

The content is the same.

Setup.hsnew file+156
@@ -0,0 +1,156 @@
1+import Distribution.Simple
2+import Distribution.Simple.LocalBuildInfo
3+import Distribution.Simple.Setup
4+import Distribution.PackageDescription
5+
6+import System.Cmd
7+import System.Directory
8+import System.FilePath
9+import System.IO
10+import System.Process
11+
12+import Control.Monad
13+
14+-- Part 1
15+-- ------
16+-- Add a build callout
17+-- We need to build elm-doc and run it because that generates the file "docs.json" needs by Libraries.hs
18+-- which is part of the elm library and executable
19+-- Unfort. there seems to be no way to tell cabal that:
20+-- (a) elm-doc generates docs.json, and
21+-- (b) elm (library) depends on docs.json
22+-- Therefore, we either use make instead (or a script), or hack around in cabal
23+
24+-- Part 2
25+-- ------
26+-- Add a post-build callout.
27+-- We need to build the runtime.js after we've built elm (because we use elm to generate some of the JavaScript),
28+-- but before cabal does the install file copy step
29+
30+-- Assumptions
31+-- Elm.cabal expects the generated files to end up in dist/data
32+rtsDir lbi = (buildDir lbi) </> ".." </> "data" -- git won't look in dist + cabal will clean it
33+jsDir lbi = (buildDir lbi) </> ".." </> "js"
34+
35+-- The runtime is called:
36+rts lbi = (rtsDir lbi) </> "elm-runtime.js"
37+
38+-- The json file is called:
39+
40+-- The elm-docs executable is called:
41+elmDoc = "elm-doc"
42+elm_doc lbi = (buildDir lbi) </> elmDoc </> elmDoc
43+
44+types lbi = (rtsDir lbi) </> "docs.json"
45+
46+-- buildDir with LocalBuildInfo points to "dist/build" (usually)
47+elm lbi = (buildDir lbi) </> "elm" </> "elm"
48+
49+-- Care! This appears to be based on an unstable API
50+-- See: http://www.haskell.org/cabal/release/cabal-latest/doc/API/Cabal/Distribution-Simple.html#2
51+
52+
53+main :: IO ()
54+main = defaultMainWithHooks simpleUserHooks { {-- buildHook = myBuild, --} postBuild = myPostBuildWithTypes }
55+
56+
57+-- Build
58+
59+-- Not currently used. buildTypes is in 'myPostBuildWithTypes'
60+-- If using this again, change postBuild to 'myPostBuild'
61+-- Purpose is to make sure docs.json was built before elm exec was (as elm exec depended on it)
62+-- This is no longer true and the code below seems to affect cabal's build dependencies
63+myBuild :: PackageDescription -> LocalBuildInfo -> UserHooks -> BuildFlags -> IO ()
64+myBuild pd lbi uh bf = do
65+ putStrLn $ "Custom build step started: compile " ++ elmDoc
66+ withExe pd (\x -> putStrLn (exeName x))
67+ buildHook simpleUserHooks (filterExe elmDoc pd) (filterLBI elmDoc lbi) uh bf
68+ putStrLn "Custom build step started: build docs.json"
69+ buildTypes lbi -- see note(1) below
70+ putStrLn "Custom build step started: compile everything"
71+ buildHook simpleUserHooks pd lbi uh bf
72+
73+-- note(1): We use to include docs.json directly into LoadLibraries at compile time
74+-- If docs.json is used in other (template) haskell files, they should be copied
75+-- and compiled in a separate directory (eg, dist/copiedSrc).
76+-- This is to make sure they are re-compiled on docs.json changes.
77+-- Copying is a better solution than 'touch'ing the source files
78+-- (touch is non-portable and confusing wrt RCS).
79+
80+-- In the PackageDescription, the list of stuff to build is held in library (in a Maybe)
81+-- and the executables list. We want a PackageDescription that only mentions the executable 'name'
82+filterExe name pd = pd {
83+ library = Nothing,
84+ executables = filter (\x -> (exeName x == name)) (executables pd)
85+ }
86+
87+-- It's not enough to fix the PackageDescription, we also have to fix the LocalBuildInfo.
88+-- This includes the component build order (data ComponentName) which is horribly internal.
89+filterLBI name lbi = lbi {
90+ libraryConfig = Nothing,
91+ compBuildOrder = [CExeName name],
92+ executableConfigs = filter (\a -> (fst a == name)) (executableConfigs lbi)
93+ }
94+
95+buildTypes lbi = do
96+ createDirectoryIfMissing False (rtsDir lbi) -- dist should already exist
97+ files <- getFiles ".elm" "libraries"
98+ system (elm_doc lbi ++ " " ++ unwords files ++ " > " ++ (types lbi))
99+ putStrLn $ "Custom build step completed: " ++ elmDoc
100+
101+
102+-- Post Build
103+
104+myPostBuildWithTypes :: Args -> BuildFlags -> PackageDescription -> LocalBuildInfo -> IO ()
105+myPostBuildWithTypes as bfs pd lbi = do
106+ putStrLn "Custom build step started: build docs.json"
107+ buildTypes lbi -- see note(1) below
108+ myPostBuild as bfs pd lbi
109+
110+myPostBuild :: Args -> BuildFlags -> PackageDescription -> LocalBuildInfo -> IO ()
111+myPostBuild as bfs pd lbi = do
112+ putStrLn "Custom post build step started: build elm-runtime.js"
113+ buildRuntime lbi
114+ postBuild simpleUserHooks as bfs pd lbi
115+
116+getFiles ext dir = do
117+ contents <- map (dir </>) `fmap` getDirectoryContents dir
118+ let files = filter (\f -> takeExtension f == ext) contents
119+ dirs = filter (not . hasExtension) contents
120+ filess <- mapM (getFiles ext) dirs
121+ return (files ++ concat filess)
122+
123+appendJS lbi file = do
124+ putStrLn (dropExtension file)
125+ str <- readFile file
126+ length str `seq` return ()
127+ appendFile (rts lbi) str
128+
129+appendElm lbi file = do
130+ jsFile <- runElm lbi file
131+ appendJS lbi jsFile
132+
133+-- replace 'system' call with 'runProcess' which handles args better and allows env variable
134+-- "Elm_datadir" which is used by LoadLibraries to find docs.json
135+runElm :: LocalBuildInfo -> String -> IO FilePath
136+runElm lbi file = do
137+ rts_c <- canonicalizePath (rts lbi) -- dist/data/elm-runtime.js
138+ let js = jsDir lbi -- dist/js
139+ let j = dropFileName (js </> file) -- dist/js/libraries/
140+ createDirectoryIfMissing True j -- must do before any canonicalization
141+ out_c <- canonicalizePath js -- dist/js (root folder)
142+ elm_c <- canonicalizePath (elm lbi) -- dist/build/elm/elm
143+ rtd_c <- canonicalizePath (rtsDir lbi) -- dist/data (for docs.json)
144+ handle <- runProcess elm_c ["--only-js", "--no-prelude", "--output-directory="++out_c, file]
145+ Nothing (Just [("Elm_datadir", rtd_c)]) Nothing Nothing Nothing
146+ exitCode <- waitForProcess handle
147+ return $ j </> replaceExtension (takeFileName file) ".js"
148+
149+
150+buildRuntime lbi = do
151+ createDirectoryIfMissing False (rtsDir lbi) -- dist should already exist
152+ writeFile (rts lbi) "Elm = {}; Elm.Native = {}; Elm.Native.Graphics = {};\n\
153+ \Elm.Graphics = {}; ElmRuntime = {}; ElmRuntime.Render = {}\n"
154+ mapM_ (appendJS lbi) =<< getFiles ".js" "libraries"
155+ mapM_ (appendElm lbi) =<< getFiles ".elm" "libraries"
156+ mapM_ (appendJS lbi) =<< getFiles ".js" "runtime"
elm/changelog.txt → changelog.txtrenamed

The content is the same.

elm/src/Compiler.hs → compiler/Compiler.hsrenamed+32−24
@@ -2,10 +2,11 @@
2module Main where
2module Main where
3
3
4import Data.Either (lefts, rights)
4import Data.Either (lefts, rights)
5−import Data.List (intersect, intercalate)
5+import Data.List (intersect, intercalate,lookup)
6import Data.Maybe (fromMaybe)
6import Data.Maybe (fromMaybe)
7import Data.Version (showVersion)
7import Data.Version (showVersion)
8import System.Console.CmdArgs
8import System.Console.CmdArgs
9+import System.Exit
9import System.FilePath
10import System.FilePath
10import Text.Blaze.Html.Renderer.String (renderHtml)
11import Text.Blaze.Html.Renderer.String (renderHtml)
11
12
@@ -16,6 +17,7 @@ import Ast
16import Initialize
17import Initialize
17import CompileToJS
18import CompileToJS
18import GenerateHtml
19import GenerateHtml
20+import qualified Libraries as Libraries
19import Paths_Elm
21import Paths_Elm
20
22
21data ELM =
23data ELM =
@@ -25,7 +27,8 @@ data ELM =
25 , separate_js :: Bool
27 , separate_js :: Bool
26 , only_js :: Bool
28 , only_js :: Bool
27 , import_js :: [FilePath]
29 , import_js :: [FilePath]
28− , generate_noscript :: Bool
30+ , no_prelude :: Bool
31+ , noscript :: Bool
29 , minify :: Bool
32 , minify :: Bool
30 , output_directory :: Maybe FilePath
33 , output_directory :: Maybe FilePath
31 }
34 }
@@ -38,7 +41,8 @@ elm = ELM { make = False &= help "automatically compile dependencies."
38 , separate_js = False &= help "Compile to separate HTML and JS files."
41 , separate_js = False &= help "Compile to separate HTML and JS files."
39 , only_js = False &= help "Compile only to JavaScript."
42 , only_js = False &= help "Compile only to JavaScript."
40 , import_js = [] &= typFile &= help "Include a JavaScript file before the body of the Elm program. Can be used many times. Files will be included in the given order."
43 , import_js = [] &= typFile &= help "Include a JavaScript file before the body of the Elm program. Can be used many times. Files will be included in the given order."
44+ , no_prelude = False &= help "Do not import Prelude by default, used only when compiling standard libraries."
41− , generate_noscript = True &= help "Add generated <noscript> tag to HTML output."
45+ , noscript = True &= help "Add generated <noscript> tag to HTML output."
42 , minify = False &= help "Minify generated JavaScript"
46 , minify = False &= help "Minify generated JavaScript"
43 , output_directory = Nothing &= typFile &= help "Output files to directory specified. Defaults to the location of original file."
47 , output_directory = Nothing &= typFile &= help "Output files to directory specified. Defaults to the location of original file."
44 } &=
48 } &=
@@ -47,37 +51,41 @@ elm = ELM { make = False &= help "automatically compile dependencies."
47
51
48main = do
52main = do
49 args <- cmdArgs elm
53 args <- cmdArgs elm
50− mini <- getDataFileName ("elm-runtime-" ++ showVersion version ++ ".js")
54+ mini <- getDataFileName "elm-runtime.js"
51 compileArgs mini args
55 compileArgs mini args
52
56
53−compileArgs mini (ELM _ [] _ _ _ _ _ _ _) =
57+compileArgs mini flags =
58+ case files flags of
54− putStrLn "Usage: elm [OPTIONS] [FILES]\nFor more help: elm --help"
59+ [] -> putStrLn "Usage: elm [OPTIONS] [FILES]\nFor more help: elm --help"
55−compileArgs mini (ELM make files rtLoc split only js nscrpt isMini outputDir) =
56− mapM_ (fileTo isMini make what js nscrpt outputDir loc) files
60+ fs -> mapM_ (fileTo flags what loc) fs
57− where loc = fromMaybe mini rtLoc
61+ where loc = fromMaybe mini (runtime flags)
58− what | only = JS
62+ what | only_js flags = JS
59− | split = Split
63+ | separate_js flags = Split
60− | otherwise = HTML
64+ | otherwise = HTML
61
65
62data What = JS | HTML | Split
66data What = JS | HTML | Split
63
67
64−fileTo isMini make what jsFiles noscript outputDir rtLoc file = do
68+fileTo flags what rtLoc file = do
65− let jsStyle = if isMini then Minified else Readable
69+ let jsStyle = if minify flags then Minified else Readable
66− formatJS = if isMini then BS.unpack . JS.minify . BS.pack else id
70+ formatJS = if minify flags then BS.unpack . JS.minify . BS.pack else id
67− ems <- build make file
71+ prelude = not (no_prelude flags)
72+ ems <- if make flags then build prelude file
73+ else do src <- readFile file
74+ return (fmap (:[]) (buildFromSource prelude src))
68− jss <- concat `fmap` mapM readFile jsFiles
75+ jss <- concat `fmap` mapM readFile (import_js flags)
69 case ems of
76 case ems of
70− Left err -> putStrLn $ "Error while compiling " ++ file ++ ":\n" ++ err
77+ Left err -> do putStrLn $ "Error while compiling " ++ file ++ ":\n" ++ err
78+ exitFailure
71− Right ms ->
79+ Right ms' ->
72− let path = fromMaybe "" outputDir </> file
80+ let path = fromMaybe "" (output_directory flags) </> file
73 js = replaceExtension path ".js"
81 js = replaceExtension path ".js"
74 html = replaceExtension path ".html"
82 html = replaceExtension path ".html"
75− pairs = map ((,) (fst ms)) (snd ms)
83+ ms = if no_prelude flags then ms' else map Libraries.addPrelude ms'
76− txt = jss ++ concatMap jsModule pairs
84+ txt = jss ++ concatMap jsModule ms
77 in case what of
85 in case what of
78 JS -> writeFile js (formatJS txt)
86 JS -> writeFile js (formatJS txt)
79 HTML -> writeFile html . renderHtml $
87 HTML -> writeFile html . renderHtml $
80− modulesToHtml jsStyle "" rtLoc jss noscript pairs
88+ modulesToHtml jsStyle "" rtLoc jss (noscript flags) ms
81 Split ->
89 Split ->
82− do writeFile html . renderHtml $ linkedHtml rtLoc js pairs
90+ do writeFile html . renderHtml $ linkedHtml rtLoc js ms
83 writeFile js (formatJS txt)
91 writeFile js (formatJS txt)
compiler/Docs.hsnew file+65
@@ -0,0 +1,65 @@
1+
2+module Main where
3+
4+import Ast
5+import Control.Applicative ((<$>), (<*>))
6+import Data.List (intercalate)
7+import Data.Maybe (catMaybes)
8+import Parse.Library
9+import Parse.Modules (moduleDef)
10+import Text.Parsec hiding (newline,spaces)
11+import System.Environment
12+import System.Exit
13+
14+
15+main = do
16+ srcs <- mapM readFile =<< getArgs
17+ case mapM docParse srcs of
18+ Left err -> putStrLn err >> exitFailure
19+ Right ms -> putStrLn (toModules ms)
20+
21+toModules ms = wrap (intercalate ",\n " (map toModule ms))
22+ where wrap s = "{ \"modules\" : [\n " ++ s ++ "\n ]\n}"
23+
24+toModule (name, values) =
25+ "{ \"name\" : " ++ show name ++ ",\n " ++
26+ "\"values\" : [\n " ++ vs ++ "\n ]\n }"
27+ where vs = intercalate ",\n " (map toValue values)
28+
29+toValue (name, tipe, desc) =
30+ "{ \"name\" : " ++ show name ++
31+ ",\n \"type\" : " ++ show tipe ++
32+ ",\n \"desc\" : " ++ show desc ++ "\n }"
33+
34+docParse :: String -> Either String (String, [(String, String, String)])
35+docParse = setupParser $ do
36+ optional freshLine
37+ (names, exports) <- option (["Main"],[]) moduleDef
38+ info <- many (annotation exports <|> try skip <|> end)
39+ return (intercalate "." names, catMaybes info)
40+ where
41+ skip = manyTill anyChar simpleNewline >> return Nothing
42+ end = many1 anyChar >> return Nothing
43+
44+annotation :: [String] -> IParser (Maybe (String, String, String))
45+annotation exports =
46+ try ((\c n t -> export (n,t,c)) <$> comment <*> (try adt <|> name) <*> tipe)
47+ where
48+ comment = concatMap clip <$> many lineComment
49+ clip str = case str of { ' ':rest -> rest ; _ -> str } ++ "\n"
50+
51+ name = do v <- lowVar <|> parens symOp
52+ whitespace ; hasType ; whitespace ; return v
53+
54+ tipe = manyTill anyChar (try (simpleNewline >> notFollowedBy (string " ")))
55+
56+ export info@(name,_,_) =
57+ if null exports || name `elem` exports then Just info else Nothing
58+
59+ adt = lookAhead ((string "data" <|> string "type") >> whitespace >> capVar)
60+
61+
62+setupParser p source =
63+ case iParse p "" source of
64+ Right result -> Right result
65+ Left err -> Left $ "Parse error at " ++ show err
elm/src/Gen/Cases.hs → compiler/Gen/Cases.hsrenamed+9−2
@@ -57,8 +57,15 @@ match vs cs def
57
57
58matchVar :: [String] -> [([Pattern],CExpr)] -> Match -> GuidCounter Match
58matchVar :: [String] -> [([Pattern],CExpr)] -> Match -> GuidCounter Match
59matchVar (v:vs) cs def = match vs (map subVar cs) def
59matchVar (v:vs) cs def = match vs (map subVar cs) def
60+ where
61+ subVar (p:ps, ce@(C t s e)) =
62+ let ctx = C t s in
63+ (ps, case p of
60− where subVar (PVar x : ps, C t s e) = (ps, C t s $ subst x (Var v) e)
64+ PVar x -> C t s $ subst x (Var v) e
61− subVar (PAnything : ps, ce) = (ps, ce)
65+ PAnything -> ce
66+ PRecord fs ->
67+ ctx $ foldr (\x -> subst x (Access (ctx (Var v)) x)) e fs
68+ )
62
69
63matchCon :: [String] -> [([Pattern],CExpr)] -> Match -> GuidCounter Match
70matchCon :: [String] -> [([Pattern],CExpr)] -> Match -> GuidCounter Match
64matchCon (v:vs) cs def = (flip (Match v) def) `liftM` mapM toClause css
71matchCon (v:vs) cs def = (flip (Match v) def) `liftM` mapM toClause css
compiler/Gen/CompileToJS.hsnew file+338
@@ -0,0 +1,338 @@
1+module CompileToJS (showErr, jsModule) where
2+
3+import Control.Arrow (first,second)
4+import Control.Monad (liftM,(<=<),join,ap)
5+import Data.Char (isAlpha,isDigit)
6+import Data.List (intercalate,sortBy,inits,foldl')
7+import qualified Data.Map as Map
8+import Data.Either (partitionEithers)
9+import qualified Text.Pandoc as Pan
10+
11+import Ast
12+import Context
13+import Rename (derename)
14+import Cases
15+import Guid
16+import Rename (deprime)
17+import Types.Types ( Type(RecordT) )
18+
19+showErr :: String -> String
20+showErr err = globalAssign "Elm.Main" (jsFunc "elm" body)
21+ where msg = show . concatMap (++"<br>") . lines $ err
22+ body = "var T = Elm.Text(elm);\n\
23+ \return { main : T.text(T.monospace(" ++ msg ++ ")) };"
24+
25+indent = concatMap f
26+ where f '\n' = "\n "
27+ f c = [c]
28+
29+internalImports =
30+ [ ("N" , "Elm.Native"),
31+ ("_N", "N.Utils(elm)"),
32+ ("_L", "N.List(elm)"),
33+ ("_E", "N.Error(elm)"),
34+ ("_str", "N.JavaScript(elm).toString")
35+ ]
36+
37+parens s = "(" ++ s ++ ")"
38+brackets s = "{" ++ s ++ "}"
39+jsObj = brackets . intercalate ", "
40+jsList ss = "["++ intercalate "," ss ++"]"
41+jsFunc args body = "function(" ++ args ++ "){" ++ indent body ++ "}"
42+assign x e = "\nvar " ++ x ++ " = " ++ e ++ ";"
43+ret e = "\nreturn "++ e ++";"
44+iff a b c = a ++ "?" ++ b ++ ":" ++ c
45+quoted s = "'" ++ concatMap f s ++ "'"
46+ where f '\n' = "\\n"
47+ f '\'' = "\\'"
48+ f '\t' = "\\t"
49+ f '\"' = "\\\""
50+ f '\\' = "\\\\"
51+ f c = [c]
52+
53+globalAssign n e = "\n" ++ assign' n e ++ ";"
54+assign' n e = n ++ " = " ++ e
55+
56+jsModule (Module names exports imports stmts) =
57+ setup ("Elm":modNames) ++ globalAssign ("Elm." ++ modName) (jsFunc "elm" program)
58+ where
59+ modNames = if null names then ["Main"] else names
60+ modName = intercalate "." modNames
61+ includes = concatMap jsImport imports
62+ body = stmtsToJS stmts
63+ defs = assign "$op" "{}"
64+ program = "\nvar " ++ usefulFuncs ++ ";" ++ defs ++ includes ++ body ++
65+ setup ("elm":"Native":modNames) ++
66+ assign "_" ("elm.Native." ++ modName ++ "||{}") ++
67+ getExports exports stmts ++ setup ("elm":modNames) ++
68+ ret (assign' ("elm." ++ modName) "_") ++ "\n"
69+ setup modNames = concatMap (\n -> globalAssign n $ n ++ "||{}") .
70+ map (intercalate ".") . drop 2 . inits $ init modNames
71+ usefulFuncs = intercalate ", " (map (uncurry assign') internalImports)
72+
73+getExports names stmts = "\n"++ intercalate ";\n" (op : map fnPair fns)
74+ where exNames n = either derename id n `elem` names
75+ exports | null names = concatMap get stmts
76+ | otherwise = filter exNames (concatMap get stmts)
77+
78+ (fns,ops) = partitionEithers exports
79+
80+ opPair op = "'" ++ op ++ "' : $op['" ++ op ++ "']"
81+ fnPair fn = let fn' = derename fn in "_." ++ fn' ++ " = " ++ fn
82+
83+ op = ("_.$op = "++) . jsObj $ map opPair ops
84+
85+ get' (FnDef x _ _) = Left x
86+ get' (OpDef op _ _ _) = Right op
87+ get s = case s of Definition d -> [ get' d ]
88+ Datatype _ _ tcs -> map (Left . fst) tcs
89+ ImportEvent _ _ x _ -> [ Left x ]
90+ ExportEvent _ _ _ -> []
91+ TypeAlias _ _ _ -> []
92+ TypeAnnotation _ _ -> []
93+
94+
95+jsImport (modul, how) =
96+ case how of
97+ As name -> assign name ("Elm." ++ modul ++ parens "elm")
98+ Hiding vs -> include ++ " var hiding=" ++ (jsObj $ map (++":1") vs) ++
99+ "; for(var k in _){if(k in hiding)continue;" ++
100+ "eval('var '+k+'=_[\"'+k+'\"]')}"
101+ Importing vs -> include ++ named
102+ where
103+ imprt v = assign' v ("_." ++ v)
104+ def (o:p) = imprt (if isOp o then "$op['" ++ o:p ++ "']" else deprime (o:p))
105+ named = if null vs then "" else "\nvar " ++ intercalate ", " (map def vs) ++ ";"
106+ where
107+ include = "\nvar _ = Elm." ++ modul ++ parens "elm" ++ ";" ++ setup modul
108+ setup moduleName = " var " ++ concatMap (++";") (defs ++ [assign' moduleName "_"])
109+ where
110+ defs = map (\n -> assign' n (n ++ "||{}")) (subnames moduleName)
111+ subnames = map (intercalate ".") . tail . inits . init . split
112+ split names = case go [] names of
113+ (name, []) -> [name]
114+ (name, ns) -> name : split ns
115+ go name str = case str of
116+ '.':rest -> (reverse name, rest)
117+ c:rest -> go (c:name) rest
118+ [] -> (reverse name, [])
119+
120+
121+
122+stmtsToJS :: [Statement] -> String
123+stmtsToJS stmts = run $ do program <- mapM toJS (sortBy cmpStmt stmts)
124+ return (concat program)
125+ where
126+ cmpStmt s1 s2 = compare (valueOf s1) (valueOf s2)
127+ valueOf s = case s of
128+ Datatype _ _ _ -> 1
129+ ImportEvent _ _ _ _ -> 2
130+ Definition (FnDef f [] _) ->
131+ if derename f == "main" then 5 else 4
132+ Definition _ -> 3
133+ ExportEvent _ _ _ -> 6
134+ TypeAlias _ _ _ -> 0
135+ TypeAnnotation _ _ -> 0
136+
137+class ToJS a where
138+ toJS :: a -> GuidCounter String
139+
140+instance ToJS Def where
141+ toJS (FnDef x [] e) = assign x `liftM` toJS' e
142+ toJS (FnDef f as e) = (assign f . wrapper . func) `liftM` toJS' e
143+ where
144+ func body = jsFunc (intercalate ", " as) (ret body)
145+ wrapper e | length as == 1 = e
146+ | otherwise = 'F' : show (length as) ++ parens e
147+ toJS (OpDef op a1 a2 e) =
148+ do body <- toJS' e
149+ let func = "F2" ++ parens (jsFunc (a1 ++ ", " ++ a2) (ret body))
150+ return (globalAssign ("$op['" ++ op ++ "']") func)
151+
152+instance ToJS Statement where
153+ toJS stmt =
154+ case stmt of
155+ Definition d -> toJS d
156+ Datatype _ _ tcs -> concat `liftM` mapM (toJS . toDef) tcs
157+ where toDef (name,args) =
158+ let vars = map (('a':) . show) [1..length args] in
159+ Definition . FnDef name vars . noContext $
160+ Data (derename name) (map (noContext . Var) vars)
161+ ImportEvent js base elm _ ->
162+ do v <- toJS' base
163+ return $ concat [ "\nvar " ++ elm ++ "=Elm.Signal(elm).constant(" ++ v ++ ");"
164+ , "\ndocument.addEventListener('", js
165+ , "_' + elm.id, function(e) { elm.notify(", elm
166+ , ".id, e.value); });" ]
167+ ExportEvent js elm _ ->
168+ return $ concat [ "\nlift(function(v) { "
169+ , "var e = document.createEvent('Event');"
170+ , "e.initEvent('", js, "_' + elm.id, true, true);"
171+ , "e.value = v;"
172+ , "document.dispatchEvent(e); return v; })(", elm, ");" ]
173+ TypeAnnotation _ _ -> return ""
174+ TypeAlias n _ t -> return ""
175+
176+toJS' :: CExpr -> GuidCounter String
177+toJS' (C txt span expr) =
178+ case expr of
179+ MultiIf ps -> multiIfToJS span ps
180+ Case e cases -> caseToJS span e cases
181+ _ -> toJS expr
182+
183+remove x e = "_N.remove('" ++ x ++ "', " ++ e ++ ")"
184+addField x v e = "_N.insert('" ++ x ++ "', " ++ v ++ ", " ++ e ++ ")"
185+setField fs e = "_N.replace(" ++ jsList (map f fs) ++ ", " ++ e ++ ")"
186+ where f (x,v) = "['" ++ x ++ "'," ++ v ++ "]"
187+access x e = e ++ "." ++ x
188+makeRecord kvs = record `liftM` collect kvs
189+ where
190+ combine r (k,v) = Map.insertWith (++) k v r
191+ collect = liftM (foldl' combine Map.empty) . mapM prep
192+ prep (k, as, e@(C t s _)) =
193+ do v <- toJS' (foldr (\x e -> C t s $ Lambda x e) e as)
194+ return (k,[v])
195+ fields fs =
196+ brackets ("\n "++intercalate ",\n " (map (\(k,v) -> k++":"++v) fs))
197+ hidden = fields . map (second jsList) .
198+ filter (not . null . snd) . Map.toList . Map.map tail
199+ record kvs = fields . (("_", hidden kvs) :) . Map.toList . Map.map head $ kvs
200+
201+
202+instance ToJS Expr where
203+ toJS expr =
204+ case expr of
205+ Var x -> return $ x
206+ Chr c -> return $ quoted [c]
207+ Str s -> return $ "_str" ++ parens (quoted s)
208+ IntNum n -> return $ show n
209+ FloatNum n -> return $ show n
210+ Boolean b -> return $ if b then "true" else "false"
211+ Range lo hi -> jsRange `liftM` toJS' lo `ap` toJS' hi
212+ Access e x -> access x `liftM` toJS' e
213+ Remove e x -> remove x `liftM` toJS' e
214+ Insert e x v -> addField x `liftM` toJS' v `ap` toJS' e
215+ Modify e fs -> do fs' <- (mapM (\(x,v) -> (,) x `liftM` toJS' v) fs)
216+ setField fs' `liftM` toJS' e
217+ Record fs -> makeRecord fs
218+ Binop op e1 e2 -> binop op `liftM` toJS' e1 `ap` toJS' e2
219+
220+ If eb et ef ->
221+ parens `liftM` (iff `liftM` toJS' eb `ap` toJS' et `ap` toJS' ef)
222+
223+ Lambda v e -> liftM (jsFunc v . ret) (toJS' e)
224+
225+ App e1 e2 -> jsApp e1 e2
226+ Let defs e -> jsLet defs e
227+ Data name es ->
228+ do fs <- mapM toJS' es
229+ return $ case name of
230+ "Nil" -> jsNil
231+ "Cons" -> jsCons (head fs) ((head . tail) fs)
232+ _ -> jsObj $ ("ctor:" ++ show name) : fields
233+ where fields = zipWith (\n e -> "_" ++ show n ++ ":" ++ e) [0..] fs
234+
235+ Markdown doc -> return $ "text('" ++ pad ++ md ++ pad ++ "')"
236+ where pad = "<div style=\"height:0;width:0;\">&nbsp;</div>"
237+ md = formatMarkdown $ Pan.writeHtmlString Pan.def doc
238+
239+jsApp e1 e2 =
240+ do f <- toJS' func
241+ as <- mapM toJS' args
242+ return $ case as of
243+ [a] -> f ++ parens a
244+ _ -> "A" ++ show (length as) ++ parens (intercalate ", " (f:as))
245+ where
246+ (func, args) = go [e2] e1
247+ go args e =
248+ case e of
249+ (C _ _ (App e1 e2)) -> go (e2 : args) e1
250+ _ -> (e, args)
251+
252+formatMarkdown = concatMap f
253+ where f '\'' = "\\'"
254+ f '\n' = "\\n"
255+ f '"' = "\""
256+ f c = [c]
257+
258+multiIfToJS span ps =
259+ case last ps of
260+ (C _ _ (Var "otherwise"), e) -> toJS' e >>= \b -> format b (init ps)
261+ _ -> format ("_E.If" ++ parens (quoted (show span))) ps
262+ where
263+ format base ps =
264+ foldr (\c e -> parens $ c ++ " : " ++ e) base `liftM` mapM f ps
265+ f (b,e) = do b' <- toJS' b
266+ e' <- toJS' e
267+ return (b' ++ " ? " ++ e')
268+
269+jsLet defs e' = do ds <- jsDefs defs
270+ e <- toJS' e'
271+ return $ jsFunc "" (concat ds ++ ret e) ++ "()"
272+ where
273+ jsDefs defs = mapM toJS (sortBy f defs)
274+ f a b = compare (valueOf a) (valueOf b)
275+ valueOf (FnDef _ args _) = min 1 (length args)
276+ valueOf (OpDef _ _ _ _) = 1
277+
278+caseToJS span e ps = do
279+ match <- caseToMatch ps
280+ e' <- toJS' e
281+ let (match',stmt) = case (match,e) of
282+ (Match name _ _, C _ _ (Var x)) -> (matchSubst [(name,x)] match, "")
283+ (Match name _ _, _) -> (match, assign name e')
284+ _ -> (match, "")
285+ matches <- matchToJS span match'
286+ return $ "function(){ " ++ stmt ++ matches ++ " }()"
287+
288+matchToJS span match =
289+ case match of
290+ Match name clauses def ->
291+ do cases <- concat `liftM` mapM (clauseToJS span name) clauses
292+ finally <- matchToJS span def
293+ return $ concat [ "\nswitch (", name, ".ctor) {",
294+ indent cases, "\n}", finally ]
295+ Fail -> return ("_E.Case" ++ parens (quoted (show span)))
296+ Break -> return "break;"
297+ Other e -> ret `liftM` toJS' e
298+ Seq ms -> concat `liftM` mapM (matchToJS span) (dropEnd [] ms)
299+ where
300+ dropEnd acc [] = acc
301+ dropEnd acc (m:ms) =
302+ case m of
303+ Other _ -> acc ++ [m]
304+ _ -> dropEnd (acc ++ [m]) ms
305+
306+clauseToJS span var (Clause name vars e) = do
307+ let vars' = map (\n -> var ++ "._" ++ show n) [0..]
308+ s <- matchToJS span $ matchSubst (zip vars vars') e
309+ return $ concat [ "\ncase ", quoted name, ":", indent s ]
310+
311+jsNil = "_L.Nil"
312+jsCons e1 e2 = "_L.Cons(" ++ e1 ++ "," ++ e2 ++ ")"
313+jsRange e1 e2 = "_L.range" ++ parens (e1 ++ "," ++ e2)
314+jsCompare e1 e2 op = parens ("_N.cmp(" ++ e1 ++ "," ++ e2 ++ ").ctor" ++ op)
315+
316+binop (o:p) e1 e2
317+ | isAlpha o || '_' == o = (o:p) ++ parens e1 ++ parens e2
318+ | otherwise =
319+ let ops = ["+","-","*","/","&&","||"] in
320+ case o:p of
321+ "::" -> jsCons e1 e2
322+ "++" -> "_L.append" ++ parens (e1 ++ "," ++ e2)
323+ "$" -> e1 ++ parens e2
324+ "<|" -> e1 ++ parens e2
325+ "|>" -> e2 ++ parens e1
326+ "." -> jsFunc "x" . ret $ e1 ++ parens (e2 ++ parens "x")
327+ "^" -> "Math.pow(" ++ e1 ++ "," ++ e2 ++ ")"
328+ "==" -> "_N.eq(" ++ e1 ++ "," ++ e2 ++ ")"
329+ "/=" -> "!_N.eq(" ++ e1 ++ "," ++ e2 ++ ")"
330+ "<" -> jsCompare e1 e2 "==='LT'"
331+ ">" -> jsCompare e1 e2 "==='GT'"
332+ "<=" -> jsCompare e1 e2 "!=='GT'"
333+ ">=" -> jsCompare e1 e2 "!=='LT'"
334+ "<~" -> "A2(lift," ++ e1 ++ "," ++ e2 ++ ")"
335+ "~" -> "A3(lift2,F2(function(f,x){return f(x)}),"++e1++","++e2++")"
336+ _ | elem (o:p) ops -> parens (e1 ++ (o:p) ++ e2)
337+ | otherwise -> concat [ "$op['", o:p, "']"
338+ , parens e1, parens e2 ]
elm/src/Gen/ExtractNoscript.hs → compiler/Gen/ExtractNoscript.hsrenamed−1
@@ -36,7 +36,6 @@ instance Extract Expr where
36 (_ , ss1 , ss2 ) -> ss1 ++ ss2
36 (_ , ss1 , ss2 ) -> ss1 ++ ss2
37 Lambda v e -> f e
37 Lambda v e -> f e
38 App (C _ _ (App (C _ _ (Var "link")) src)) txt -> linkExtract src txt
38 App (C _ _ (App (C _ _ (Var "link")) src)) txt -> linkExtract src txt
39− App (C _ _ (App (C _ _ (Var "Graphics.link")) src)) txt -> linkExtract src txt
40 App (C _ _ (App (C _ _ (Var "Text.link")) src)) txt -> linkExtract src txt
39 App (C _ _ (App (C _ _ (Var "Text.link")) src)) txt -> linkExtract src txt
41 App (C _ _ (Var "header")) e -> tag "h1" e
40 App (C _ _ (Var "header")) e -> tag "h1" e
42 App (C _ _ (Var "bold")) e -> tag "b" e
41 App (C _ _ (Var "bold")) e -> tag "b" e
compiler/Gen/GenerateHtml.hsnew file+75
@@ -0,0 +1,75 @@
1+{-# LANGUAGE OverloadedStrings #-}
2+module GenerateHtml (generateHtml,
3+ modulesToHtml, linkedHtml,
4+ JSStyle (..)
5+ ) where
6+
7+import Data.List (intercalate)
8+import Text.Blaze (preEscapedToMarkup)
9+import Text.Blaze.Html (Html)
10+import qualified Text.Blaze.Html5 as H
11+import Text.Blaze.Html5 ((!))
12+import qualified Text.Blaze.Html5.Attributes as A
13+
14+import Text.Jasmine (minify)
15+import qualified Data.ByteString.Lazy.Char8 as BS
16+
17+import Ast
18+import Initialize (buildFromSource)
19+import CompileToJS
20+import ExtractNoscript
21+import Libraries as Libraries
22+
23+data JSStyle = Minified | Readable
24+
25+makeScript :: JSStyle -> Either String String -> H.Html
26+makeScript _ (Left s) =
27+ H.script ! A.type_ "text/javascript" ! A.src (H.toValue s) $ ""
28+makeScript jsStyle (Right s) =
29+ H.script ! A.type_ "text/javascript" $ preEscapedToMarkup content
30+ where content = case jsStyle of
31+ Minified -> BS.unpack . minify . BS.pack $ s
32+ Readable -> s
33+
34+-- |This function compiles Elm code into simple HTML.
35+--
36+-- Usage example:
37+--
38+-- > generateHtml "/elm-min.js" "Some title" [elmFile|elm-source/somePage.elm|]
39+generateHtml :: String -- ^ Location of elm-runtime.js as expected by the browser
40+ -> String -- ^ The page title
41+ -> String -- ^ The elm source code.
42+ -> Html
43+generateHtml libLoc title source =
44+ case buildFromSource True source of
45+ Right modul -> modulesToHtml Readable title libLoc [] True [modul]
46+ Left err -> createHtml Readable libLoc title (Right $ showErr err)
47+ (H.noscript "") "Main"
48+
49+
50+modulesToHtml jsStyle title libLoc jss nscrpt modules =
51+ createHtml jsStyle libLoc title' js noscript altTitle
52+ where
53+ js = Right $ jss ++ concatMap jsModule modules
54+ noscript = if nscrpt then extractNoscript $ last modules else ""
55+ title' = if null title then altTitle else title
56+ altTitle = intercalate "." names
57+ where Module names _ _ _ = last modules
58+
59+
60+linkedHtml rtLoc jsLoc modules =
61+ createHtml Readable rtLoc title (Left jsLoc) (H.noscript "") title
62+ where
63+ title = (\(Module names _ _ _) -> intercalate "." names) (last modules)
64+
65+
66+createHtml jsStyle libLoc title js noscript moduleToLoad =
67+ H.docTypeHtml $ do
68+ H.head $ do
69+ H.meta ! A.charset "UTF-8"
70+ H.title . H.toHtml $ title
71+ makeScript Readable (Left libLoc)
72+ makeScript jsStyle js
73+ H.body $ do
74+ H.script ! A.type_ "text/javascript" $ preEscapedToMarkup ("Elm.fullscreen(Elm." ++ moduleToLoad ++ ")" :: String)
75+ H.noscript $ preEscapedToMarkup noscript
compiler/Initialize.hsnew file+97
@@ -0,0 +1,97 @@
1+module Initialize (build, buildFromSource) where
2+
3+import Control.Applicative ((<$>))
4+import Control.Monad.Error
5+import Data.List (lookup,nub)
6+import qualified Data.Map as Map
7+
8+import Ast
9+import Data.Either (lefts,rights)
10+import Data.List (intercalate,partition)
11+import Parse.Parser (parseProgram, preParse)
12+import Rename
13+import qualified Libraries as Libs
14+import Types.Types ((-:))
15+import Types.Hints (hints)
16+import Types.Unify
17+import Types.Alias (dealias, mistakes)
18+import Optimize
19+import CompileToJS (jsModule)
20+
21+checkMistakes :: Module -> Either String Module
22+checkMistakes modul@(Module name ex im stmts) =
23+ case mistakes stmts of
24+ m:ms -> Left (unlines (m:ms))
25+ [] -> return modul
26+
27+checkTypes :: Module -> Either String Module
28+checkTypes modul =
29+ do subs <- unify hints modul
30+ subs `seq` return (optimize (renameModule modul))
31+
32+check :: Module -> Either String Module
33+check = checkMistakes >=> checkTypes
34+
35+buildFromSource :: Bool -> String -> Either String Module
36+buildFromSource withPrelude src = (check . add) =<< (parseProgram src)
37+ where add = if withPrelude then Libs.addPrelude else id
38+
39+build :: Bool -> FilePath -> IO (Either String [Module])
40+build withPrelude root = do
41+ names <- getSortedModuleNames root
42+ case names of
43+ Left err -> return (Left err)
44+ Right ns -> do srcs <- zipWithM buildFile' [1..] ns
45+ return (sequence srcs)
46+ where
47+ buildFile' n name = putStrLn (msg n name) >> buildFile withPrelude name
48+ msg n name = "["++show n++" of "++show (length ns)++"] Compiling "++name
49+
50+buildFile :: Bool -> String -> IO (Either String Module)
51+buildFile withPrelude moduleName =
52+ let filePath = toFilePath moduleName in
53+ case isNative moduleName of
54+ True -> return (Right $ Module [moduleName] [] [] [])
55+ --return (Left "Can't do that yet")
56+ --Right `liftM` readFile filePath
57+ False -> do txt <- readFile filePath
58+ return $ buildFromSource withPrelude txt
59+
60+
61+getSortedModuleNames :: FilePath -> IO (Either String [String])
62+getSortedModuleNames root = do
63+ deps <- readDeps [] root
64+ return (sortDeps =<< deps)
65+
66+type Deps = (String, [String])
67+
68+sortDeps :: [Deps] -> Either String [String]
69+sortDeps deps = go [] (nub deps)
70+ where
71+ msg = "A cyclical or missing module dependency or was detected in: "
72+
73+ go :: [String] -> [Deps] -> Either String [String]
74+ go sorted [] = Right sorted
75+ go sorted unsorted =
76+ case partition (all (`elem` sorted) . snd) unsorted of
77+ ([],m:ms) -> Left (msg ++ intercalate ", " (map fst (m:ms)) ++ show sorted ++ show unsorted)
78+ (srtd,unsrtd) -> go (sorted ++ map fst srtd) unsrtd
79+
80+readDeps :: [FilePath] -> FilePath -> IO (Either String [Deps])
81+readDeps seen root = do
82+ txt <- readFile root
83+ case preParse txt of
84+ Left err -> return (Left err)
85+ Right (name,deps) -> do rest <- mapM (readDeps seen' . toFilePath) newDeps
86+ return $ do rs <- sequence rest
87+ return ((name, realDeps) : concat rs)
88+ where realDeps = filter (`notElem` builtIns) deps
89+ newDeps = filter (`notElem` seen) realDeps
90+ seen' = root : seen ++ newDeps
91+ builtIns = Map.keys Libs.libraries
92+
93+isNative name = takeWhile (/='.') name == "Native"
94+toFilePath name = map swapDots name ++ ext
95+ where swapDots '.' = '/'
96+ swapDots c = c
97+ ext = if isNative name then ".js" else ".elm"
compiler/Language/Elm.hsnew file+58
@@ -0,0 +1,58 @@
1+{-# LANGUAGE TypeSynonymInstances, FlexibleInstances #-}
2+{- | This module exports the functions necessary for compiling Elm code into the
3+ respective HTML, JS and CSS code.
4+
5+ The type class @'ElmSource'@ requires an instance for all types that the Elm
6+ compiler understands. The provided instances for String, Text and QuasiQuoted
7+ Elm source code should be sufficient.
8+
9+ The documentation for the Elm language is available at
10+ <http://elm-lang.org/Documentation.elm>, and many interactive examples are
11+ available at <http://elm-lang.org/Examples.elm>
12+
13+ Example implementations using Yesod and Happstack are available
14+ at <https://github.com/tazjin/Elm/tree/master/Examples>
15+-}
16+module Language.Elm (
17+ compile, toHtml,
18+ moduleName,
19+ runtime, docs
20+ ) where
21+
22+import qualified Ast as Ast
23+import qualified Libraries as Libraries
24+import Data.List (intercalate)
25+import Data.Version (showVersion)
26+import CompileToJS (showErr, jsModule)
27+import ExtractNoscript
28+import GenerateHtml
29+import Initialize
30+import Text.Blaze.Html (Html)
31+import Paths_Elm
32+
33+-- |This function compiles Elm code to JavaScript.
34+compile :: String -> String
35+compile source = either showErr jsModule modul
36+ where modul = buildFromSource True source
37+
38+-- |This function extracts the module name of a given source program.
39+moduleName :: String -> String
40+moduleName source = either (const "Main") getName modul
41+ where modul = buildFromSource False source
42+ getName (Ast.Module names _ _ _) = intercalate "." names
43+
44+-- |This function compiles Elm code into a full HTML page.
45+toHtml :: String -- ^ Location of elm-min.js as expected by the browser
46+ -> String -- ^ The page title
47+ -> String -- ^ The elm source code
48+ -> Html
49+toHtml = generateHtml
50+
51+-- |The absolute path to Elm's runtime system.
52+runtime :: IO FilePath
53+runtime = getDataFileName "elm-runtime.js"
54+
55+-- |The absolute path to Elm's core library documentation.
56+docs :: IO FilePath
57+docs = getDataFileName "docs.json"
58+
elm/src/Language/Elm/Quasi.hs → compiler/Language/Elm/Quasi.hsrenamed

The content is the same.

elm/src/Ast.hs → compiler/Model/Ast.hsrenamed+28−25
@@ -2,7 +2,7 @@
2module Ast where
2module Ast where
3
3
4import Context
4import Context
5−import Data.Char (isDigit)
5+import Data.Char (isDigit, isSymbol)
6import Data.List (intercalate)
6import Data.List (intercalate)
7import Types.Types
7import Types.Types
8import qualified Text.Pandoc as Pandoc
8import qualified Text.Pandoc as Pandoc
@@ -12,8 +12,8 @@ data Module = Module [String] Exports Imports [Statement]
12type Exports = [String]
12type Exports = [String]
13
13
14type Imports = [(String, ImportMethod)]
14type Imports = [(String, ImportMethod)]
15−data ImportMethod = As String | Hiding [String] | Importing [String]
15+data ImportMethod = As String | Importing [String] | Hiding [String]
16− deriving (Eq,Ord)
16+ deriving (Eq, Ord, Show)
17
17
18
18
19data Pattern = PData String [Pattern]
19data Pattern = PData String [Pattern]
@@ -73,24 +73,27 @@ plist = foldr pcons pnil
73ptuple es = PData ("Tuple" ++ show (length es)) es
73ptuple es = PData ("Tuple" ++ show (length es)) es
74
74
75brkt s = "{ " ++ s ++ " }"
75brkt s = "{ " ++ s ++ " }"
76+parensIf b s = if b then parens s else s
77+isOp c = isSymbol c || elem c "+-/*=.$<>:&|^?%#@~!"
76
78
77instance Show Pattern where
79instance Show Pattern where
80+ show p =
81+ case p of
78− show (PRecord fs) = brkt (intercalate ", " fs)
82+ PRecord fs -> brkt (intercalate ", " fs)
79− show (PVar x) = x
83+ PVar x -> x
80− show PAnything = "_"
84+ PAnything -> "_"
81− show (PData "Cons" [hd@(PData "Cons" _),tl]) =
85+ PData "Cons" [hd@(PData "Cons" _),tl] ->
82− parens (show hd) ++ " : " ++ show tl
86+ parens (show hd) ++ " :: " ++ show tl
83− where parens s = "(" ++ s ++ ")"
84− show (PData "Cons" [hd,tl]) = show hd ++ " : " ++ show tl
87+ PData "Cons" [hd,tl] -> show hd ++ " : " ++ show tl
85− show (PData "Nil" []) = "[]"
88+ PData "Nil" [] -> "[]"
86− show (PData name ps) =
89+ PData name ps ->
87 if take 5 name == "Tuple" && all isDigit (drop 5 name) then
90 if take 5 name == "Tuple" && all isDigit (drop 5 name) then
88 parens . intercalate ", " $ map show ps
91 parens . intercalate ", " $ map show ps
89− else (if null ps then id else parens) $ unwords (name : map show ps)
92+ else parensIf (not (null ps)) $ unwords (name : map show ps)
90− where parens s = "(" ++ s ++ ")"
91
93
92instance Show Expr where
94instance Show Expr where
93 show e =
95 show e =
96+ let show' (C _ _ e) = parensIf (needsParens e) (show e) in
94 case e of
97 case e of
95 IntNum n -> show n
98 IntNum n -> show n
96 FloatNum n -> show n
99 FloatNum n -> show n
@@ -116,7 +119,7 @@ instance Show Expr where
116 where iff (b,e) = show b ++ " -> " ++ show e
119 where iff (b,e) = show b ++ " -> " ++ show e
117 sep = concatMap ("\n | " ++)
120 sep = concatMap ("\n | " ++)
118 Let defs e -> "let { "++intercalate " ; " (map show defs)++" } in "++show e
121 Let defs e -> "let { "++intercalate " ; " (map show defs)++" } in "++show e
119− Var x -> x
122+ Var (c:cs) -> if isOp c then parens (c:cs) else c:cs
120 Case e pats -> "case "++ show e ++" of " ++ brkt (intercalate " ; " pats')
123 Case e pats -> "case "++ show e ++" of " ++ brkt (intercalate " ; " pats')
121 where pats' = map (\(p,e) -> show p ++ " -> " ++ show e) pats
124 where pats' = map (\(p,e) -> show p ++ " -> " ++ show e) pats
122 Data name es
125 Data name es
@@ -138,13 +141,13 @@ getLambdas (C _ _ (Lambda x e)) = (x:xs,e')
138 where (xs,e') = getLambdas e
141 where (xs,e') = getLambdas e
139getLambdas e = ([],e)
142getLambdas e = ([],e)
140
143
141−show' (C _ _ e) = if needsParens e then "(" ++ show e ++ ")" else show e
144+needsParens e =
142−
145+ case e of
143−needsParens (Binop _ _ _) = True
146+ Binop _ _ _ -> True
144−needsParens (Lambda _ _) = True
147+ Lambda _ _ -> True
145−needsParens (App _ _) = True
148+ App _ _ -> True
146−needsParens (If _ _ _) = True
149+ If _ _ _ -> True
147−needsParens (Let _ _) = True
150+ Let _ _ -> True
148−needsParens (Case _ _) = True
151+ Case _ _ -> True
149−needsParens (Data name (x:xs)) = name /= "Cons"
152+ Data name (x:xs) -> name /= "Cons"
150−needsParens _ = False
153+ _ -> False
elm/src/Context.hs → compiler/Model/Context.hsrenamed

The content is the same.

elm/src/Guid.hs → compiler/Model/Guid.hsrenamed+3−1
@@ -1,5 +1,5 @@
1{-# LANGUAGE GeneralizedNewtypeDeriving #-}
1{-# LANGUAGE GeneralizedNewtypeDeriving #-}
2−module Guid (guid, run, runAt, GuidCounter) where
2+module Guid (guid, set, run, runAt, GuidCounter) where
3
3
4import Control.Monad.State (evalState, State, get, put)
4import Control.Monad.State (evalState, State, get, put)
5
5
@@ -13,5 +13,7 @@ guid = GC $ do n <- get
13 put (n + 1)
13 put (n + 1)
14 return n
14 return n
15
15
16+set n = GC (put n)
17+
16run = runAt 0
18run = runAt 0
17runAt n x = evalState (runGC x) n
19runAt n x = evalState (runGC x) n
compiler/Model/Libraries.hsnew file+59
@@ -0,0 +1,59 @@
1+module Libraries (libraries, addPrelude) where
2+
3+import Ast
4+import Control.Applicative ((<$>),(<*>))
5+import qualified Data.Map as Map
6+import Data.List (inits)
7+import Text.JSON
8+import LoadLibraries as Libs
9+
10+addPrelude :: Module -> Module
11+addPrelude (Module name exs ims stmts) = Module name exs (customIms ++ ims) stmts
12+ where customIms = concatMap addModule prelude
13+
14+ addModule (n, method) = case lookup n ims of
15+ Nothing -> [(n, method)]
16+ Just (As m) -> [(n, method)]
17+ Just _ -> []
18+
19+prelude = text : map (\n -> (n, Hiding [])) modules
20+ where
21+ text = ("Text", Hiding ["link", "color", "height"])
22+ modules = [ "Prelude", "Signal", "List", "Maybe", "Time"
23+ , "Graphics.Element", "Color", "Graphics.Collage" ]
24+
25+libraries :: Map.Map String (Map.Map String String)
26+libraries =
27+ case getLibs of
28+ Error err -> error err
29+ Ok libs -> Map.unionWith Map.union libs nilAndTuples
30+ where nilAndTuples = Map.singleton "Prelude" (Map.fromList pairs)
31+ pairs =
32+ [ ("Cons", "a -> [a] -> [a]")
33+ , ("Nil", "[a]")
34+ ] ++ map makeTuple (inits ['a'..'i'])
35+
36+ makeTuple cs =
37+ let name = "Tuple" ++ show (length cs)
38+ in (name, concatMap (\c -> c : " -> ") cs ++
39+ name ++ concatMap (\c -> [' ',c]) cs)
40+
41+getLibs :: Result (Map.Map String (Map.Map String String))
42+getLibs = do
43+ obj <- decodeStrict Libs.docs :: Result (JSObject JSValue)
44+ modules <- valFromObj "modules" obj :: Result [JSObject JSValue]
45+ Map.fromList `fmap` mapM getValues modules
46+
47+
48+get :: String -> JSObject JSValue -> Result String
49+get = valFromObj
50+
51+getValue :: JSObject JSValue -> Result (String,String)
52+getValue obj = (,) <$> get "name" obj <*> get "type" obj
53+
54+getValues :: JSObject JSValue -> Result (String, Map.Map String String)
55+getValues obj = do
56+ name <- get "name" obj
57+ vs <- valFromObj "values" obj
58+ vals <- mapM getValue vs
59+ return (name, Map.fromList vals)
compiler/Model/LoadLibraries.hsnew file+34
@@ -0,0 +1,34 @@
1+module LoadLibraries (docs) where
2+
3+import Control.DeepSeq (force)
4+import qualified Control.Exception as E
5+import Paths_Elm
6+import System.Directory
7+import System.FilePath
8+import System.IO.Unsafe (unsafePerformIO)
9+
10+-- See stackoverflow discussion for trade-off between using unsafeIO or TemplateHaskell:
11+-- http://stackoverflow.com/questions/12716215/load-pure-global-variable-from-file
12+
13+-- Given the awkwardness of including a compile-time generated file
14+-- vs loading static data, then the unsafeIO seems better.
15+
16+{-# NOINLINE docs #-}
17+docs :: String
18+docs = force $ unsafePerformIO (safeReadDocs =<< getDataFileName "docs.json")
19+
20+safeReadDocs :: FilePath -> IO String
21+safeReadDocs name = E.catch (readDocs name) (emitError name)
22+
23+readDocs :: FilePath -> IO String
24+readDocs name = do
25+ exists <- doesFileExist name
26+ if exists then readFile name
27+ else ioError . userError $ "File Not Found"
28+
29+
30+emitError :: FilePath -> IOError -> IO String
31+emitError name err = do
32+ putStrLn $ "Error! Types for standard library not loaded properly!\n File should be here:" ++ name ++ "\n The file is created and copied by command: cabal install"
33+ putStrLn (show err)
34+ return "{\"modules\":[]}"
elm/src/Parse/Binops.hs → compiler/Parse/Binops.hsrenamed+1
@@ -28,6 +28,7 @@ table = [ (9, R, ".")
28 , (3, R, "&&")
28 , (3, R, "&&")
29 , (2, R, "||")
29 , (2, R, "||")
30 , (0, R, "$")
30 , (0, R, "$")
31+ , (0, R, "<|"), (0, L, "|>")
31 ]
32 ]
32
33
33opLevel op = Map.findWithDefault 9 op dict
34opLevel op = Map.findWithDefault 9 op dict
elm/src/Parse/Expr.hs → compiler/Parse/Expr.hsrenamed

The content is the same.

elm/src/Parse/Foreign.hs → compiler/Parse/Foreign.hsrenamed

The content is the same.

elm/src/Parse/Library.hs → compiler/Parse/Library.hsrenamed+3−5
@@ -6,7 +6,7 @@ import Context
6import Control.Applicative ((<$>),(<*>))
6import Control.Applicative ((<$>),(<*>))
7import Control.Monad
7import Control.Monad
8import Control.Monad.State
8import Control.Monad.State
9−import Data.Char (isSymbol,isUpper)
9+import Data.Char (isUpper)
10import Rename (deprime)
10import Rename (deprime)
11import Text.Parsec hiding (newline,spaces,State)
11import Text.Parsec hiding (newline,spaces,State)
12import Text.Parsec.Indent
12import Text.Parsec.Indent
@@ -16,7 +16,7 @@ reserveds = [ "if", "then", "else"
16 , "let", "in"
16 , "let", "in"
17 , "data", "type"
17 , "data", "type"
18 , "module", "where"
18 , "module", "where"
19− , "import", "as", "hiding"
19+ , "import", "as", "hiding", "open"
20 , "export", "foreign" ]
20 , "export", "foreign" ]
21
21
22expecting = flip (<?>)
22expecting = flip (<?>)
@@ -58,8 +58,6 @@ reserved word =
58anyOp :: IParser String
58anyOp :: IParser String
59anyOp = betwixt '`' '`' var <|> symOp <?> "infix operator (e.g. +, *, ||)"
59anyOp = betwixt '`' '`' var <|> symOp <?> "infix operator (e.g. +, *, ||)"
60
60
61−isOp c = isSymbol c || elem c "+-/*=.$<>:&|^?%#@~!"
62−
63symOp :: IParser String
61symOp :: IParser String
64symOp = do op <- many1 (satisfy isOp)
62symOp = do op <- many1 (satisfy isOp)
65 guard (op `notElem` [ "=", "..", "->", "--", "|", "\8594", ":" ])
63 guard (op `notElem` [ "=", "..", "->", "--", "|", "\8594", ":" ])
@@ -162,7 +160,7 @@ whitespace :: IParser ()
162whitespace = optional forcedWS <?> ""
160whitespace = optional forcedWS <?> ""
163
161
164freshLine :: IParser [[String]]
162freshLine :: IParser [[String]]
165−freshLine = try (do { many1 newline; many space_nl }) <|> try (many1 space_nl) <?> ""
163+freshLine = try (many1 newline >> many space_nl) <|> try (many1 space_nl) <?> ""
166 where space_nl = try $ spaces >> many1 newline
164 where space_nl = try $ spaces >> many1 newline
167
165
168newline :: IParser String
166newline :: IParser String
elm/src/Parse/Modules.hs → compiler/Parse/Modules.hsrenamed+6−7
@@ -30,18 +30,17 @@ import' :: IParser (String, ImportMethod)
30import' = do
30import' = do
31 reserved "import"
31 reserved "import"
32 whitespace
32 whitespace
33+ open <- optionMaybe (reserved "open")
34+ whitespace
33 name <- intercalate "." <$> dotSep1 capVar
35 name <- intercalate "." <$> dotSep1 capVar
34− method <- option (Hiding []) $ try (whitespace >>
36+ case open of
37+ Just _ -> return (name, Hiding [])
35− (as' <|> hiding' <|> importing'))
38+ Nothing -> let how = try (whitespace >> (as' <|> importing'))
36− return (name, method)
39+ in (,) name <$> option (Importing []) how
37
40
38
41
39as' :: IParser ImportMethod
42as' :: IParser ImportMethod
40as' = reserved "as" >> whitespace >> As <$> capVar <?> "alias for module"
43as' = reserved "as" >> whitespace >> As <$> capVar <?> "alias for module"
41
44
42−hiding' :: IParser ImportMethod
43−hiding' = reserved "hiding" >> whitespace >>
44− Hiding <$> varList <?> "listing of hidden values"
45−
46importing' :: IParser ImportMethod
45importing' :: IParser ImportMethod
47importing' = Importing <$> varList <?> "listing of imported values (x,y,z)"
46importing' = Importing <$> varList <?> "listing of imported values (x,y,z)"
elm/src/Parse/Parser.hs → compiler/Parse/Parser.hsrenamed+19−6
@@ -1,10 +1,10 @@
1−module Parse.Parser (parseProgram) where
1+module Parse.Parser (parseProgram, preParse) where
2
2
3import Ast
3import Ast
4import Control.Applicative ((<$>), (<*>))
4import Control.Applicative ((<$>), (<*>))
5import Control.Monad
5import Control.Monad
6import Data.Char (isSymbol, isDigit)
6import Data.Char (isSymbol, isDigit)
7−import Data.List (foldl')
7+import Data.List (foldl',intercalate)
8import Text.Parsec hiding (newline,spaces)
8import Text.Parsec hiding (newline,spaces)
9
9
10import Parse.Library
10import Parse.Library
@@ -14,8 +14,8 @@ import Parse.Modules
14import Parse.Foreign
14import Parse.Foreign
15
15
16
16
17−statement = let defs = [ foreignDef, datatype, typeAlias, typeAnnotation ] in
18− (:[]) <$> choice defs <|> def <?> "datatype or variable definition"
17+statement = choice (typeAlias:defs) <|> def <?> "datatype or variable definition"
18+ where defs = map ((:[]) <$>) [ foreignDef, datatype, typeAnnotation ]
19
19
20freshDef = commitIf (freshLine >> (letter <|> char '_')) $ do
20freshDef = commitIf (freshLine >> (letter <|> char '_')) $ do
21 freshLine
21 freshLine
@@ -33,7 +33,20 @@ program = do
33 optional freshLine ; optional spaces ; eof
33 optional freshLine ; optional spaces ; eof
34 return $ Module names exports is statements
34 return $ Module names exports is statements
35
35
36−parseProgram source =
36+parseProgram = setupParser program
37+
38+preParse :: String -> Either String (String, [String])
39+preParse = setupParser $ do
40+ optional skip
41+ (,) <$> option "Main" moduleName <*> option [] imprts
42+ where
43+ skip = try (manyTill anyChar (try (string "/**")))
44+ imprts = fmap (map fst) imports `followedBy` freshLine
45+ getName = intercalate "." . fst
46+ moduleName = do optional freshLine
47+ getName <$> moduleDef `followedBy` freshLine
48+
49+setupParser p source =
37− case iParse program "" source of
50+ case iParse p "" source of
38 Right result -> Right result
51 Right result -> Right result
39 Left err -> Left $ "Parse error at " ++ show err
52 Left err -> Left $ "Parse error at " ++ show err
elm/src/Parse/Patterns.hs → compiler/Parse/Patterns.hsrenamed+5−4
@@ -88,10 +88,11 @@ matchSingle :: Pattern -> CExpr -> Pattern -> GuidCounter [Def]
88matchSingle pat exp@(C t s _) p =
88matchSingle pat exp@(C t s _) p =
89 let ctx = C t s in
89 let ctx = C t s in
90 case p of
90 case p of
91− PData _ ps -> do x <- guid
91+ PData _ ps -> do
92+ x <- guid
92− let v = '_' : show x
93+ let v = '_' : show x
93− dss <- mapM (matchSingle p . ctx $ Var v) ps
94+ dss <- mapM (matchSingle pat . ctx $ Var v) ps
94− return (FnDef v [] exp : concat dss)
95+ return (FnDef v [] exp : concat dss)
95
96
96 PVar x ->
97 PVar x ->
97 return [ FnDef x [] (ctx $ Case exp [(pat, ctx $ Var x)]) ]
98 return [ FnDef x [] (ctx $ Case exp [(pat, ctx $ Var x)]) ]
elm/src/Parse/Types.hs → compiler/Parse/Types.hsrenamed+18−7
@@ -9,8 +9,9 @@ import Data.List (lookup)
9import Text.Parsec
9import Text.Parsec
10import Text.Parsec.Indent
10import Text.Parsec.Indent
11
11
12+import Context
12import Parse.Library
13import Parse.Library
13−import Types.Types hiding (string,parens)
14+import Types.Types hiding (parens,string)
14import Guid
15import Guid
15
16
16data ParseType = VarPT String
17data ParseType = VarPT String
@@ -46,10 +47,7 @@ typeUnambiguous :: IParser ParseType
46typeUnambiguous = typeList <|> typeTuple <|> typeRecord
47typeUnambiguous = typeList <|> typeTuple <|> typeRecord
47
48
48typeSimple :: IParser ParseType
49typeSimple :: IParser ParseType
49−typeSimple = dealias <$> var
50+typeSimple = VarPT <$> var
50− where dealias "String" = listPT (VarPT "Char")
51− dealias "Time" = VarPT "Float"
52− dealias v = VarPT v
53
51
54typeApp :: IParser ParseType
52typeApp :: IParser ParseType
55typeApp = do name <- capVar <?> "type constructor"
53typeApp = do name <- capVar <?> "type constructor"
@@ -70,8 +68,9 @@ typeConstructor :: IParser (String, [ParseType])
70typeConstructor = (,) <$> (capVar <?> "another type constructor")
68typeConstructor = (,) <$> (capVar <?> "another type constructor")
71 <*> spacePrefix (typeSimple <|> typeUnambiguous)
69 <*> spacePrefix (typeSimple <|> typeUnambiguous)
72
70
73−typeAlias :: IParser Statement
71+typeAlias :: IParser [Statement]
74typeAlias = do
72typeAlias = do
73+ start <- getPosition
75 reserved "type" <?> "type alias (type Point = {x:Int, y:Int})"
74 reserved "type" <?> "type alias (type Point = {x:Int, y:Int})"
76 forcedWS
75 forcedWS
77 alias <- capVar
76 alias <- capVar
@@ -79,9 +78,21 @@ typeAlias = do
79 whitespace ; string "=" ; whitespace
78 whitespace ; string "=" ; whitespace
80 let n = length args
79 let n = length args
81 tipe <- typeExpr
80 tipe <- typeExpr
81+ end <- getPosition
82 case toTypeWith alias (zip args [1..n]) tipe of
82 case toTypeWith alias (zip args [1..n]) tipe of
83− Right t -> return (TypeAlias alias [1..n] t)
84 Left msg -> fail msg
83 Left msg -> fail msg
84+ Right t -> return (TypeAlias alias [1..n] t : ctor)
85+ where ctor = case tipe of
86+ RecordPT _ kvs -> [toConstructor start end alias kvs]
87+ _ -> []
88+
89+toConstructor start end alias kvs =
90+ Definition (FnDef alias args (ctxt (Record rec)))
91+ where
92+ ctxt = pos start end
93+ args = map fst kvs
94+ rec = map (\a -> (a, [], ctxt (Var a))) args
95+
85
96
86typeAnnotation :: IParser Statement
97typeAnnotation :: IParser Statement
87typeAnnotation = TypeAnnotation <$> try start <*> (toType <$> typeExpr)
98typeAnnotation = TypeAnnotation <$> try start <*> (toType <$> typeExpr)
compiler/Transform/LetBoundVars.hsnew file+53
@@ -0,0 +1,53 @@
1+module LetBoundVars (letBoundVars) where
2+
3+import Context
4+import Ast
5+
6+class LetBoundVars a where
7+ letBoundVars :: a -> [String]
8+
9+instance LetBoundVars a => LetBoundVars [a] where
10+ letBoundVars = concatMap letBoundVars
11+
12+instance LetBoundVars Statement where
13+ letBoundVars stmt =
14+ case stmt of
15+ Definition d -> letBoundVars d
16+ Datatype _ _ tcs -> []
17+ ImportEvent _ e _ _ -> letBoundVars e
18+ ExportEvent _ _ _ -> []
19+ TypeAnnotation _ _ -> []
20+ TypeAlias _ _ _ -> []
21+
22+instance LetBoundVars Def where
23+ letBoundVars (FnDef n _ e) = n : letBoundVars e
24+ letBoundVars (OpDef _ _ _ e) = letBoundVars e
25+
26+instance LetBoundVars e => LetBoundVars (Context e) where
27+ letBoundVars (C _ _ e) = letBoundVars e
28+
29+instance LetBoundVars Expr where
30+ letBoundVars expr =
31+ let f = letBoundVars in
32+ case expr of
33+ IntNum _ -> []
34+ FloatNum _ -> []
35+ Chr _ -> []
36+ Str _ -> []
37+ Boolean _ -> []
38+ Range e1 e2 -> f e1 ++ f e2
39+ Access e _ -> []
40+ Remove e _ -> []
41+ Insert e1 _ e2 -> f e1 ++ f e2
42+ Modify e ps -> f e ++ concatMap (f . snd) ps
43+ Record trps -> concatMap (\(_,_,e) -> f e) trps
44+ Binop op e1 e2 -> f e1 ++ f e2
45+ Lambda x e -> f e
46+ App e1 e2 -> f e1 ++ f e2
47+ If e1 e2 e3 -> concatMap f [e1,e2,e3]
48+ MultiIf ps -> concatMap (\(b,e) -> f b ++ f e) ps
49+ Let defs e -> concatMap letBoundVars defs ++ f e
50+ Var x -> []
51+ Data name es -> concatMap f es
52+ Case e cases -> f e ++ concatMap (f . snd) cases
53+ Markdown _ -> []
elm/src/Optimize.hs → compiler/Transform/Optimize.hsrenamed+3−1
@@ -112,7 +112,7 @@ binop op ce1@(C t1 s1 e1) ce2@(C t2 s2 e2) =
112 ("||", Boolean True, _) -> Boolean True
112 ("||", Boolean True, _) -> Boolean True
113 ("||", Boolean False, _) -> e2
113 ("||", Boolean False, _) -> e2
114
114
115− (":", _, _) -> let (C _ _ e) = cons ce1 ce2 in e
115+ ("::", _, _) -> let (C _ _ e) = cons ce1 ce2 in e
116
116
117 ("++", Str s1, Str s2) -> Str $ s1 ++ s2
117 ("++", Str s1, Str s2) -> Str $ s1 ++ s2
118 ("++", Str s1, Binop "++" (C _ _ (Str s2)) ce) ->
118 ("++", Str s1, Binop "++" (C _ _ (Str s2)) ce) ->
@@ -124,6 +124,8 @@ binop op ce1@(C t1 s1 e1) ce2@(C t2 s2 e2) =
124 ("++", _, Data "Nil" []) -> e1
124 ("++", _, Data "Nil" []) -> e1
125 ("++", Data "Cons" [h,t], _) -> Data "Cons" [h, noContext $ binop "++" t ce2]
125 ("++", Data "Cons" [h,t], _) -> Data "Cons" [h, noContext $ binop "++" t ce2]
126
126
127+ ("|>", _, _) -> App ce2 ce1
128+ ("<|", _, _) -> App ce1 ce2
127 ("$", _, _) -> App ce1 ce2
129 ("$", _, _) -> App ce1 ce2
128 (".", _, _) ->
130 (".", _, _) ->
129 Lambda "x" (noContext $
131 Lambda "x" (noContext $
elm/src/Rename.hs → compiler/Transform/Rename.hsrenamed+2
@@ -133,6 +133,8 @@ patternExtend pattern env =
133 first (PData name . reverse) `liftM` foldM f ([], env) ps
133 first (PData name . reverse) `liftM` foldM f ([], env) ps
134 where f (rps,env') p = do (rp,env'') <- patternExtend p env'
134 where f (rps,env') p = do (rp,env'') <- patternExtend p env'
135 return (rp:rps, env'')
135 return (rp:rps, env'')
136+ PRecord fs ->
137+ return (pattern, foldr (\f e n -> if n == f then f else env n) env fs)
136
138
137patternRename :: (String -> String) -> (Pattern, CExpr) -> GuidCounter (Pattern, CExpr)
139patternRename :: (String -> String) -> (Pattern, CExpr) -> GuidCounter (Pattern, CExpr)
138patternRename env (p,e) = do
140patternRename env (p,e) = do
elm/src/Replace.hs → compiler/Transform/Replace.hsrenamed

The content is the same.

elm/src/Substitute.hs → compiler/Transform/Substitute.hsrenamed

The content is the same.

elm/src/Types/Alias.hs → compiler/Types/Alias.hsrenamed+31−29
@@ -1,5 +1,5 @@
1
1
2−module Types.Alias (dealias, mistakes) where
2+module Types.Alias (dealias, get, mistakes) where
3
3
4import Ast
4import Ast
5import Control.Arrow (second)
5import Control.Arrow (second)
@@ -10,37 +10,39 @@ import Types.Substitutions (subst)
10import Types.Types
10import Types.Types
11
11
12builtins :: [(String,([X],Type))]
12builtins :: [(String,([X],Type))]
13−builtins = [ ("String", ([], string)) ]
13+builtins =
14−
14+ let touch = ("t0", time) : map (flip (,) int) ["x","y","x0","y0","id"]
15+ state = [("string", string), ("selectionStart", int), ("selectionEnd", int)]
16+ line = [("color", tipe "Color"), ("width", float),
17+ ("cap", tipe "LineCap"), ("join", tipe "LineJoin"),
18+ ("miterLimit", float), ("dashing", listOf int),
19+ ("dashOffset", int)]
20+ makeRecord fields =
21+ RecordT (Map.fromList $ map (second (:[])) fields) EmptyRecord
22+ in [ ("String", ([], listOf char)),
23+ ("Time", ([], float)),
24+ ("KeyCode", ([], int)),
25+ ("Touch", ([], makeRecord touch)),
26+ ("FieldState", ([], makeRecord state)),
27+ ("LineStyle", ([], makeRecord line))
28+ ]
29+
15−getAliases :: [Statement] -> Map.Map String ([X],Type)
30+get :: [Statement] -> Map.Map String ([X],Type)
16−getAliases stmts = Map.fromList (builtins ++ concatMap getAlias stmts)
31+get stmts = Map.fromList (builtins ++ concatMap getAlias stmts)
17 where getAlias stmt = case stmt of
32 where getAlias stmt = case stmt of
18 TypeAlias alias xs t -> [(alias, (xs,t))]
33 TypeAlias alias xs t -> [(alias, (xs,t))]
19 _ -> []
34 _ -> []
20
35
21−
36+dealias :: Map.Map String ([X],Type) -> Type -> Type
22−dealias :: [Statement] -> [Statement]
37+dealias aliases t =
23−dealias stmts = map dealiasS stmts
38+ let f = dealias aliases in
24− where
25− dealiasT :: Type -> Type
26− dealiasT t =
27− case t of
39+ case t of
28− ADT name ts -> case Map.lookup name (getAliases stmts) of
40+ ADT name ts -> case Map.lookup name aliases of
29− Just (xs,t) -> dealiasT (subst (zip xs ts) t)
41+ Just (xs,t) -> f (subst (zip xs ts) t)
30− Nothing -> ADT name (map dealiasT ts)
42+ Nothing -> ADT name (map f ts)
31− LambdaT t u -> LambdaT (dealiasT t) (dealiasT u)
43+ LambdaT t u -> LambdaT (f t) (f u)
32− RecordT r t -> RecordT (Map.map (map dealiasT) r) (dealiasT t)
44+ RecordT r t -> RecordT (Map.map (map f) r) (f t)
33− _ -> t
45+ _ -> t
34−
35− dealiasS :: Statement -> Statement
36− dealiasS s =
37− case s of
38− Datatype n xs tcs -> Datatype n xs (map (second (map dealiasT)) tcs)
39− ExportEvent js elm tipe -> ExportEvent js elm (dealiasT tipe)
40− ImportEvent js e elm tipe -> ImportEvent js e elm (dealiasT tipe)
41− TypeAnnotation name tipe -> TypeAnnotation name (dealiasT tipe)
42− TypeAlias alias xs tipe -> TypeAlias alias xs (dealiasT tipe)
43− Definition _ -> s
44
46
45mistakes :: [Statement] -> [String]
47mistakes :: [Statement] -> [String]
46mistakes stmts = badKinds stmts ++ dups stmts ++ badOrder stmts
48mistakes stmts = badKinds stmts ++ dups stmts ++ badOrder stmts
@@ -55,7 +57,7 @@ badKinds stmts = map msg (concatMap badS stmts)
55 badT t =
57 badT t =
56 case t of
58 case t of
57 ADT name ts ->
59 ADT name ts ->
58− case Map.lookup name (getAliases stmts) of
60+ case Map.lookup name (get stmts) of
59 Just (xs,t) | length xs == length ts -> []
61 Just (xs,t) | length xs == length ts -> []
60 | otherwise -> [name]
62 | otherwise -> [name]
61 Nothing -> concatMap badT ts
63 Nothing -> concatMap badT ts
elm/src/Types/Constrain.hs → compiler/Types/Constrain.hsrenamed+41−31
@@ -4,6 +4,7 @@ module Types.Constrain (constrain) where
4import Control.Arrow (second)
4import Control.Arrow (second)
5import Control.Monad (liftM,mapM,zipWithM,foldM)
5import Control.Monad (liftM,mapM,zipWithM,foldM)
6import Control.Monad.State (evalState)
6import Control.Monad.State (evalState)
7+import Data.Char (isDigit)
7import Data.List (foldl',sort,group,isPrefixOf,intercalate,isSuffixOf)
8import Data.List (foldl',sort,group,isPrefixOf,intercalate,isSuffixOf)
8import qualified Data.Map as Map
9import qualified Data.Map as Map
9import qualified Data.Set as Set
10import qualified Data.Set as Set
@@ -13,32 +14,33 @@ import Context
13import Guid
14import Guid
14
15
15import Types.Types
16import Types.Types
16−import Types.Substitutions
17+import qualified Types.Substitutions as Subs
17
18
18beta = VarT `liftM` guid
19beta = VarT `liftM` guid
19unionA = Map.unionWith (++)
20unionA = Map.unionWith (++)
20unionsA = Map.unionsWith (++)
21unionsA = Map.unionsWith (++)
21
22
22−getAliases imports hints = hints ++ concatMap aliasesFrom imports'
23+getAliases imports hints = concatMap aliasesFrom imports
23− where imports' = map head . group $ sort imports
24+ where aliasesFrom (name,method) =
24− aliasesFrom (name,method) =
25+ let values = concatMap (getValue name) hints
25− case method of
26+ in case method of
26− As alias -> concatMap (findAlias name alias) hints
27+ As alias -> map (\(n,t) -> (alias ++ "." ++ n, t)) values
27− Hiding [] -> concatMap (findAlias name "") hints
28+ Hiding vs -> filter (\(n,t) -> n `notElem` vs) values
28− _ -> []
29+ Importing vs -> filter (\(n,t) -> n `elem` vs) values
29− findAlias mName' mAlias (name,tipe) =
30+ getValue inModule (name,tipe) =
30− let mName = mName' ++ "." in
31− case mName `isPrefixOf` name of
31+ case inModule `isPrefixOf` name of
32− True -> [ (mAlias ++ drop (length mName) name, tipe) ]
32+ True -> [ (drop (length inModule + 1) name, tipe) ]
33− False -> []
33+ False -> []
34−
34+
35−findAmbiguous hints hints' assumptions continue =
35+findAmbiguous hints assumptions continue =
36− let potentialDups = map head . filter (\g -> length g > 1) . group $ sort hints'
36+ let potentialDups = map head . filter (\g -> length g > 1) . group . sort $
37+ filter (elem '.') hints
37− dups = filter (\k -> Map.member k assumptions) potentialDups
38+ dups = filter (\k -> Map.member k assumptions) potentialDups
38− in case dups of
39+ in case dups of
39− n:_ -> return . Left $ "Error: Ambiguous occurrence of '" ++ n ++ "' could refer to " ++
40+ n:_ -> return . Left $ "Error: Ambiguous occurrence of '" ++ n ++
41+ "' could refer to " ++
40− intercalate ", " (filter (isSuffixOf n) hints)
42+ intercalate ", " (filter (isSuffixOf n) hints)
41− _ -> continue
43+ _ -> continue
42
44
43mergeSchemes :: [Map.Map String Scheme]
45mergeSchemes :: [Map.Map String Scheme]
44 -> GuidCounter (TVarMap, ConstraintSet, Map.Map String Scheme)
46 -> GuidCounter (TVarMap, ConstraintSet, Map.Map String Scheme)
@@ -59,21 +61,20 @@ mergeSchemes schmss = do (ass,css,sss) <- unzip3 `liftM` mapM split kvs
59
61
60constrain typeHints (Module _ _ imports stmts) = do
62constrain typeHints (Module _ _ imports stmts) = do
61 (ass,css,schemess) <- unzip3 `liftM` mapM stmtGen stmts
63 (ass,css,schemess) <- unzip3 `liftM` mapM stmtGen stmts
62− hints <- typeHints
64+ aliasHints <- getAliases imports `liftM` typeHints
63 (as', cs', schemes) <- mergeSchemes schemess
65 (as', cs', schemes) <- mergeSchemes schemess
64 let constraints = Set.unions (cs':css)
66 let constraints = Set.unions (cs':css)
65 as = unionsA (as':ass)
67 as = unionsA (as':ass)
66− extraImports = ("Time", Hiding ["read"]) : map (\n -> (n, Hiding []))
67− ["List","Signal","Text","Graphics","Color"]
68− aliasHints = getAliases (imports ++ extraImports) hints
69 allHints = Map.union schemes (Map.fromList aliasHints)
68 allHints = Map.union schemes (Map.fromList aliasHints)
70 insert as n = do v <- guid; return $ Map.insertWith' (\_ x -> x) n [v] as
69 insert as n = do v <- guid; return $ Map.insertWith' (\_ x -> x) n [v] as
71 assumptions <- foldM insert as (Map.keys schemes)
70 assumptions <- foldM insert as (Map.keys schemes)
72− findAmbiguous (map fst hints) (map fst aliasHints) assumptions $ do
71+ findAmbiguous (map fst aliasHints) assumptions $ do
73 let f k s vs = map (\v -> C (Just k) NoSpan $ v :<<: s) vs
72 let f k s vs = map (\v -> C (Just k) NoSpan $ v :<<: s) vs
74 cs = concat . Map.elems $ Map.intersectionWithKey f allHints assumptions
73 cs = concat . Map.elems $ Map.intersectionWithKey f allHints assumptions
75 escapees = Map.keys $ Map.difference assumptions allHints
74 escapees = Map.keys $ Map.difference assumptions allHints
75+ return $ case escapees of
76− return . Right . (,) escapees $ Set.toList constraints ++ cs
76+ _ -> Right (Set.toList constraints ++ cs)
77+ --_ -> Left ("Undefined variable(s): " ++ intercalate ", " escapees)
77
78
78type TVarMap = Map.Map String [X]
79type TVarMap = Map.Map String [X]
79type ConstraintSet = Set.Set (Context Constraint)
80type ConstraintSet = Set.Set (Context Constraint)
@@ -232,13 +233,13 @@ caseGen tipe (p, ce@(C _ span e)) = do
232 return ( as', Set.union cs cs', t )
233 return ( as', Set.union cs cs', t )
233
234
234patternGen :: (Constraint -> Context Constraint)
235patternGen :: (Constraint -> Context Constraint)
235− -> Type
236+ -> Type -- Type of e in `case e of ...`
236 -> TVarMap
237 -> TVarMap
237 -> Pattern
238 -> Pattern
238 -> GuidCounter (TVarMap, ConstraintSet, Type)
239 -> GuidCounter (TVarMap, ConstraintSet, Type)
239patternGen ctxt tipe as pattern =
240patternGen ctxt tipe as pattern =
240 case pattern of
241 case pattern of
241− PAnything -> do b <- beta ; return (Map.empty, Set.empty, b)
242+ PAnything -> do b <- beta ; return ( as, Set.empty, b )
242 PVar v -> do
243 PVar v -> do
243 b <- beta
244 b <- beta
244 let cs = map (ctxt . (b :=:) . VarT) (Map.findWithDefault [] v as)
245 let cs = map (ctxt . (b :=:) . VarT) (Map.findWithDefault [] v as)
@@ -253,6 +254,15 @@ patternGen ctxt tipe as pattern =
253 return ( Map.insert name [constr] as'
254 return ( Map.insert name [constr] as'
254 , Set.insert (ctxt (VarT constr :=: t)) cs
255 , Set.insert (ctxt (VarT constr :=: t)) cs
255 , output )
256 , output )
257+ PRecord fs ->
258+ do pairs <- mapM (\f -> do b <- beta; return (f,b)) fs
259+ b <- beta
260+ let t = RecordT (Map.fromList $ map (second (:[])) pairs) b
261+ mkCs (name,tipe) = map (ctxt . (tipe :=:) . VarT)
262+ (Map.findWithDefault [] name as)
263+ return ( foldr Map.delete as fs
264+ , Set.fromList (ctxt (t :=: tipe) : concatMap mkCs pairs)
265+ , t )
256
266
257
267
258defScheme :: Def -> GuidCounter (Map.Map String [X], Scheme)
268defScheme :: Def -> GuidCounter (Map.Map String [X], Scheme)
@@ -273,7 +283,7 @@ defGenHelp name args e = do
273 let as' = Map.findWithDefault [v] arg as
283 let as' = Map.findWithDefault [v] arg as
274 return $ map (\y -> ctx arg NoSpan $ VarT x :=: VarT y) as'
284 return $ map (\y -> ctx arg NoSpan $ VarT x :=: VarT y) as'
275 cs' <- concat `liftM` mapM genCs argDict
285 cs' <- concat `liftM` mapM genCs argDict
276− scheme <- generalize (concat $ Map.elems as') $
286+ scheme <- Subs.generalize (concat $ Map.elems as') $
277 Forall (map snd argDict) (cs' ++ Set.toList cs) tipe
287 Forall (map snd argDict) (cs' ++ Set.toList cs) tipe
278 return ( as', Set.empty, (name, scheme) )
288 return ( as', Set.empty, (name, scheme) )
279
289
@@ -302,7 +312,7 @@ stmtGen stmt =
302 , Map.singleton elm (Forall [] [] tipe) )
312 , Map.singleton elm (Forall [] [] tipe) )
303
313
304 TypeAnnotation name tipe ->
314 TypeAnnotation name tipe ->
305− do schm <- generalize [] (Forall [] [] tipe)
315+ do schm <- Subs.generalize [] =<< Subs.superize name tipe
306 return (Map.empty, Set.empty, Map.singleton name schm)
316 return (Map.empty, Set.empty, Map.singleton name schm)
307
317
308 TypeAlias _ _ _ -> return (Map.empty, Set.empty, Map.empty)
318 TypeAlias _ _ _ -> return (Map.empty, Set.empty, Map.empty)
compiler/Types/Hints.hsnew file+31
@@ -0,0 +1,31 @@
1+module Types.Hints (hints) where
2+
3+import Control.Arrow (first)
4+import Control.Monad (liftM)
5+import Data.Maybe (catMaybes)
6+import qualified Data.Map as Map
7+import Guid
8+import qualified Libraries as Libs
9+import Parse.Library (iParse)
10+import Parse.Types
11+import qualified Types.Substitutions as Subs
12+import Types.Types
13+
14+hints :: GuidCounter [(String, Scheme)]
15+hints = liftM catMaybes (mapM toScheme values)
16+ where
17+ values :: [(String, String)]
18+ values = addPrefixes (Map.toList (Map.map Map.toList Libs.libraries))
19+
20+ addPrefixes :: [(String,[(String, String)])] -> [(String, String)]
21+ addPrefixes = concatMap (\(m,vs) -> map (first (\n -> m ++ "." ++ n)) vs)
22+
23+ toScheme :: (String, String) -> GuidCounter (Maybe (String, Scheme))
24+ toScheme (name, 't':'y':'p':'e':' ':_) = return Nothing
25+ toScheme (name, 'd':'a':'t':'a':' ':_) = return Nothing
26+ toScheme (name, tipeString) =
27+ let err = "compiler error parsing type of " ++ name ++ ":\n" ++ tipeString in
28+ case iParse (fmap toType typeExpr) err tipeString of
29+ Left err -> error (show err)
30+ Right tipe -> do scheme <- Subs.generalize [] =<< Subs.superize name tipe
31+ return (Just (name, scheme))
elm/src/Types/Solver.hs → compiler/Types/Solver.hsrenamed+57−45
@@ -13,14 +13,17 @@ import Guid
13import Types.Types
13import Types.Types
14import Types.Constrain
14import Types.Constrain
15import Types.Substitutions
15import Types.Substitutions
16+import Types.Alias (dealias)
16
17
17isSolved ss (C _ _ (t1 :=: t2)) = t1 == t2
18isSolved ss (C _ _ (t1 :=: t2)) = t1 == t2
18isSolved ss (C _ _ (x :<<: _)) = isJust (lookup x ss)
19isSolved ss (C _ _ (x :<<: _)) = isJust (lookup x ss)
19isSolved ss c = False
20isSolved ss c = False
20
21
22+type Aliases = Map.Map String ([X],Type)
23+
21−crush :: Scheme -> GuidCounter (Either String Scheme)
24+crush :: Aliases -> Scheme -> GuidCounter (Either String Scheme)
22−crush (Forall xs cs t) =
25+crush aliases (Forall xs cs t) =
23− do subs <- solver cs Map.empty
26+ do subs <- solver aliases Map.empty cs
24 return $ do ss' <- subs
27 return $ do ss' <- subs
25 let ss = Map.toList ss'
28 let ss = Map.toList ss'
26 cs' = filter (not . isSolved ss) (subst ss cs)
29 cs' = filter (not . isSolved ss) (subst ss cs)
@@ -34,10 +37,11 @@ schemeSubHelp txt span x s t1 rltn t2 = do
34 | otherwise = do (st, cs) <- concretize s
37 | otherwise = do (st, cs) <- concretize s
35 return (subst [(x,st)] t, cs)
38 return (subst [(x,st)] t, cs)
36
39
37−schemeSub x s c = do s' <- crush s
40+schemeSub aliases x s c =
41+ do s' <- crush aliases s
38− case s' of
42+ case s' of
39− Right s'' -> Right `liftM` schemeSub' x s'' c
43+ Right s'' -> Right `liftM` schemeSub' x s'' c
40− Left err -> return $ Left err
44+ Left err -> return $ Left err
41
45
42schemeSub' x s c@(C txt span constraint) =
46schemeSub' x s c@(C txt span constraint) =
43 case constraint of
47 case constraint of
@@ -77,29 +81,32 @@ recordConstraints eq fs t fs' t' =
77 let tipe = RecordT (Map.singleton k bs) (VarT x)
81 let tipe = RecordT (Map.singleton k bs) (VarT x)
78 return (cs ++ [eq t tipe])
82 return (cs ++ [eq t tipe])
79
83
80−solver :: [Context Constraint]
84+solver :: Aliases
81 -> Map.Map X Type
85 -> Map.Map X Type
86+ -> [Context Constraint]
82 -> GuidCounter (Either String (Map.Map X Type))
87 -> GuidCounter (Either String (Map.Map X Type))
83−solver [] subs = return $ Right subs
88+solver _ subs [] = return $ Right subs
84−solver (C txt span c : cs) subs =
89+solver aliases subs (C txt span c : cs) =
85 let ctx = C txt span
90 let ctx = C txt span
86 eq t1 t2 = ctx (t1 :=: t2)
91 eq t1 t2 = ctx (t1 :=: t2)
92+ solv = solver aliases subs
93+ uniError' = uniError (\t1 t2 -> solv (eq t1 t2 : cs)) aliases txt span
87 in case c of
94 in case c of
88 -- Destruct Type-constructors
95 -- Destruct Type-constructors
89 t1@(ADT n1 ts1) :=: t2@(ADT n2 ts2) ->
96 t1@(ADT n1 ts1) :=: t2@(ADT n2 ts2) ->
90− if n1 /= n2 then uniError txt span t1 t2 else
91− solver (zipWith eq ts1 ts2 ++ cs) subs
97+ if n1 == n2 then solv (zipWith eq ts1 ts2 ++ cs)
98+ else uniError' t1 t2
92
99
93 LambdaT t1 t2 :=: LambdaT t1' t2' ->
100 LambdaT t1 t2 :=: LambdaT t1' t2' ->
94− solver ([ eq t1 t1', eq t2 t2' ] ++ cs) subs
101+ solv ([ eq t1 t1', eq t2 t2' ] ++ cs)
95
102
96 RecordT fs t :=: RecordT fs' t' ->
103 RecordT fs t :=: RecordT fs' t' ->
97 do cs' <- recordConstraints eq fs t fs' t'
104 do cs' <- recordConstraints eq fs t fs' t'
98− solver (cs' ++ cs) subs
105+ solv (cs' ++ cs)
99
106
100 -- Type-equality
107 -- Type-equality
101 VarT x :=: VarT y
108 VarT x :=: VarT y
102− | x == y -> solver cs subs
109+ | x == y -> solv cs
103 | otherwise ->
110 | otherwise ->
104 case (Map.lookup x subs, Map.lookup y subs) of
111 case (Map.lookup x subs, Map.lookup y subs) of
105 (Just (Super xts), Just (Super yts)) ->
112 (Just (Super xts), Just (Super yts)) ->
@@ -108,68 +115,69 @@ solver (C txt span c : cs) subs =
108 in case Set.toList ts of
115 in case Set.toList ts of
109 [] -> unionError txt span xts yts
116 [] -> unionError txt span xts yts
110 [t] -> let cs1 = subst [(x,t),(y,t)] cs in
117 [t] -> let cs1 = subst [(x,t),(y,t)] cs in
111− cs1 `seq` solver cs1 (setXY t subs)
118+ cs1 `seq` solver aliases (setXY t subs) cs1
112− _ -> solver cs $ setXY (Super ts) subs
119+ _ -> solver aliases (setXY (Super ts) subs) cs
113 (Just (Super xts), _) ->
120 (Just (Super xts), _) ->
114 let cs2 = subst [(y,VarT x)] cs in
121 let cs2 = subst [(y,VarT x)] cs in
115− solver cs2 $ Map.insert y (VarT x) subs
122+ solver aliases (Map.insert y (VarT x) subs) cs2
116 (_, _) ->
123 (_, _) ->
117 let cs3 = subst [(x,VarT y)] cs in
124 let cs3 = subst [(x,VarT y)] cs in
118− solver cs3 $ Map.insert x (VarT y) subs
125+ solver aliases (Map.insert x (VarT y) subs) cs3
119
126
120 VarT x :=: t -> do
127 VarT x :=: t -> do
121 if x `occurs` t then occursError txt span (VarT x) t else
128 if x `occurs` t then occursError txt span (VarT x) t else
122 (case Map.lookup x subs of
129 (case Map.lookup x subs of
130+ Nothing ->
123− Nothing -> let cs4 = subst [(x,t)] cs in
131+ let cs4 = subst [(x,t)] cs
124− solver cs4 . Map.map (subst [(x,t)]) $
125− Map.insert x t subs
132+ subs' = Map.map (subst [(x,t)]) $ Map.insert x t subs
133+ in solver aliases subs' cs4
126 Just (Super ts) ->
134 Just (Super ts) ->
127 let ts' = Set.intersection ts (Set.singleton t) in
135 let ts' = Set.intersection ts (Set.singleton t) in
128 case Set.toList ts' of
136 case Set.toList ts' of
129− [] -> solver (ctx (t :<: Super ts) : cs) subs
137+ [] -> solv (ctx (t :<: Super ts) : cs)
130 [t'] -> let cs5 = subst [(x,t)] cs in
138 [t'] -> let cs5 = subst [(x,t)] cs in
131− solver cs5 $ Map.insert x t' subs
139+ solver aliases (Map.insert x t' subs) cs5
132− _ -> solver cs $ Map.insert x (Super ts') subs
140+ _ -> solver aliases (Map.insert x (Super ts') subs) cs
133− Just t' -> solver (ctx (t' :=: t) : cs) subs
141+ Just t' -> solv (ctx (t' :=: t) : cs)
134 )
142 )
135
143
136− t :=: VarT x -> solver ((ctx (VarT x :=: t)) : cs) subs
144+ t :=: VarT x -> solv ((ctx (VarT x :=: t)) : cs)
137
145
138− t1 :=: t2 | t1 == t2 -> solver cs subs
146+ t1 :=: t2 | t1 == t2 -> solv cs
139− | otherwise -> uniError txt span t1 t2
147+ | otherwise -> uniError' t1 t2
140
148
141 -- subtypes
149 -- subtypes
142 VarT x :<: Super ts ->
150 VarT x :<: Super ts ->
143 case Map.lookup x subs of
151 case Map.lookup x subs of
144− Nothing -> solver cs $ Map.insert x (Super ts) subs
152+ Nothing -> solver aliases (Map.insert x (Super ts) subs) cs
145 Just (Super ts') ->
153 Just (Super ts') ->
146 case Set.toList $ Set.intersection ts ts' of
154 case Set.toList $ Set.intersection ts ts' of
147 [] -> unionError txt span ts ts'
155 [] -> unionError txt span ts ts'
148− [t] -> solver (subst [(x,t)] cs) $ Map.insert x t subs
156+ [t] -> solver aliases (Map.insert x t subs) (subst [(x,t)] cs)
149− ts'' -> solver cs $
157+ ts'' -> solver aliases subs' cs
150− Map.insert x (Super $ Set.fromList ts'') subs
158+ where subs' = Map.insert x (Super $ Set.fromList ts'') subs
151
159
152 ADT "List" [t] :<: Super ts
160 ADT "List" [t] :<: Super ts
153− | any f (Set.toList ts) -> solver cs subs
161+ | any f (Set.toList ts) -> solv cs
154 | otherwise -> subtypeError txt span (ADT "List" [t]) (Super ts)
162 | otherwise -> subtypeError txt span (ADT "List" [t]) (Super ts)
155 where f (ADT "List" [VarT _]) = True
163 where f (ADT "List" [VarT _]) = True
156− f (ADT "List" [t']) = t == t'
164+ f (ADT "List" [t']) = dealias aliases t == t'
157 f _ = False
165 f _ = False
158
166
159 t :<: Super ts
167 t :<: Super ts
160− | Set.member t ts -> solver cs subs
168+ | Set.member t ts -> solv cs
169+ | Set.member (dealias aliases t) ts -> solv cs
161− | otherwise -> subtypeError txt span t (Super ts)
170+ | otherwise -> subtypeError txt span t (Super ts)
162
171
163 x :<<: s
172 x :<<: s
164 | any (occurs x) cs ->
173 | any (occurs x) cs ->
165− do css <- mapM (schemeSub x s) cs
174+ do css <- mapM (schemeSub aliases x s) cs
166 case lefts css of
175 case lefts css of
167 err : _ -> return $ Left err
176 err : _ -> return $ Left err
168− [] -> solver (concat (rights css)) subs
177+ [] -> solv (concat (rights css))
169 | otherwise ->
178 | otherwise ->
170 do (t,cs7) <- concretize s
179 do (t,cs7) <- concretize s
171− let cs'' = (cs ++ ctx (VarT x :=: t) : cs7)
180+ solv (cs ++ ctx (VarT x :=: t) : cs7)
172− solver cs'' subs
173
181
174showMsg msg = case msg of
182showMsg msg = case msg of
175 Just str -> "\nIn context: " ++ str
183 Just str -> "\nIn context: " ++ str
@@ -181,10 +189,14 @@ occursError msg span t1 t2 =
181 , "Occurs check: cannot construct the infinite type:\n"
189 , "Occurs check: cannot construct the infinite type:\n"
182 , show t1, " = ", show t2, showMsg msg ]
190 , show t1, " = ", show t2, showMsg msg ]
183
191
184−uniError msg span t1 t2 =
192+uniError solveWith aliases msg span t1 t2 =
193+ let t1' = dealias aliases t1
194+ t2' = dealias aliases t2
195+ in if t1 /= t1' || t2 /= t2'
196+ then solveWith t1' t2'
185− return . Left $ concat
197+ else return . Left $ concat
186− [ "Type error (" ++ show span ++ "):\n"
198+ [ "Type error (" ++ show span ++ "):\n"
187− , show t1, " is not equal to ", show t2, showMsg msg ]
199+ , show t1, " is not equal to ", show t2, showMsg msg ]
188
200
189unionError msg span ts ts' =
201unionError msg span ts ts' =
190 return . Left $ concat
202 return . Left $ concat
elm/src/Types/Substitutions.hs → compiler/Types/Substitutions.hsrenamed+58−12
@@ -1,16 +1,17 @@
1−
1+{-# LANGUAGE GeneralizedNewtypeDeriving #-}
2module Types.Substitutions (subst,
2module Types.Substitutions (subst,
3 occurs,
3 occurs,
4 freeVars,
4 freeVars,
5 concretize,
5 concretize,
6 rescheme,
6 rescheme,
7− generalize) where
7+ generalize,
8+ superize) where
8
9
9import Ast
10import Ast
10import Context
11import Context
11−import Control.DeepSeq (NFData (..), deepseq)
12+import Control.Monad (liftM, liftM2)
12−import Control.Monad (liftM)
13+import Control.Monad.State (runState, State, get, put)
13−import Data.List (foldl')
14+import Data.List (nub)
14import qualified Data.Set as Set
15import qualified Data.Set as Set
15import qualified Data.Map as Map
16import qualified Data.Map as Map
16import Guid
17import Guid
@@ -51,13 +52,14 @@ class FreeVars a where
51 freeVars :: a -> [X]
52 freeVars :: a -> [X]
52
53
53instance FreeVars Type where
54instance FreeVars Type where
54− freeVars (VarT v) = [v]
55+ freeVars t =
56+ case t of
57+ VarT v -> [v]
55− freeVars (LambdaT t1 t2) = freeVars t1 ++ freeVars t2
58+ LambdaT t1 t2 -> freeVars t1 ++ freeVars t2
56− freeVars (ADT _ ts) = concatMap freeVars ts
59+ ADT _ ts -> concatMap freeVars ts
57− freeVars (RecordT fs t) =
58− freeVars (concat $ Map.elems fs) ++ freeVars t
60+ RecordT fs t -> freeVars (concat $ Map.elems fs) ++ freeVars t
59− freeVars EmptyRecord = []
61+ EmptyRecord -> []
60− freeVars (Super _ ) = []
62+ Super _ -> []
61
63
62instance FreeVars Constraint where
64instance FreeVars Constraint where
63 freeVars (t1 :=: t2) = freeVars t1 ++ freeVars t2
65 freeVars (t1 :=: t2) = freeVars t1 ++ freeVars t2
@@ -88,3 +90,47 @@ generalize :: [X] -> Scheme -> GuidCounter Scheme
88generalize exceptions (Forall xs cs t) = rescheme (Forall (xs ++ frees) cs t)
90generalize exceptions (Forall xs cs t) = rescheme (Forall (xs ++ frees) cs t)
89 where allFrees = Set.fromList $ freeVars t ++ concatMap freeVars cs
91 where allFrees = Set.fromList $ freeVars t ++ concatMap freeVars cs
90 frees = Set.toList $ Set.difference allFrees (Set.fromList exceptions)
92 frees = Set.toList $ Set.difference allFrees (Set.fromList exceptions)
93+
94+newtype Superize a = S { runSuper :: State ([X], [X], [X]) a }
95+ deriving (Monad)
96+
97+superize :: String -> Type -> GuidCounter Scheme
98+superize name tipe =
99+ do constraints <- liftM concat $
100+ sequence [ mapM (<: nmbr) (nub ns)
101+ , mapM (<: apnd) (nub as)
102+ , mapM (<: comp) (nub cs) ]
103+ return (Forall (concat [ns,as,cs]) constraints tipe')
104+ where
105+ (tipe', (ns,as,cs)) = runState (runSuper (go tipe)) ([],[],[])
106+ t <: super = do x <- guid
107+ return $ C (Just name) NoSpan (VarT t :<: super x)
108+
109+ nmbr t = number
110+ apnd t = appendable t
111+ comp t = comparable t
112+
113+ go :: Type -> Superize Type
114+ go t =
115+ case t of
116+ EmptyRecord -> return t
117+ Super _ -> return t
118+ VarT _ -> return t
119+ LambdaT t1 t2 -> liftM2 LambdaT (go t1) (go t2)
120+ ADT "Number" [VarT t] -> addNumber t
121+ ADT "Appendable" [VarT t] -> addAppendable t
122+ ADT "Comparable" [VarT t] -> addComparable t
123+ ADT name ts -> liftM (ADT name) (mapM go ts)
124+ RecordT fs t -> liftM2 RecordT fs' (go t)
125+ where pairs = Map.toList fs
126+ fs' = do ps <- mapM (\(f,t) -> liftM ((,) f) (mapM go t)) pairs
127+ return (Map.fromList ps)
128+
129+ add :: (X -> ([X],[X],[X]) -> ([X],[X],[X])) -> X -> Superize Type
130+ add f v = S $ do (ns, as, cs) <- get
131+ put $ f v (ns, as, cs)
132+ return (VarT v)
133+
134+ addNumber = add (\n (ns,as,cs) -> (n:ns,as,cs))
135+ addAppendable = add (\a (ns,as,cs) -> (ns,a:as,cs))
136+ addComparable = add (\c (ns,as,cs) -> (ns,as,c:cs))
compiler/Types/Types.hsnew file+94
@@ -0,0 +1,94 @@
1+
2+module Types.Types where
3+
4+import Context
5+import Data.Char (isDigit)
6+import Data.List (intercalate,isPrefixOf)
7+import qualified Data.Set as Set
8+import qualified Data.Map as Map
9+
10+type X = Int
11+
12+data Type = LambdaT Type Type
13+ | VarT X
14+ | ADT String [Type]
15+ | EmptyRecord
16+ | RecordT (Map.Map String [Type]) Type
17+ | Super (Set.Set Type)
18+ deriving (Eq, Ord)
19+
20+data Scheme = Forall [X] [Context Constraint] Type deriving (Eq, Ord, Show)
21+
22+data Constraint = Type :=: Type
23+ | Type :<: Type
24+ | X :<<: Scheme
25+ deriving (Eq, Ord, Show)
26+
27+recordT :: [(String,Type)] -> Map.Map String [Type]
28+recordT fields =
29+ foldl (\r (x,t) -> Map.insertWith (++) x [t] r) Map.empty fields
30+
31+recordOf :: [(String,Type)] -> Type
32+recordOf fields = RecordT (recordT fields) EmptyRecord
33+
34+tipe t = ADT t []
35+
36+int = tipe "Int"
37+float = tipe "Float"
38+time = tipe "Time"
39+date = tipe "Date"
40+
41+char = tipe "Char"
42+bool = tipe "Bool"
43+text = tipe "Text"
44+order = tipe "Order"
45+string = tipe "String"
46+
47+number = Super $ Set.fromList [ int, float, time ]
48+appendable t = Super $ Set.fromList [ string, text, listOf (VarT t) ]
49+comparable t = Super $ Set.fromList [ int, float, char, string, time, date ]
50+
51+element = tipe "Element"
52+
53+listOf t = ADT "List" [t]
54+signalOf t = ADT "Signal" [t]
55+tupleOf ts = ADT ("Tuple" ++ show (length ts)) ts
56+maybeOf t = ADT "Maybe" [t]
57+eitherOf a b = ADT "Either" [a,b]
58+pairOf t = tupleOf [t,t]
59+point = pairOf int
60+
61+infixr ==>
62+t1 ==> t2 = LambdaT t1 t2
63+
64+infix 8 -:
65+name -: tipe = (,) name $ Forall [] [] tipe
66+
67+parens = ("("++) . (++")")
68+
69+instance Show Type where
70+ show t =
71+ let addParens (c:cs) =
72+ if notElem ' ' cs || c == '(' then c:cs else parens (c:cs)
73+ in case t of
74+ LambdaT t1@(LambdaT _ _) t2 -> parens (show t1) ++ " -> " ++ show t2
75+ LambdaT t1 t2 -> show t1 ++ " -> " ++ show t2
76+ VarT x -> 't' : show x
77+ ADT "List" [ADT "Char" []] -> "String"
78+ ADT "List" [tipe] -> "[" ++ show tipe ++ "]"
79+ ADT name cs ->
80+ if isTupleString name
81+ then parens . intercalate "," $ map show cs
82+ else name ++ concatMap ((' ':) . addParens . show) cs
83+ Super ts -> "{" ++ (intercalate "," . map show $ Set.toList ts) ++ "}"
84+ EmptyRecord -> "{}"
85+ RecordT fs t ->
86+ start ++ intercalate ", " (concatMap fields $ Map.toList fs) ++ " }"
87+ where field n s = n ++ " : " ++ show s
88+ fields (n,ss) = map (field n) ss
89+ start = case t of
90+ EmptyRecord -> "{ "
91+ _ -> "{ " ++ show t ++ " | "
92+
93+
94+isTupleString str = "Tuple" `isPrefixOf` str && all isDigit (drop 5 str)
compiler/Types/Unify.hsnew file+16
@@ -0,0 +1,16 @@
1+
2+module Types.Unify (unify) where
3+
4+import Control.Monad (liftM)
5+import qualified Data.Map as Map
6+
7+import Ast
8+import Guid
9+import Types.Constrain
10+import Types.Solver
11+import Types.Alias as Alias
12+
13+unify hints modul@(Module _ _ _ stmts) = run $ do
14+ constraints <- constrain hints modul
15+ either (return . Left) (solver (Alias.get stmts) Map.empty) constraints
16+
core-js/Automaton.jsdeleted−221
@@ -1,221 +0,0 @@
1−
2−(function() {
3−try{
4−
5−var $op={};
6−for(this['i'] in Elm){eval('var '+this['i']+'=Elm[this.i];');}
7−if (Elm.Automaton) throw new Error("Module name collision, 'Automaton' is already defined.");
8−Elm.Automaton=function(){
9− try{
10− if (!(Elm.Prelude instanceof Object)) throw 'module not found';
11− } catch(e) {
12− throw ("Module 'Prelude' is missing. Compile with --make flag or load missing module in a separate JavaScript file.");
13− }
14− var hiddenVars={};
15− for (this['i'] in Elm.Prelude) {
16− if (hiddenVars[this['i']]) continue;
17− eval('var ' + this['i'] + ' = Elm.Prelude[this.i];');}
18− function Automaton_0(a1){
19− return ["Automaton",a1];}
20− var Listen_8=["Listen"];
21− var Ignore_9=["Ignore"];
22− function DragFrom_10(a1){
23− return ["DragFrom",a1];}
24− $op['>>>'] = function(a1_24){
25− return function(a2_25){
26− return function(){
27− var Automaton$m1_26=a1_24;
28− var m1_27=function(){
29− switch(Automaton$m1_26[0]){
30− case "Automaton":
31− return Automaton$m1_26[1];
32− }
33− throw new Error("Non-exhaustive pattern match in case");}();
34− var Automaton$m2_28=a2_25;
35− var m2_29=function(){
36− switch(Automaton$m2_28[0]){
37− case "Automaton":
38− return Automaton$m2_28[1];
39− }
40− throw new Error("Non-exhaustive pattern match in case");}();
41− return Automaton_0(function(a_32){
42− return function(){
43− var Tuple2$bm1__33=m1_27(a_32);
44− var b_34=function(){
45− switch(Tuple2$bm1__33[0]){
46− case "Tuple2":
47− return Tuple2$bm1__33[1];
48− }
49− throw new Error("Non-exhaustive pattern match in case");}();
50− var m1__35=function(){
51− switch(Tuple2$bm1__33[0]){
52− case "Tuple2":
53− return Tuple2$bm1__33[2];
54− }
55− throw new Error("Non-exhaustive pattern match in case");}();
56− return function(){
57− var Tuple2$cm2__40=m2_29(b_34);
58− var c_41=function(){
59− switch(Tuple2$cm2__40[0]){
60− case "Tuple2":
61− return Tuple2$cm2__40[1];
62− }
63− throw new Error("Non-exhaustive pattern match in case");}();
64− var m2__42=function(){
65− switch(Tuple2$cm2__40[0]){
66− case "Tuple2":
67− return Tuple2$cm2__40[2];
68− }
69− throw new Error("Non-exhaustive pattern match in case");}();
70− return ["Tuple2",c_41,$op['>>>'](m1__35)(m2__42)];}();}();});}();};};
71− $op['<<<'] = function(a2_47){
72− return function(a1_48){
73− return $op['>>>'](a1_48)(a2_47);};};
74− $op['^>>'] = function(f_49){
75− return function(a_50){
76− return $op['>>>'](pure_4(f_49))(a_50);};};
77− $op['>>^'] = function(a_51){
78− return function(f_52){
79− return $op['>>>'](a_51)(pure_4(f_52));};};
80− $op['^<<'] = function(f_53){
81− return function(a_54){
82− return $op['>>>'](a_54)(pure_4(f_53));};};
83− $op['<<^'] = function(a_55){
84− return function(f_56){
85− return $op['>>>'](pure_4(f_56))(a_55);};};
86− var count_7=init_5(0)(function(__84){
87− return function(c_85){
88− return (1+c_85);};});
89− function run_1(Automaton$m0_14){
90− return function(input_15){
91− return function(){
92− switch(Automaton$m0_14[0]){
93− case "Automaton":
94− return lift(fst)(foldp$(function(a_17){
95− return function(Tuple2$bAutomaton$m_18){
96− return function(){
97− switch(Tuple2$bAutomaton$m_18[0]){
98− case "Tuple2":
99− switch(Tuple2$bAutomaton$m_18[2][0]){
100− case "Automaton":
101− return Tuple2$bAutomaton$m_18[2][1](a_17);
102− }break;
103− }
104− throw new Error("Non-exhaustive pattern match in case");}();};})(Automaton$m0_14[1])(input_15));
105− }
106− throw new Error("Non-exhaustive pattern match in case");}();};}
107− function step_2(Automaton$m_21){
108− return function(a_22){
109− return function(){
110− switch(Automaton$m_21[0]){
111− case "Automaton":
112− return Automaton$m_21[1](a_22);
113− }
114− throw new Error("Non-exhaustive pattern match in case");}();};}
115− function combine_3(autos_57){
116− return Automaton_0(function(a_58){
117− return function(){
118− var Tuple2$bsautos__59=unzip(map(function(Automaton$m_62){
119− return function(){
120− switch(Automaton$m_62[0]){
121− case "Automaton":
122− return Automaton$m_62[1](a_58);
123− }
124− throw new Error("Non-exhaustive pattern match in case");}();})(autos_57));
125− var bs_60=function(){
126− switch(Tuple2$bsautos__59[0]){
127− case "Tuple2":
128− return Tuple2$bsautos__59[1];
129− }
130− throw new Error("Non-exhaustive pattern match in case");}();
131− var autos__61=function(){
132− switch(Tuple2$bsautos__59[0]){
133− case "Tuple2":
134− return Tuple2$bsautos__59[2];
135− }
136− throw new Error("Non-exhaustive pattern match in case");}();
137− return ["Tuple2",bs_60,combine_3(autos__61)];}();});}
138− function pure_4(f_68){
139− return Automaton_0(function(x_69){
140− return ["Tuple2",f_68(x_69),pure_4(f_68)];});}
141− function init_5(s_70){
142− return function(step_71){
143− return Automaton_0(function(a_72){
144− return function(){
145− var s__73=step_71(a_72)(s_70);
146− return ["Tuple2",s__73,init_5(s__73)(step_71)];}();});};}
147− function init__6(s_74){
148− return function(step_75){
149− return Automaton_0(function(a_76){
150− return function(){
151− var Tuple2$bs__77=step_75(a_76)(s_74);
152− var b_78=function(){
153− switch(Tuple2$bs__77[0]){
154− case "Tuple2":
155− return Tuple2$bs__77[1];
156− }
157− throw new Error("Non-exhaustive pattern match in case");}();
158− var s__79=function(){
159− switch(Tuple2$bs__77[0]){
160− case "Tuple2":
161− return Tuple2$bs__77[2];
162− }
163− throw new Error("Non-exhaustive pattern match in case");}();
164− return ["Tuple2",b_78,init__6(s__79)(step_75)];}();});};}
165− function vecSub_11(Tuple2$x1y1_86){
166− return function(Tuple2$x2y2_87){
167− return function(){
168− switch(Tuple2$x1y1_86[0]){
169− case "Tuple2":
170− return function(){
171− switch(Tuple2$x2y2_87[0]){
172− case "Tuple2":
173− return ["Tuple2",(Tuple2$x1y1_86[1]-Tuple2$x2y2_87[1]),(Tuple2$x1y1_86[2]-Tuple2$x2y2_87[2])];
174− }
175− throw new Error("Non-exhaustive pattern match in case");}();
176− }
177− throw new Error("Non-exhaustive pattern match in case");}();};}
178− function stepDrag_12(Tuple2$presspos_92){
179− return function(Tuple2$dsform_93){
180− return function(){
181− switch(Tuple2$presspos_92[0]){
182− case "Tuple2":
183− return function(){
184− switch(Tuple2$dsform_93[0]){
185− case "Tuple2":
186− return function(){
187− function wrap_98(ds__99){
188− return ["Tuple2",Tuple2$dsform_93[2],["Tuple2",ds__99,Tuple2$dsform_93[2]]];}
189− return function(){
190− switch(Tuple2$dsform_93[1][0]){
191− case "DragFrom":
192− return (Tuple2$presspos_92[1]?["Tuple2",uncurry(move)(vecSub_11(Tuple2$presspos_92[2])(Tuple2$dsform_93[1][1]))(Tuple2$dsform_93[2]),["Tuple2",DragFrom_10(Tuple2$dsform_93[1][1]),Tuple2$dsform_93[2]]]:function(){
193− var form__101=uncurry(move)(vecSub_11(Tuple2$presspos_92[2])(Tuple2$dsform_93[1][1]))(Tuple2$dsform_93[2]);
194− return ["Tuple2",form__101,["Tuple2",Listen_8,form__101]];}());
195− case "Ignore":
196− return wrap_98((Tuple2$presspos_92[1]?Ignore_9:Listen_8));
197− case "Listen":
198− return wrap_98((not(Tuple2$presspos_92[1])?Listen_8:(isWithin(Tuple2$presspos_92[2])(Tuple2$dsform_93[2])?DragFrom_10(Tuple2$presspos_92[2]):Ignore_9)));
199− }
200− throw new Error("Non-exhaustive pattern match in case");}();}();
201− }
202− throw new Error("Non-exhaustive pattern match in case");}();
203− }
204− throw new Error("Non-exhaustive pattern match in case");}();};}
205− function draggable_13(form_102){
206− return init__6(["Tuple2",Listen_8,form_102])(stepDrag_12);}
207− return {$op : {'>>>' : $op['>>>'], '<<<' : $op['<<<'], '^>>' : $op['^>>'], '>>^' : $op['>>^'], '^<<' : $op['^<<'], '<<^' : $op['<<^']},
208− run:run_1,
209− step:step_2,
210− combine:combine_3,
211− pure:pure_4,
212− init:init_5,
213− init$:init__6,
214− count:count_7,
215− draggable:draggable_13};}();
216−Elm.main=function(){
217− return Elm.Automaton.main;};
218−} catch (e) {
219−Elm.main=function() {
220−var msg = ('<br/><h2>Your browser may not be supported. Are you using a modern browser?</h2>' + '<br/><span style="color:grey">Runtime Error in Automaton module:<br/>' + e + '</span>');
221−document.body.innerHTML = Elm.Text.monospace(msg);throw e;};}}());
core-js/Char.jsdeleted−64
@@ -1,64 +0,0 @@
1−/*! Char !*/
2−
3−/*[Classification]*/
4−
5−/** isUpper : Char -> Bool
6− Selects upper case letters.
7−**/
8−/** isLower : Char -> Bool
9− Selects lower case letters.
10−**/
11−/** isDigit : Char -> Bool
12− Selects ASCII digits (0..9).
13−**/
14−/** isOctDigit : Char -> Bool
15− Selects ASCII octal digits (0..7).
16−**/
17−/** isHexDigit : Char -> Bool
18− Selects ASCII hexadecimal digits (0..9a..fA..F).
19−**/
20−
21−/*[Conversion]*/
22−
23−/** toUpper : Char -> Char
24− Convert to upper case.
25−**/
26−/** toLower : Char -> Char
27− Convert to lower case.
28−**/
29−/** toLocaleUpper : Char -> Char
30− Convert to upper case, according to any locale-specific case mappings.
31−**/
32−/** toLocaleLower : Char -> Char
33− Convert to lower case, according to any locale-specific case mappings.
34−**/
35−/** toCode : Char -> Int
36− Convert to unicode.
37−**/
38−/** fromCode : Int -> Char
39− Convert from unicode.
40−**/
41−
42−Elm.Char = function() {
43− function isBetween(lo,hi) { return function(chr) {
44− var c = chr.charCodeAt(0);
45− return lo <= c && c <= hi;
46− };
47− }
48− var isDigit = isBetween('0'.charCodeAt(0),'9'.charCodeAt(0));
49− var chk1 = isBetween('a'.charCodeAt(0),'f'.charCodeAt(0));
50− var chk2 = isBetween('A'.charCodeAt(0),'F'.charCodeAt(0));
51−
52− return {fromCode : function(c) { return String.fromCharCode(c); },
53− toCode : function(c) { return c.charCodeAt(0); },
54− toUpper : function(c) { return c.toUpperCase(); },
55− toLower : function(c) { return c.toLowerCase(); },
56− toLocaleUpper : function(c) { return c.toLocaleUpperCase(); },
57− toLocaleLower : function(c) { return c.toLocaleLowerCase(); },
58− isLower : isBetween('a'.charCodeAt(0),'z'.charCodeAt(0)),
59− isUpper : isBetween('A'.charCodeAt(0),'Z'.charCodeAt(0)),
60− isDigit : isDigit,
61− isOctDigit : isBetween('0'.charCodeAt(0),'7'.charCodeAt(0)),
62− isHexDigit : function(c) { return isDigit(c) || chk1(c) || chk2(c); }
63− };
64−}();
core-js/Date.jsdeleted−32
@@ -1,32 +0,0 @@
1−
2−Elm.Date = function() {
3−
4− function dateNow() { return new window.Date; }
5− function readDate(str) {
6− var d = new window.Date(Elm.JavaScript.castStringToJSString(str));
7− if (isNaN(d.getTime())) return ["Nothing"];
8− return ["Just",d];
9− }
10−
11− var dayTable = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
12− var monthTable = ["Jan", "Feb", "Mar", "Apr", "May", "Jun",
13− "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"];
14−
15− return {
16− read : readDate,
17− year : function(d) { return d.getFullYear(); },
18− month : function(d) { return [monthTable[d.getMonth()]]; },
19− day : function(d) { return d.getDate(); },
20− hour : function(d) { return d.getHours(); },
21− minute : function(d) { return d.getMinutes(); },
22− second : function(d) { return d.getSeconds(); },
23− dayOfWeek : function(d) { return [dayTable[d.getDay()]]; },
24− toTime : function(d) { return d.getTime(); },
25− Mon : ["Mon"], Tue : ["Tue"], Wed : ["Wed"],
26− Thu : ["Thu"], Fri : ["Fri"], Sat : ["Sat"], Sun : ["Sun"],
27− Jan : ["Jan"], Feb : ["Feb"], Mar : ["Mar"], Apr : ["Apr"],
28− May : ["May"], Jun : ["Jun"], Jul : ["Jul"], Aug : ["Aug"],
29− Sep : ["Sep"], Oct : ["Oct"], Nov : ["Nov"], Dec : ["Dec"]
30− };
31−
32−}();
core-js/Dict.jsdeleted−485
@@ -1,485 +0,0 @@
1−
2−Elm.Dict=function(){
3− var compare = Elm.Prelude.compare;
4− var uncurry = Elm.Prelude.uncurry;
5− var Nothing = Elm.Prelude.Nothing;
6− var Just = Elm.Prelude.Just;
7− var not = Elm.Prelude.not;
8− var eq = Elm.Prelude.eq;
9− var isJust=Elm.Maybe.isJust;
10− var Red_0=['Red'];
11− var Black_1=['Black'];
12− function RBNode_2(a1){
13− return function(a2){
14− return function(a3){
15− return function(a4){
16− return function(a5){
17− return ['RBNode',a1,a2,a3,a4,a5];};};};};}
18− var RBEmpty_3=['RBEmpty'];
19− function min_6(t_42){
20− return function(){
21− switch(t_42[0]){
22− case 'RBEmpty':
23− throw '(min RBEmpty) is not defined';
24− case 'RBNode':
25− switch(t_42[4][0]){
26− case 'RBEmpty':
27− return ['Tuple2',t_42[2],t_42[3]];
28− }
29− return min_6(t_42[4]);
30− }
31− throw new Error("Non-exhaustive pattern match in case");}();}
32− function lookup_7(k_46){
33− return function(t_47){
34− return function(){
35− switch(t_47[0]){
36− case 'RBEmpty':
37− return Nothing;
38− case 'RBNode':
39− return function(){
40− var case12=compare(k_46)(t_47[2]);
41− switch(case12[0]){
42− case 'EQ':
43− return Just(t_47[3]);
44− case 'GT':
45− return lookup_7(k_46)(t_47[5]);
46− case 'LT':
47− return lookup_7(k_46)(t_47[4]);
48− }
49− throw new Error("Non-exhaustive pattern match in case");}();
50− }
51− throw new Error("Non-exhaustive pattern match in case");}();};}
52− function findWithDefault_8(base_52){
53− return function(k_53){
54− return function(t_54){
55− return function(){
56− switch(t_54[0]){
57− case 'RBEmpty':
58− return base_52;
59− case 'RBNode':
60− return function(){
61− var case19=compare(k_53)(t_54[2]);
62− switch(case19[0]){
63− case 'EQ':
64− return t_54[3];
65− case 'GT':
66− return findWithDefault_8(base_52)(k_53)(t_54[5]);
67− case 'LT':
68− return findWithDefault_8(base_52)(k_53)(t_54[4]);
69− }
70− throw new Error("Non-exhaustive pattern match in case");}();
71− }
72− throw new Error("Non-exhaustive pattern match in case");}();};};}
73− function member_9(k_59){
74− return function(t_60){
75− return isJust(lookup_7(k_59)(t_60));};}
76− function rotateLeft_10(t_61){
77− return function(){
78− switch(t_61[0]){
79− case 'RBNode':
80− switch(t_61[5][0]){
81− case 'RBNode':
82− return RBNode_2(t_61[1])(t_61[5][2])(t_61[5][3])(RBNode_2(Red_0)(t_61[2])(t_61[3])(t_61[4])(t_61[5][4]))(t_61[5][5]);
83− }break;
84− }
85− throw 'rotateLeft of a node without enough children';}();}
86− function rotateRight_11(t_71){
87− return function(){
88− switch(t_71[0]){
89− case 'RBNode':
90− switch(t_71[4][0]){
91− case 'RBNode':
92− return RBNode_2(t_71[1])(t_71[4][2])(t_71[4][3])(t_71[4][4])(RBNode_2(Red_0)(t_71[2])(t_71[3])(t_71[4][5])(t_71[5]));
93− }break;
94− }
95− throw 'rotateRight of a node without enough children';}();}
96− function rotateLeftIfNeeded_12(t_81){
97− return function(){
98− switch(t_81[0]){
99− case 'RBNode':
100− switch(t_81[5][0]){
101− case 'RBNode':
102− switch(t_81[5][1][0]){
103− case 'Red':
104− return rotateLeft_10(t_81);
105− }break;
106− }break;
107− }
108− return t_81;}();}
109− function rotateRightIfNeeded_13(t_82){
110− return function(){
111− switch(t_82[0]){
112− case 'RBNode':
113− switch(t_82[4][0]){
114− case 'RBNode':
115− switch(t_82[4][1][0]){
116− case 'Red':
117− switch(t_82[4][4][0]){
118− case 'RBNode':
119− switch(t_82[4][4][1][0]){
120− case 'Red':
121− return rotateRight_11(t_82);
122− }break;
123− }break;
124− }break;
125− }break;
126− }
127− return t_82;}();}
128− function otherColor_14(c_83){
129− return function(){
130− switch(c_83[0]){
131− case 'Black':
132− return Red_0;
133− case 'Red':
134− return Black_1;
135− }
136− throw new Error("Non-exhaustive pattern match in case");}();}
137− function color_flip_15(t_84){
138− return function(){
139− switch(t_84[0]){
140− case 'RBNode':
141− switch(t_84[4][0]){
142− case 'RBNode':
143− switch(t_84[5][0]){
144− case 'RBNode':
145− return RBNode_2(otherColor_14(t_84[1]))(t_84[2])(t_84[3])(RBNode_2(otherColor_14(t_84[4][1]))(t_84[4][2])(t_84[4][3])(t_84[4][4])(t_84[4][5]))(RBNode_2(otherColor_14(t_84[5][1]))(t_84[5][2])(t_84[5][3])(t_84[5][4])(t_84[5][5]));
146− }break;
147− }break;
148− }
149− throw 'color_flip called on a RBEmpty or RBNode with a RBEmpty child';}();}
150− function color_flipIfNeeded_16(t_98){
151− return function(){
152− switch(t_98[0]){
153− case 'RBNode':
154− switch(t_98[4][0]){
155− case 'RBNode':
156− switch(t_98[4][1][0]){
157− case 'Red':
158− switch(t_98[5][0]){
159− case 'RBNode':
160− switch(t_98[5][1][0]){
161− case 'Red':
162− return color_flip_15(t_98);
163− }break;
164− }break;
165− }break;
166− }break;
167− }
168− return t_98;}();}
169− function fixUp_17(t_99){
170− return color_flipIfNeeded_16(rotateRightIfNeeded_13(rotateLeftIfNeeded_12(t_99)));}
171− function ensureBlackRoot_18(t_100){
172− return function(){
173− switch(t_100[0]){
174− case 'RBNode':
175− switch(t_100[1][0]){
176− case 'Red':
177− return RBNode_2(Black_1)(t_100[2])(t_100[3])(t_100[4])(t_100[5]);
178− }break;
179− }
180− return t_100;}();}
181− function insert_19(k_105){
182− return function(v_106){
183− return function(t_107){
184− return function(){
185− function ins_108(t_109){
186− return function(){
187− switch(t_109[0]){
188− case 'RBEmpty':
189− return RBNode_2(Red_0)(k_105)(v_106)(RBEmpty_3)(RBEmpty_3);
190− case 'RBNode':
191− return function(){
192− var h_115=function(){
193− var case114=compare(k_105)(t_109[2]);
194− switch(case114[0]){
195− case 'EQ':
196− return RBNode_2(t_109[1])(t_109[2])(v_106)(t_109[4])(t_109[5]);
197− case 'GT':
198− return RBNode_2(t_109[1])(t_109[2])(t_109[3])(t_109[4])(ins_108(t_109[5]));
199− case 'LT':
200− return RBNode_2(t_109[1])(t_109[2])(t_109[3])(ins_108(t_109[4]))(t_109[5]);
201− }
202− throw new Error("Non-exhaustive pattern match in case");}();
203− return fixUp_17(h_115);}();
204− }
205− throw new Error("Non-exhaustive pattern match in case");}();}
206− return ensureBlackRoot_18(ins_108(t_107));}();};};}
207− function singleton_20(k_116){
208− return function(v_117){
209− return insert_19(k_116)(v_117)(RBEmpty_3);};}
210− function isRed_21(t_118){
211− return function(){
212− switch(t_118[0]){
213− case 'RBNode':
214− switch(t_118[1][0]){
215− case 'Red':
216− return true;
217− }break;
218− }
219− return false;}();}
220− function isRedLeft_22(t_119){
221− return function(){
222− switch(t_119[0]){
223− case 'RBNode':
224− switch(t_119[4][0]){
225− case 'RBNode':
226− switch(t_119[4][1][0]){
227− case 'Red':
228− return true;
229− }break;
230− }break;
231− }
232− return false;}();}
233− function isRedLeftLeft_23(t_120){
234− return function(){
235− switch(t_120[0]){
236− case 'RBNode':
237− switch(t_120[4][0]){
238− case 'RBNode':
239− switch(t_120[4][4][0]){
240− case 'RBNode':
241− switch(t_120[4][4][1][0]){
242− case 'Red':
243− return true;
244− }break;
245− }break;
246− }break;
247− }
248− return false;}();}
249− function isRedRight_24(t_121){
250− return function(){
251− switch(t_121[0]){
252− case 'RBNode':
253− switch(t_121[5][0]){
254− case 'RBNode':
255− switch(t_121[5][1][0]){
256− case 'Red':
257− return true;
258− }break;
259− }break;
260− }
261− return false;}();}
262− function isRedRightLeft_25(t_122){
263− return function(){
264− switch(t_122[0]){
265− case 'RBNode':
266− switch(t_122[5][0]){
267− case 'RBNode':
268− switch(t_122[5][4][0]){
269− case 'RBNode':
270− switch(t_122[5][4][1][0]){
271− case 'Red':
272− return true;
273− }break;
274− }break;
275− }break;
276− }
277− return false;}();}
278− function moveRedLeft_26(t_123){
279− return function(){
280− var t__124=color_flip_15(t_123);
281− return function(){
282− switch(t__124[0]){
283− case 'RBNode':
284− return function(){
285− switch(t__124[5][0]){
286− case 'RBNode':
287− switch(t__124[5][4][0]){
288− case 'RBNode':
289− switch(t__124[5][4][1][0]){
290− case 'Red':
291− return color_flip_15(rotateLeft_10(RBNode_2(t__124[1])(t__124[2])(t__124[3])(t__124[4])(rotateRight_11(t__124[5]))));
292− }break;
293− }break;
294− }
295− return t__124;}();
296− }
297− return t__124;}();}();}
298− function moveRedRight_27(t_130){
299− return function(){
300− var t__131=color_flip_15(t_130);
301− return (isRedLeftLeft_23(t__131)?color_flip_15(rotateRight_11(t__131)):t__131);}();}
302− function moveRedLeftIfNeeded_28(t_132){
303− return ((not(isRedLeft_22(t_132))&&not(isRedLeftLeft_23(t_132)))?moveRedLeft_26(t_132):t_132);}
304− function moveRedRightIfNeeded_29(t_133){
305− return ((not(isRedRight_24(t_133))&&not(isRedRightLeft_25(t_133)))?moveRedRight_27(t_133):t_133);}
306− function deleteMin_30(t_134){
307− return function(){
308− function del_135(t_136){
309− return function(){
310− switch(t_136[0]){
311− case 'RBNode':
312− switch(t_136[4][0]){
313− case 'RBEmpty':
314− return RBEmpty_3;
315− }break;
316− }
317− return function(){
318− var case198=moveRedLeftIfNeeded_28(t_136);
319− switch(case198[0]){
320− case 'RBEmpty':
321− return RBEmpty_3;
322− case 'RBNode':
323− return fixUp_17(RBNode_2(case198[1])(case198[2])(case198[3])(del_135(case198[4]))(case198[5]));
324− }
325− throw new Error("Non-exhaustive pattern match in case");}();}();}
326− return ensureBlackRoot_18(del_135(t_134));}();}
327− function remove_31(k_142){
328− return function(t_143){
329− return function(){
330− function eq_and_noRightNode_144(t_150){
331− return function(){
332− switch(t_150[0]){
333− case 'RBNode':
334− switch(t_150[5][0]){
335− case 'RBEmpty':
336− return eq(k_142,t_150[2]);
337− }break;
338− }
339− return false;}();}
340− function eq_145(t_152){
341− return function(){
342− switch(t_152[0]){
343− case 'RBNode':
344− return eq(k_142,t_152[2]);
345− }
346− return false;}();}
347− function delLT_146(t_154){
348− return function(){
349− var case216=moveRedLeftIfNeeded_28(t_154);
350− switch(case216[0]){
351− case 'RBEmpty':
352− throw 'delLT on RBEmpty';
353− case 'RBNode':
354− return fixUp_17(RBNode_2(case216[1])(case216[2])(case216[3])(del_149(case216[4]))(case216[5]));
355− }
356− throw new Error("Non-exhaustive pattern match in case");}();}
357− function delEQ_147(t_160){
358− return function(){
359− switch(t_160[0]){
360− case 'RBEmpty':
361− throw 'delEQ called on a RBEmpty';
362− case 'RBNode':
363− return function(){
364− var Tuple2$k_v__164=min_6(t_160[5]);
365− var k__165=function(){
366− switch(Tuple2$k_v__164[0]){
367− case 'Tuple2':
368− return Tuple2$k_v__164[1];
369− }
370− throw new Error("Non-exhaustive pattern match in case");}();
371− var v__166=function(){
372− switch(Tuple2$k_v__164[0]){
373− case 'Tuple2':
374− return Tuple2$k_v__164[2];
375− }
376− throw new Error("Non-exhaustive pattern match in case");}();
377− return fixUp_17(RBNode_2(t_160[1])(k__165)(v__166)(t_160[4])(deleteMin_30(t_160[5])));}();
378− }
379− throw new Error("Non-exhaustive pattern match in case");}();}
380− function delGT_148(t_171){
381− return function(){
382− switch(t_171[0]){
383− case 'RBEmpty':
384− throw 'delGT called on a RBEmpty';
385− case 'RBNode':
386− return fixUp_17(RBNode_2(t_171[1])(t_171[2])(t_171[3])(t_171[4])(del_149(t_171[5])));
387− }
388− throw new Error("Non-exhaustive pattern match in case");}();}
389− function del_149(t_177){
390− return function(){
391− switch(t_177[0]){
392− case 'RBEmpty':
393− return RBEmpty_3;
394− case 'RBNode':
395− return ((compare(k_142)(t_177[2])[0] === 'LT')?delLT_146(t_177):function(){
396− var u_179=(isRedLeft_22(t_177)?rotateRight_11(t_177):t_177);
397− return (eq_and_noRightNode_144(u_179)?u_179[4]:function(){
398− var t__180=moveRedRightIfNeeded_29(t_177);
399− return (eq_145(t__180)?delEQ_147(t__180):delGT_148(t__180));}());}());
400− }
401− throw new Error("Non-exhaustive pattern match in case");}();}
402− return (member_9(k_142)(t_143)?ensureBlackRoot_18(del_149(t_143)):t_143);}();};}
403− function map_32(f_181){
404− return function(t_182){
405− return function(){
406− switch(t_182[0]){
407− case 'RBEmpty':
408− return RBEmpty_3;
409− case 'RBNode':
410− return RBNode_2(t_182[1])(t_182[2])(f_181(t_182[3]))(map_32(f_181)(t_182[4]))(map_32(f_181)(t_182[5]));
411− }
412− throw new Error("Non-exhaustive pattern match in case");}();};}
413− function foldl_33(f_188){
414− return function(acc_189){
415− return function(t_190){
416− return function(){
417− switch(t_190[0]){
418− case 'RBEmpty':
419− return acc_189;
420− case 'RBNode':
421− return foldl_33(f_188)(f_188(t_190[2])(t_190[3])(foldl_33(f_188)(acc_189)(t_190[4])))(t_190[5]);
422− }
423− throw new Error("Non-exhaustive pattern match in case");}();};};}
424− function foldr_34(f_195){
425− return function(acc_196){
426− return function(t_197){
427− return function(){
428− switch(t_197[0]){
429− case 'RBEmpty':
430− return acc_196;
431− case 'RBNode':
432− return foldr_34(f_195)(f_195(t_197[2])(t_197[3])(foldr_34(f_195)(acc_196)(t_197[5])))(t_197[4]);
433− }
434− throw new Error("Non-exhaustive pattern match in case");}();};};}
435− function union_35(t1_202){
436− return function(t2_203){
437− return foldl_33(insert_19)(t2_203)(t1_202);};}
438− function intersect_36(t1_204){
439− return function(t2_205){
440− return foldl_33(function(k_206){
441− return function(v_207){
442− return function(t_208){
443− return (member_9(k_206)(t2_205)?insert_19(k_206)(v_207)(t_208):t_208);};};})(empty_4)(t1_204);};}
444− function diff_37(t1_209){
445− return function(t2_210){
446− return foldl_33(function(k_211){
447− return function(v_212){
448− return function(t_213){
449− return remove_31(k_211)(t_213);};};})(t1_209)(t2_210);};}
450− function keys_38(t_214){
451− return foldr_34(function(k_215){
452− return function(v_216){
453− return function(acc_217){
454− return ['Cons',k_215,acc_217];};};})(['Nil'])(t_214);}
455− function values_39(t_218){
456− return foldr_34(function(k_219){
457− return function(v_220){
458− return function(acc_221){
459− return ['Cons',v_220,acc_221];};};})(['Nil'])(t_218);}
460− function toList_40(t_222){
461− return foldr_34(function(k_223){
462− return function(v_224){
463− return function(acc_225){
464− return ['Cons',['Tuple2',k_223,v_224],acc_225];};};})(['Nil'])(t_222);}
465− function fromList_41(assocs_226){
466− return Elm.List.foldl(uncurry(insert_19))(empty_4)(assocs_226);}
467− var empty_4=RBEmpty_3;
468− return {$op : {},
469− empty:empty_4,
470− lookup:lookup_7,
471− findWithDefault:findWithDefault_8,
472− member:member_9,
473− insert:insert_19,
474− singleton:singleton_20,
475− remove:remove_31,
476− map:map_32,
477− foldl:foldl_33,
478− foldr:foldr_34,
479− union:union_35,
480− intersect:intersect_36,
481− diff:diff_37,
482− keys:keys_38,
483− values:values_39,
484− toList:toList_40,
485− fromList:fromList_41};}();
core-js/Either.jsdeleted−75
@@ -1,75 +0,0 @@
1−/*! Either
2−!*/
3−
4−
5−Elm.Either = function() {
6− /*[Definition]*/
7−
8− /** data Either a b = Left a | Right b
9− Represents any data that can take two different types.
10−
11− This can also be used for error handling (`Either String a`) where
12− error messages are stored on the left, and the correct values
13− ("right" values) are stored on the right.
14− **/
15− function Left(a1) { return ['Left',a1]; }
16− function Right(a1){ return ['Right',a1]; }
17−
18− /*[Basics]*/
19−
20− /** either : (a -> c) -> (b -> c) -> Either a b -> c
21− Apply the first function to a `Left` and the second function to a `Right`.
22− This allows the extraction of a value from an `Either`.
23− **/
24− function either(f){ return function(g){ return function(e){
25− switch(e[0]){
26− case 'Left': return f(e[1]);
27− case 'Right': return g(e[1]);
28− }
29− };};}
30−
31− /** isLeft : Either a b -> Bool
32− True if the value is a `Left`.
33− **/
34− function isLeft(e) { return e[0] == 'Left'; }
35−
36− /** isRight : Either a b -> Bool
37− True if the value is a `Right`.
38− **/
39− function isRight(e) { return e[0] == 'Right'; }
40−
41− /*[With Lists]*/
42−
43− function get(es) { return Elm.List.map(function(x){return x[1];})(es); }
44−
45− /** lefts : [Either a b] -> [a]
46− Keep only the values held in `Left` values.
47− **/
48− function lefts(es) { return get(Elm.List.filter(isLeft)(es)); }
49−
50− /** rights : [Either a b] -> [a]
51− Keep only the values held in `Right` values.
52− **/
53− function rights(es) { return get(Elm.List.filter(isRight)(es)); }
54−
55− /** partition : [Either a b] -> ([a],[b])
56− Split into two lists, lefts on the left and rights on the right.
57− So we have the equivalence:
58−
59− partition es == (lefts es, rights es)
60− **/
61− function partition(es) {
62− var lrs = Elm.List.partition(isLeft)(es);
63− lrs[1] = get(lrs[1]);
64− lrs[2] = get(lrs[2]);
65− return lrs;
66− }
67− return {Left:Left,
68− Right:Right,
69− either:either,
70− isLeft:isLeft,
71− isRight:isRight,
72− lefts:lefts,
73− rights:rights,
74− partition:partition};
75−}();
core-js/Graphics/Collage.jsdeleted−317
@@ -1,317 +0,0 @@
1−
2−var Collage = function() {
3−
4−var JS = Elm.JavaScript;
5−
6−function tracePoints(ctx,points) {
7− var i = points.length - 1;
8− if (i <= 0) return;
9− ctx.moveTo(points[i][1], points[i][2]);
10− while (i--) { ctx.lineTo(points[i][1], points[i][2]); }
11−}
12−
13−function solid(ctx,color,points) {
14− tracePoints(ctx,points);
15− ctx.strokeStyle = Elm.Color.extract(color);
16− ctx.stroke();
17−};
18−
19−function filled(ctx,color,points) {
20− tracePoints(ctx,points);
21− ctx.fillStyle = Elm.Color.extract(color);
22− ctx.fill();
23−}
24−
25−function textured(redo,ctx,src,points) {
26− var img = new Image();
27− img.src = JS.castStringToJSString(src);
28− img.onload = redo;
29−
30− tracePoints(ctx,points);
31− ctx.fillStyle = ctx.createPattern(img,'repeat');
32− ctx.fill();
33−}
34−
35−function customLine(pattern,ctx,color,points) {
36− if (pattern.length === 0) { pattern = [8,4]; }
37− customLineHelp(ctx, pattern, points);
38− ctx.strokeStyle = Elm.Color.extract(color);
39− ctx.stroke();
40−};
41−
42−var customLineHelp = function(ctx, pattern, points) {
43− var i = points.length - 1;
44− if (i <= 0) return;
45− var x0 = points[i][1], y0 = points[i][2];
46− var x1=0, y1=0, dx=0, dy=0, remaining=0, nx=0, ny=0;
47− var pindex = 0, plen = pattern.length;
48− var draw = true, segmentLength = pattern[0];
49− ctx.moveTo(x0,y0);
50− while (i--) {
51− x1 = points[i][1]; y1 = points[i][2];
52− dx = x1 - x0; dy = y1 - y0;
53− remaining = Math.sqrt(dx * dx + dy * dy);
54− while (segmentLength <= remaining) {
55− x0 += dx * segmentLength / remaining;
56− y0 += dy * segmentLength / remaining;
57− ctx[draw ? 'lineTo' : 'moveTo'](x0, y0);
58− // update starting position
59− dx = x1 - x0; dy = y1 - y0;
60− remaining = Math.sqrt(dx * dx + dy * dy);
61− // update pattern
62− draw = !draw;
63− pindex = (pindex + 1) % plen;
64− segmentLength = pattern[pindex];
65− }
66− if (remaining > 0) {
67− ctx[draw ? 'lineTo' : 'moveTo'](x1, y1);
68− segmentLength -= remaining;
69− }
70− x0 = x1; y0 = y1;
71− }
72−};
73−
74−function drawLine(ctx,form) {
75− var points = form[3][1];
76− switch(form[1][0]) {
77− case "Solid" : return solid(ctx,form[2],points);
78− case "Dotted": return customLine([3,3],ctx,form[2],points);
79− case "Dashed": return customLine([8,4],ctx,form[2],points);
80− case "Custom": return customLine(form[1][1],ctx,form[2],points);
81− }
82−};
83−
84−function drawShape(redo,ctx,shapeStyle,color,points) {
85− switch(shapeStyle[0]) {
86− case "Filled": return filled(ctx,color,points);
87− case "Outlined": return solid(ctx,color,points);
88− case "Textured": return textured(redo,ctx,shapeStyle[1],points);
89− case "CustomOutline":
90− return customLine(shapeStyle[1],ctx,color,points);
91− }
92−};
93−
94−function drawImage(redo,ctx,w,h,src) {
95− var img = new Image();
96− img.onload = redo;
97− img.src = JS.castStringToJSString(src);
98− ctx.drawImage(img,-w/2,-h/2,w,h);
99−}
100−
101−function renderForm(redo,ctx,theta,scale,x,y,form) {
102− ctx.save();
103− if (x !== 0 || y !== 0) ctx.translate(x,y);
104− if (theta !== ~~theta) ctx.rotate(2*Math.PI*theta);
105− if (scale !== 1) ctx.scale(scale,scale);
106− ctx.beginPath();
107− switch(form[0]) {
108− case "FLine": drawLine(ctx,form); break;
109− case "FShape": drawShape(redo,ctx,form[1],form[2],form[3][1]); break;
110− case "FImage": drawImage(redo,ctx,form[1],form[2],form[3]); break;
111− }
112− ctx.restore();
113−};
114−
115−function renderForms(redo,ctx,w,h,forms) {
116− ctx.clearRect(0,0,w,h);
117− for (var i = forms.length; i--; ) {
118− var f = forms[i];
119− renderForm(redo,ctx,f[1],f[2],f[3][1],f[3][2],f[4]);
120− }
121−}
122−
123−function collageForms(w,h,forms) {
124− var canvas = Render.newElement('canvas');
125− w = ~~w;
126− h = ~~h;
127− canvas.style.width = w + 'px';
128− canvas.style.height = h + 'px';
129− canvas.style.display = "block";
130− canvas.width = w;
131− canvas.height = h;
132− if (canvas.getContext) {
133− var ctx = canvas.getContext('2d');
134− function redo() { renderForms(this,ctx,w,h,forms); }
135− renderForms(redo,ctx,w,h,forms);
136− return canvas;
137− }
138− canvas.innerHTML = "Your browser does not support the canvas element.";
139− return canvas;
140−};
141−
142−function applyTransforms(theta,scale,x,y,w,h,e) {
143− var t = "translate(" + (x - w / 2) + "px,"+ (y - h / 2) + "px)";
144− var r = theta === (~~theta) ? "" : "rotate(" + theta*360 + "deg)";
145− var s = scale === 1 ? "" : "scale(" + scale + "," + scale + ")";
146− var transforms = t + " " + s + " " + r;
147− e.style.transform = transforms;
148− e.style.msTransform = transforms;
149− e.style.MozTransform = transforms;
150− e.style.webkitTransform = transforms;
151− e.style.OTransform = transforms;
152−}
153−
154−function collageElement(w,h,theta,scale,x,y,elem) {
155− var e = Render.render(elem);
156− applyTransforms(theta,scale,x,y,elem[3],elem[4],e);
157− var div = Render.newElement('div');
158− Render.addTo(div,e);
159− div.style.width = (~~w) + "px";
160− div.style.height = (~~h) + "px";
161− div.style.overflow = "hidden";
162− return div;
163−}
164−
165−function collage(w,h,formss) {
166− if (formss.length === 0) { return collageForms(w,h,[]); }
167− var elems = new Array(formss.length);
168− for (var i = formss.length; i--; ) {
169− var f = formss[i];
170− if (typeof f[0] === "string") {
171− elems[i] = collageElement(w,h,f[1],f[2],f[3][1],f[3][2],f[4][1]);
172− } else {
173− elems[i] = collageForms(w,h,f);
174− }
175− }
176− if (formss.length === 1) { return elems[0]; }
177− return Render.flowWith(Render.goIn,function(x){return x},elems);
178−}
179−
180−function updateFormSet(node,currSet,nextSet) {
181− if (Value.eq(nextSet,currSet)) return;
182− var w = node.style.width.slice(0,-2) - 0;
183− var h = node.style.height.slice(0,-2) - 0;
184− if (typeof nextSet[0] === "object") {
185− if (typeof currSet[0] === "object") {
186− if (node.getContext) {
187− var ctx = node.getContext('2d');
188− function redo() { renderForms(this,ctx,w,h,nextSet); }
189− return renderForms(redo,ctx,w,h,nextSet);
190− }
191− }
192− var newNode = collageForms(w,h,nextSet);
193− newNode.style.position = 'absolute';
194− return node.parentNode.replaceChild(newNode,node);
195− }
196− node.style.width = (~~w) + "px";
197− node.style.height = (~~h) + "px";
198− var f = nextSet;
199− var next = nextSet[4][1];
200− Render.update(node.firstChild, currSet[4][1], next);
201− applyTransforms(f[1],f[2],f[3][1],f[3][2],next[3],next[4],node.firstChild);
202−}
203−
204−// assumes that the form sets are the same length.
205−function updateCollage(node,currs,nexts) {
206− if (nexts.length === 1) {
207− return updateFormSet(node,currs[0],nexts[0]);
208− }
209− var kids = node.childNodes;
210− var len = kids.length;
211− for (var i = len; i--; ) {
212− updateFormSet(kids[len-i-1], currs[i], nexts[i]);
213− }
214−}
215−
216−function style(clr,n,list) {
217− return ["Tuple2",
218− '<span style="font-size:100%;color:' + clr + ';">' + n + '</span>',
219− list];
220−}
221−
222−function insideForm(point) { return function(form) {
223− if (!inBoundsOf(point[1],point[2],form)) return false;
224− var hw, hh;
225− switch (form[4][0]) {
226− case "FShape": return insideShape(point,form[1],form[2],form[3],form[4][3][1]);
227− case "FLine": return false;
228− case "FImage":
229− hw = form[4][1] / 2;
230− hh = form[4][2] / 2;
231− break;
232− case "FElement":
233− hw = form[4][1][3] / 2;
234− hh = form[4][1][4] / 2;
235− break;
236− }
237− return insideShape(point,form[1],form[2],form[3],
238− [ [null, hw, hh],
239− [null,-hw, hh],
240− [null,-hw,-hh],
241− [null, hw,-hh],
242− [null, hw, hh] ]);
243− };
244−}
245−
246−function inBoundsOf(px,py,form) {
247− if (form.length < 6) {
248− var fx = form[3][1], fy = form[3][2];
249− var radiusSquared = 0;
250− var scale = form[2];
251− switch (form[4][0]) {
252− case "FShape":
253− var points = form[4][3][1];
254− for (var i = points.length; --i; ) {
255− var p = points[i];
256− radiusSquared = Math.max(radiusSquared, p[1]*p[1] + p[2]*p[2]);
257− }
258− radiusSquared *= scale * scale;
259− break;
260− case "FLine":
261− break;
262− case "FImage":
263− var x = scale * form[4][1] / 2;
264− var y = scale * form[4][2] / 2;
265− radiusSquared = x*x + y*y;
266− break;
267− case "FElement":
268− var x = scale * form[4][1][3] / 2;
269− var y = scale * form[4][1][4] / 2;
270− radiusSquared = x*x + y*y;
271− break;
272− }
273− form.push(function(px,py) {
274− var dx = px - fx;
275− var dy = py - fy;
276− return dx*dx + dy*dy < radiusSquared + 1;
277− });
278− }
279− return form[5](px,py);
280−}
281−
282−function insideShape(point,theta,scale,pos,points) {
283− var counter = 0;
284− var list = ["Nil"];
285− var p1,p2;
286−
287− var x = (point[1] - pos[1]) / scale;
288− var y = (point[2] - pos[2]) / scale;
289− if (theta !== 0) {
290− var t = -2 * Math.PI * theta;
291− var nx = x * Math.cos(t) - y * Math.sin(t);
292− y = x * Math.sin(t) + y * Math.cos(t);
293− x = nx;
294− }
295−
296− if (points.length === 0) { return false; }
297− p1 = points[0];
298− for (var i = points.length - 1; i--; ) {
299− p2 = points[i];
300− var p1x = p1[1], p1y = p1[2], p2x = p2[1], p2y = p2[2];
301−
302− if (p1y < p2y) {var ymin=p1y, ymax=p2y;} else {var ymin=p2y, ymax=p1y;}
303− if (p1x < p2x) {var xmin=p1x, xmax=p2x;} else {var xmin=p2x, xmax=p1x;}
304−
305− if (ymin < y && y <= ymax && x <= xmax) {
306− if (x <= xmin || x <= ((y-p1y)*(p2x-p1x)/(p2y-p1y)+p1x)) {
307− ++counter;
308− }
309− }
310− p1 = p2;
311− }
312− return (counter % 2) === 1;
313−}
314−
315−return {collage:collage, updateCollage:updateCollage, insideForm:insideForm};
316−
317−}();
core-js/Graphics/Color.jsdeleted−86
@@ -1,86 +0,0 @@
1−Elm.Color = function() {
2−
3−function Color_0(a1) {
4− return function(a2) {
5− return function(a3) {
6− return function(a4) {
7− return["Color", a1, a2, a3, a4]
8− }
9− }
10− }
11−}
12−var rgba_1 = Color_0;
13−var red_3 = ["Color",255,0,0,1];
14−var green_4 = ["Color",0,255,0,1];
15−var blue_5 = ["Color",0,0,255,1];
16−var yellow_6 = ["Color",255,255,0,1];
17−var cyan_7 = ["Color",0,255,255,1];
18−var magenta_8 = ["Color",255,0,255,1];
19−var black_9 = ["Color",0,0,0,1];
20−var white_10 = ["Color",255,255,255,1];
21−var gray_11 = ["Color",128,128,128,1];
22−var grey_12 = ["Color",128,128,128,1];
23−function rgb_2(r_13) {
24− return function(g_14) {
25− return function(b_15) {
26− return ["Color",r_13,g_14,b_15,1]
27− }
28− }
29−}
30−function extract(c) {
31− if (c[4] === 1) { return 'rgb(' + c[1] + ',' + c[2] + ',' + c[3] + ')'; }
32− return 'rgba(' + c[1] + ',' + c[2] + ',' + c[3] + ',' + c[4] + ')';
33−}
34−function complement(rgb) {
35− var hsv = toHSV(rgb);
36− hsv.hue = (hsv.hue + 180) % 360;
37− return toRGB(hsv);
38−}
39−
40−function hsva(h) { return function(s) { return function(v) { return function(a) {
41− var clr = toRGB({hue:h, saturation:s, value:v});
42− clr[4] = a;
43− return clr;
44− }; }; };
45−}
46−
47−function hsv(h) { return function(s) { return function(v) {
48− return toRGB({hue:h, saturation:s, value:v}); }; }; }
49−
50−function toHSV(rgb) {
51− var hsv = {};
52− var r = rgb[1] / 255.0, g = rgb[2] / 255.0, b = rgb[3] / 255.0;
53− var M = Math.max(r,g,b);
54− var m = Math.min(r,g,b);
55− var c = M - m;
56−
57− var h = 0;
58− if (c === 0) { h = 0; }
59− else if (M === r) { h = ((g - b) / c) % 6; }
60− else if (M === g) { h = ((b - r) / c) + 2; }
61− else if (M === b) { h = ((r - g) / c) + 4; }
62− h *= 60;
63−
64− return { value : M, hue : h, saturation : (M === 0 ? 0 : c / M) };
65−}
66−
67−function between(lo,hi,x) { return lo <= x && x < hi; }
68−function norm(n) { return Math.round(n*255); }
69−
70−function toRGB(hsv) {
71− var c = hsv.value * hsv.saturation;
72− var hue = hsv.hue / 60;
73− var x = c * (1 - Math.abs((hue % 2) - 1));
74− var r = 0, g = 0, b = 0;
75− if (between(0,1,hue)) { r = c; g = x; b = 0; }
76− else if (between(1,2,hue)) { r = x; g = c; b = 0; }
77− else if (between(2,3,hue)) { r = 0; g = c; b = x; }
78− else if (between(3,4,hue)) { r = 0; g = x; b = c; }
79− else if (between(4,5,hue)) { r = x; g = 0; b = c; }
80− else if (between(5,6,hue)) { r = c; g = 0; b = x; }
81−
82− var m = hsv.value - c;
83− return ["Color", norm(r+m), norm(g+m), norm(b+m), 1 ];
84−}
85− return{rgba:rgba_1, rgb:rgb_2, hsva:hsva, hsv:hsv, red:red_3, green:green_4, blue:blue_5, yellow:yellow_6, cyan:cyan_7, magenta:magenta_8, black:black_9, white:white_10, gray:gray_11, grey:grey_12,complement:complement,extract:extract}
86−}();
core-js/Graphics/Element.jsdeleted−517
@@ -1,517 +0,0 @@
1−Elm.Graphics = function() {
2− for (this['i'] in Elm.List) {
3− eval('var ' + this['i'] + ' = Elm.List[this.i];');
4− }
5− var JS = Elm.JavaScript;
6− var DLeft_0 = ["DLeft"];
7− var DRight_1 = ["DRight"];
8− var DUp_2 = ["DUp"];
9− var DDown_3 = ["DDown"];
10− var DIn_4 = ["DIn"];
11− var DOut_5 = ["DOut"];
12− function Absolute_12(a1) {
13− return["Absolute", a1]
14− }
15− function Relative_13(a1) {
16− return["Relative", a1]
17− }
18− var Near_14 = ["Near"];
19− var Mid_15 = ["Mid"];
20− var Far_16 = ["Far"];
21− function Position_17(a1) {
22− return function(a2) {
23− return["Position", a1, a2]
24− }
25− }
26− function PositionTL_18(a1) {
27− return function(a2) {
28− return["PositionTL", a1, a2]
29− }
30− }
31− function PositionTR_19(a1) {
32− return function(a2) {
33− return["PositionTR", a1, a2]
34− }
35− }
36− function PositionBL_20(a1) {
37− return function(a2) {
38− return["PositionBL", a1, a2]
39− }
40− }
41− function PositionBR_21(a1) {
42− return function(a2) {
43− return["PositionBR", a1, a2]
44− }
45− }
46− function Element_37(id,e,w,h,o,c,l) {
47− return["Element", id, e, w, h, o, c, l ]
48− }
49− function EText_39(a1) {
50− return function(a2) {
51− return["EText", a1, a2]
52− }
53− }
54− function EImage_40(a1) {
55− return["EImage", JS.castStringToJSString(a1)]
56− }
57− function EVideo_41(a1) {
58− return["EVideo", JS.castStringToJSString(a1)]
59− }
60− function EFittedImage_42(a1) {
61− return["EFittedImage", JS.castStringToJSString(a1)]
62− }
63− function EFlow_43(a1) {
64− return function(a2) {
65− return["EFlow", a1, JS.castListToJSArray(a2)]
66− }
67− }
68− function ECollage_44(a1) {
69− return function(a2) {
70− return function(a3) {
71− return["ECollage", a1, a2, Value.groupForms(a3)]
72− }
73− }
74− }
75− var EEmpty_45 = ["EEmpty"];
76− function EContainer_46(a1) {
77− return function(a2) {
78− return["EContainer", a1, a2]
79− }
80− }
81− var Solid_68 = ["Solid"];
82− var Dotted_69 = ["Dotted"];
83− var Dashed_70 = ["Dashed"];
84− function Custom_71(a1) {
85− return["Custom", JS.castListToJSArray(a1)]
86− }
87− var Filled_72 = ["Filled"];
88− var Outlined_73 = ["Outlined"];
89− function CustomOutline_74(a1) {
90− return["CustomOutline", JS.castListToJSArray(a1)]
91− }
92− function Line_75(a1) {
93− return["Line", JS.castListToJSArray(a1)]
94− }
95− function Shape_78(a1) {
96− return function(a2) {
97− var points = JS.castListToJSArray(a1);
98− if (points.length > 0) { points.push(points[0]); }
99− return["Shape", points, a2];
100− }
101− }
102− function Form_84(a1) {
103− return function(a2) {
104− return function(a3) {
105− return function(a4) {
106− return["Form", a1, a2, a3, a4]
107− }
108− }
109− }
110− }
111− function FLine_85(a1) {
112− return function(a2) {
113− return function(a3) {
114− return["FLine", a1, a2, a3]
115− }
116− }
117− }
118− function FShape_86(a1) {
119− return function(a2) {
120− return function(a3) {
121− return["FShape", a1, a2, a3]
122− }
123− }
124− }
125− function FImage_87(a1) {
126− return function(a2) {
127− return function(a3) {
128− return["FImage", a1, a2, JS.castStringToJSString(a3)]
129− }
130− }
131− }
132− function FElement_88(a1) {
133− return["FElement", a1]
134− }
135− var left_6 = DLeft_0;
136− var right_7 = DRight_1;
137− var down_8 = DDown_3;
138− var up_9 = DUp_2;
139− var inward_10 = DIn_4;
140− var outward_11 = DOut_5;
141− var topLeft_22 = Position_17(Near_14)(Near_14);
142− var topRight_23 = Position_17(Far_16)(Near_14);
143− var bottomLeft_24 = Position_17(Near_14)(Far_16);
144− var bottomRight_25 = Position_17(Far_16)(Far_16);
145− var midLeft_26 = Position_17(Near_14)(Mid_15);
146− var midRight_27 = Position_17(Far_16)(Mid_15);
147− var midTop_28 = Position_17(Mid_15)(Near_14);
148− var midBottom_29 = Position_17(Mid_15)(Far_16);
149− var middle_30 = Position_17(Mid_15)(Mid_15);
150− function middleAt(a1) {
151− return function(a2) {
152− return["PositionAt", a1, a2]
153− }
154− }
155− var topLeftAt_31 = PositionTL_18;
156− var topRightAt_32 = PositionTR_19;
157− var bottomLeftAt_33 = PositionBL_20;
158− var bottomRightAt_34 = PositionBR_21;
159− var absolute_35 = Absolute_12;
160− var relative_36 = Relative_13;
161− function newElement_38(e,w,h,o,c,l) { return Element_37(Guid.guid(),e,w,h,o,c,l); }
162− function basicNewElement(e,w,h) { return Element_37(Guid.guid(),e,w,h,1,["Nothing"],["Nothing"]); }
163− var line_76 = Line_75;
164− var polygon_79 = Shape_78;
165− function sprite_96(src) {
166− return function(w) {
167− return function(h) {
168− return function(pos) {
169− return Form_84(0)(1)(pos)(FImage_87(w)(h)(src))
170− }
171− }
172− }
173− }
174− function toForm_97(pos) {
175− return function(e) {
176− return Form_84(0)(1)(pos)(FElement_88(e))
177− }
178− }
179− function width_47(w__101) {
180− return function(e) {
181− var be = e[2];
182− switch(be[0]) {
183− case "EImage":
184− case "EVideo":
185− return newElement_38(e[2],w__101,e[4] * w__101 / e[3], e[5], e[6], e[7]);
186− case "EText":
187− var p = Value.getTextSize(w__101,e[4],be[2]);
188− return newElement_38(e[2], w__101, p[1], e[5], e[6], e[7]);
189− }
190− return newElement_38(e[2], w__101, e[4], e[5], e[6], e[7]);
191− }
192− }
193− function height_48(h__108) {
194− return function(e) {
195− var be = e[2];
196− switch(be[0]) {
197− case "EImage":
198− case "EVideo":
199− return newElement_38(e[2], e[3] * h__108 / e[4], h__108, e[5], e[6], e[7]);
200− }
201− return newElement_38(e[2], e[3], h__108, e[5], e[6], e[7]);
202− }
203− }
204− function size_49(w) {
205− return function(h) {
206− return function(e) {
207− return newElement_38(e[2], w, h, e[5], e[6], e[7]);
208− }
209− }
210− }
211− function opacity_50(o) {
212− return function(e) {
213− return newElement_38(e[2], e[3], e[4], o, e[6], e[7]);
214− }
215− }
216− function color_51(c) {
217− return function(e) {
218− return newElement_38(e[2], e[3], e[4], e[5], ["Just",c], e[7]);
219− }
220− }
221− function link(lnk) {
222− return function(e) {
223− return newElement_38(e[2], e[3], e[4], e[5], e[6], ["Just", JS.castStringToJSString(lnk)]);
224− }
225− }
226− function widthOf_52(e) { return ~~e[3]; }
227− function heightOf_53(e) { return ~~e[4]; }
228− function sizeOf_54(e) { return["Tuple2", ~~e[3], ~~e[4]] }
229− function text_56(txt) {
230− var p = Value.getTextSize(0,0,txt);
231− return basicNewElement(EText_39("left")(txt), p[0], p[1])
232− }
233− function plainText(str) {
234− var txt = Value.toText(str);
235− var p = Value.getTextSize(0,0,txt);
236− return basicNewElement(EText_39("left")(txt),p[0],p[1])
237− }
238− function asText(v) {
239− var txt = Elm.Text.monospace(Value.toText(Value.show(v)));
240− var p = Value.getTextSize(0,0,txt);
241− return basicNewElement(EText_39("left")(txt),p[0],p[1])
242− }
243− function centeredText(txt) {
244− var p = Value.getTextSize(0,0,txt);
245− return basicNewElement(EText_39("center")(txt),p[0],p[1])
246− }
247− function justifiedText(txt) {
248− var p = Value.getTextSize(0,0,txt);
249− return basicNewElement(EText_39("justify")(txt),p[0],p[1])
250− }
251− function rightedText(txt) {
252− var p = Value.getTextSize(0,0,txt);
253− return basicNewElement(EText_39("right")(txt),p[0],p[1])
254− }
255− function image_57(w) {
256− return function(h) {
257− return function(src) {
258− return basicNewElement(EImage_40(src),w,h)
259− }
260− }
261− }
262− function images(srcs) {
263− var pics = Elm.Signal.constant(spacer_66(0)(0));
264− var update = Elm.Signal.lift(function(src) {
265− src = JS.castStringToJSString(src);
266− var img = new Image();
267− img.onload = function() {
268− Dispatcher.notify(pics.id,
269− image_57(this.width)(this.height)(src));
270− };
271− img.src = src;
272− })(srcs);
273− function f(x) { return function(y) { return x; } }
274− var combine = Elm.Signal.lift2(f)(pics)(update);
275− return combine;
276− }
277− function video_58(w) {
278− return function(h) {
279− return function(src) {
280− return basicNewElement(EVideo_41(src),w,h)
281− }
282− }
283− }
284− function fittedImage_59(w_147) {
285− return function(h_148) {
286− return function(s_149) {
287− return basicNewElement(EFittedImage_42(s_149),w_147,h_148)
288− }
289− }
290− }
291− function flow_60(dir_150) {
292− return function(es_151) {
293− return function() {
294− var w_152 = function() {
295− var ws_154 = map(widthOf_52)(es_151);
296− return function(case1) {
297− var case0 = case1;
298− switch(case0[0]) {
299− case "DLeft":
300− return sum(ws_154);
301− case "DRight":
302− return sum(ws_154)
303− }
304− return maximum(ws_154)
305− }(dir_150)
306− }();
307− var h_153 = function() {
308− var hs_155 = map(heightOf_53)(es_151);
309− return function(case3) {
310− var case2 = case3;
311− switch(case2[0]) {
312− case "DDown":
313− return sum(hs_155);
314− case "DUp":
315− return sum(hs_155)
316− }
317− return maximum(hs_155)
318− }(dir_150)
319− }();
320− return basicNewElement(EFlow_43(dir_150)(es_151), w_152, h_153)
321− }()
322− }
323− }
324− function above_61(e1_156) {
325− return function(e2_157) {
326− return basicNewElement(EFlow_43(DDown_3)(["Cons", e1_156, ["Cons", e2_157, ["Nil"]]]), Math.max(widthOf_52(e1_156),widthOf_52(e2_157)), heightOf_53(e1_156) + heightOf_53(e2_157));
327− }
328− }
329− function below_62(e1_158) {
330− return function(e2_159) {
331− return basicNewElement(EFlow_43(DDown_3)(["Cons", e2_159, ["Cons", e1_158, ["Nil"]]]), Math.max(widthOf_52(e1_158),widthOf_52(e2_159)), heightOf_53(e1_158) + heightOf_53(e2_159));
332− }
333− }
334− function beside_63(e1_160) {
335− return function(e2_161) {
336− return basicNewElement(EFlow_43(DRight_1)(["Cons", e1_160, ["Cons", e2_161, ["Nil"]]]), widthOf_52(e1_160) + widthOf_52(e2_161), Math.max(heightOf_53(e1_160),heightOf_53(e2_161)));
337− }
338− }
339− function layers_64(es_162) {
340− return basicNewElement(EFlow_43(DOut_5)(es_162), maximum(map(widthOf_52)(es_162)), maximum(map(heightOf_53)(es_162)))
341− }
342− function collage_65(w_163) {
343− return function(h_164) {
344− return function(forms_165) {
345− return basicNewElement(ECollage_44(w_163)(h_164)(forms_165),w_163,h_164)
346− }
347− }
348− }
349− function spacer_66(w_166) {
350− return function(h_167) {
351− return basicNewElement(EEmpty_45,w_166,h_167)
352− }
353− }
354− function container_67(w_169) {
355− return function(h_170) {
356− return function(pos_168) {
357− return function(e_171) {
358− return basicNewElement(EContainer_46(pos_168)(e_171),w_169,h_170)
359− }
360− }
361− }
362− }
363− function segment_77(p1_172) {
364− return function(p2_173) {
365− return Line_75(["Cons", p1_172, ["Cons", p2_173, ["Nil"]]])
366− }
367− }
368− function rect_80(w_174) {
369− return function(h_175) {
370− return function(pos_176) {
371− return Shape_78(["Cons", ["Tuple2", 0 - w_174 / 2, 0 - h_175 / 2],
372− ["Cons", ["Tuple2", 0 - w_174 / 2, h_175 / 2],
373− ["Cons", ["Tuple2", w_174 / 2, h_175 / 2],
374− ["Cons", ["Tuple2", w_174 / 2, 0 - h_175 / 2], ["Nil"]]]]])(pos_176)
375− }
376− }
377− }
378− function oval_81(w_177) {
379− return function(h_178) {
380− return function(pos_179) {
381− return function() {
382− var n_180 = 50;
383− return function() {
384− function f_181(i_182) {
385− return["Tuple2", w_177 / 2 * Math.cos(2 * (Math.PI / n_180) * i_182), h_178 / 2 * Math.sin(2 * (Math.PI / n_180) * i_182)];
386− }
387− return Shape_78(map(f_181)(function() {
388− var lo = 0;
389− var hi = n_180 - 1;
390− var lst = ["Nil"];
391− if(lo <= hi) {
392− do {
393− lst = ["Cons", hi, lst]
394− }while(hi-- > lo)
395− }
396− return lst
397− }()))(pos_179)
398− }()
399− }()
400− }
401− }
402− }
403− function circle_82(r_183) {
404− return oval_81(2 * r_183)(2 * r_183)
405− }
406− function ngon_83(n_184) {
407− return function(r_185) {
408− return function(pos_186) {
409− return function() {
410− var m_187 = n_184;
411− return function() {
412− function f_188(i_189) {
413− return["Tuple2", r_185 * Math.cos(2 * (Math.PI / m_187) * i_189), r_185 * Math.sin(2 * (Math.PI / m_187) * i_189)];
414− }
415− return Shape_78(map(f_188)(function() {
416− var lo = 0;
417− var hi = n_184 - 1;
418− var lst = ["Nil"];
419− if(lo <= hi) {
420− do {
421− lst = ["Cons", hi, lst]
422− }while(hi-- > lo)
423− }
424− return lst
425− }()))(pos_186)
426− }()
427− }()
428− }
429− }
430− }
431− function solid_89(clr_190) {
432− return function(ln_191) {
433− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Solid_68)(clr_190)(ln_191))
434− }
435− }
436− function dotted_90(clr_192) {
437− return function(ln_193) {
438− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Dotted_69)(clr_192)(ln_193))
439− }
440− }
441− function dashed_91(clr_194) {
442− return function(ln_195) {
443− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Dashed_70)(clr_194)(ln_195))
444− }
445− }
446− function customLine_92(pattern_196) {
447− return function(clr_197) {
448− return function(ln_198) {
449− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Custom_71(pattern_196))(clr_197)(ln_198))
450− }
451− }
452− }
453− function filled_93(clr) {
454− return function(shape) {
455− return Form_84(0)(1)(shape[2])(FShape_86(Filled_72)(clr)(shape));
456− }
457− }
458− function outlined_94(clr) {
459− return function(shape) {
460− return Form_84(0)(1)(shape[2])(FShape_86(Outlined_73)(clr)(shape));
461− }
462− }
463− function customOutline_95(pattern) {
464− return function(clr) {
465− return function(shape) {
466− return Form_84(0)(1)(shape[2])(FShape_86(CustomOutline_74(pattern))(clr)(shape));
467− }
468− }
469− }
470− function textured(src) {
471− return function(shape) {
472− return Form_84(0)(1)(shape[2])(FShape_86(["Textured",src])(null)(shape));
473− }
474− }
475− function rotate_98(t_212) {
476− return function(Form$thetascaleposform_213) {
477− return function(case5) {
478− var case0 = case5;
479− switch(case0[0]) {
480− case "Form":
481− var case1 = case0[1], case2 = case0[2], case3 = case0[3], case4 = case0[4];
482− return Form_84(t_212 + case1)(case2)(case3)(case4)
483− }
484− throw new Error("Non-exhaustive pattern match in case");
485− }(Form$thetascaleposform_213)
486− }
487− }
488− function scale_99(s) {
489− return function(form) {
490− return Form_84(form[1])(s * form[2])(form[3])(form[4])
491− }
492− }
493− function move_100(x_224) {
494− return function(y_225) {
495− return function(Form$thetascaleTuple2$pxpyform_226) {
496− return function(case7) {
497− var case0 = case7;
498− switch(case0[0]) {
499− case "Form":
500− var case1 = case0[1], case2 = case0[2], case3 = case0[3], case4 = case0[4];
501− switch(case3[0]) {
502− case "Tuple2":
503− var case5 = case3[1], case6 = case3[2];
504− return Form_84(case1)(case2)(["Tuple2", x_224 + case5, y_225 + case6])(case4)
505− }
506− break
507− }
508− throw new Error("Non-exhaustive pattern match in case");
509− }(Form$thetascaleTuple2$pxpyform_226)
510− }
511− }
512− }
513− return{left:left_6, right:right_7, down:down_8, up:up_9, inward:inward_10, outward:outward_11, topLeft:topLeft_22, topRight:topRight_23, bottomLeft:bottomLeft_24, bottomRight:bottomRight_25, midLeft:midLeft_26, midRight:midRight_27, midTop:midTop_28, midBottom:midBottom_29, middle:middle_30, middleAt:middleAt, topLeftAt:topLeftAt_31, topRightAt:topRightAt_32, bottomLeftAt:bottomLeftAt_33, bottomRightAt:bottomRightAt_34, absolute:absolute_35, relative:relative_36, width:width_47, height:height_48, size:size_49, opacity:opacity_50,
514− color:color_51, link:link, widthOf:widthOf_52, heightOf:heightOf_53, sizeOf:sizeOf_54, text:text_56, asText:asText, plainText:plainText, centeredText:centeredText, justifiedText:justifiedText, rightedText:rightedText, image:image_57, images:images, video:video_58, fittedImage:fittedImage_59, flow:flow_60, above:above_61, below:below_62, beside:beside_63, layers:layers_64, collage:collage_65, spacer:spacer_66, container:container_67, line:line_76, segment:segment_77, polygon:polygon_79, rect:rect_80, oval:oval_81, circle:circle_82, ngon:ngon_83, solid:solid_89, dotted:dotted_90, dashed:dashed_91, customLine:customLine_92, filled:filled_93,
515− outlined:outlined_94, customOutline:customOutline_95, textured:textured, sprite:sprite_96, toForm:toForm_97, rotate:rotate_98, scale:scale_99, move:move_100,
516− isWithin: Collage.insideForm}
517−}();
core-js/Graphics/Render.jsdeleted−277
@@ -1,277 +0,0 @@
1−
2−var Render = function(){
3−
4−function newElement(elementType) {
5− var e = document.createElement(elementType);
6− e.style.padding = "0";
7− e.style.margin = "0";
8− return e;
9−};
10−
11−function addTo(container, elem) {
12− container.appendChild(elem);
13−};
14−
15−function makeText(pos,txt) {
16− var e = newElement('div');
17− e.innerHTML = txt;
18− e.style.textAlign = pos;
19− return e;
20−};
21−
22−function image(src) {
23− var img = newElement('img');
24− img.src = src;
25− img.name = src;
26− img.style.display = "block";
27− return img;
28−}
29−
30−function fittedImage(w,h,src) {
31− var e = newElement('div');
32− e.style.width = w + 'px';
33− e.style.height = h + 'px';
34− e.style.position = "relative";
35− e.style.overflow = "hidden";
36−
37− var img = newElement('img');
38− img.onload = function() {
39− img.style.position = 'absolute';
40− img.style.margin = 'auto';
41−
42− var sw = w, sh = h;
43− if (w / h > this.width / this.height) {
44− sh = Math.round(this.height * w / this.width);
45− } else {
46− sw = Math.round(this.width * h / this.height);
47− }
48− img.style.width = sw + 'px';
49− img.style.height = sh + 'px';
50− img.style.left = ((w - sw) / 2) + 'px';
51− img.style.top = ((h - sh) / 2) + 'px';
52− };
53− img.src = src;
54− img.name = src;
55− addTo(e,img);
56− return e;
57−};
58−
59−var video = function(src) {
60− var e = newElement('video');
61− e.controls = "controls";
62− var source = newElement('source');
63− source.src = src;
64− var segs = src.split('.');
65− source.type = "video/" + segs[segs.length-1];
66− addTo(e, source);
67− e.style.display = "block";
68− return e;
69−};
70−
71−function divify(e) {
72− var div = newElement('div');
73− addTo(div, e);
74− return div;
75−};
76−function goDown(e) {
77− return e //.tagName === "DIV" ? e : divify(e);
78−};
79−function goRight(e) {
80− e.style.styleFloat = "left";
81− e.style.cssFloat = "left";
82− return e;
83−};
84−function goIn(e) {
85− e.style.position = 'absolute';
86− return e;
87−};
88−function flowWith(f, prep, elist) {
89− var container = newElement('div');
90− for (var i = elist.length; i--; ) {
91− addTo(container, f(prep(elist[i])));
92− }
93− return container;
94−};
95−
96−function flow(dir,elist) {
97− switch(dir) {
98− case "DDown": elist = elist.slice(0).reverse();
99− case "DUp": return flowWith(goDown,render,elist);
100− case "DRight": elist = elist.slice(0).reverse();
101− case "DLeft": return flowWith(goRight,render,elist);
102− case "DOut": elist = elist.slice(0).reverse();
103− case "DIn": return flowWith(goIn,render,elist);
104− };
105−};
106−
107−function toPos(pos) {
108− switch(pos[0]) {
109− case "Absolute": return pos[1] + "px";
110− case "Relative": return (pos[1] * 100) + "%";
111− }
112−}
113−
114−function setPos(pos,e) {
115− e.style.position = 'absolute';
116− e.style.margin = 'auto';
117− switch(pos[0]) {
118− case "Position":
119− if (pos[1][0] !== "Far") e.style.left = 0;
120− if (pos[1][0] !== "Near") e.style.right = 0;
121− if (pos[2][0] !== "Far") e.style.top = 0;
122− if (pos[2][0] !== "Near") e.style.bottom = 0;
123− break;
124− case "PositionAt":
125− e.style.top = toPos(pos[2]);
126− e.style.left = toPos(pos[1]);
127− var shift = "translate(" + ~~(-e.style.width.slice(0,-2) / 2) + "px," + ~~(-e.style.height.slice(0,-2) / 2) + "px)";
128− e.style.transform = shift;
129− e.style.msTransform = shift;
130− e.style.MozTransform = shift;
131− e.style.webkitTransform = shift;
132− e.style.OTransform = shift;
133− break;
134− default:
135− var p = pos[0].slice(-2);
136− e.style[p[0] === "T" ? 'top' : 'bottom'] = toPos(pos[2]);
137− e.style[p[1] === "L" ? 'left' : 'right'] = toPos(pos[1]);
138− }
139−}
140−
141−function container(pos,elem) {
142− var e = render(elem);
143− setPos(pos,e);
144− var div = newElement('div');
145− div.style.position = "relative";
146− div.style.overflow = "hidden";
147− addTo(div,e);
148− return div;
149−};
150−
151−function render(elem) {
152− var e = {};
153− switch(elem[2][0]) {
154− case "EText": e = makeText(elem[2][1],elem[2][2]); break;
155− case "EImage": e = image(elem[2][1]); break;
156− case "EVideo": e = video(elem[2][1]); break;
157− case "EFittedImage": e = fittedImage(elem[3],elem[4],elem[2][1]); break;
158− case "EFlow": e = flow(elem[2][1][0],elem[2][2]); break;
159− case "ECollage": e = Collage.collage(elem[2][1],elem[2][2],elem[2][3]); break;
160− case "EEmpty": e = newElement('div'); break;
161− case "EContainer": e = container(elem[2][1],elem[2][2]); break;
162− case "EHtml":
163− e = elem[2][1];
164− if (e.type !== 'button') {
165− var p = Value.getExcess(e);
166− elem[3] -= p[0];
167− elem[4] -= p[1];
168− }
169− break;
170− case "EExternalHtml":
171− e = newElement('div');
172− addTo(e, elem[2][1]);
173− break;
174− }
175− e.id = elem[1];
176− e.style.width = (~~elem[3]) + 'px';
177− e.style.height = (~~elem[4]) + 'px';
178− if (elem[5] !== 1) { e.style.opacity = elem[5]; }
179− if (elem[6][0] === "Just") {
180− e.style.backgroundColor = Elm.Color.extract(elem[6][1]);
181− }
182− if (elem[7][0] === "Just") {
183− var a = newElement('a');
184− a.href = elem[7][1];
185− addTo(a,e);
186− return a;
187− }
188− return e;
189−};
190−
191−function update(node,curr,next) {
192− if (node.tagName === 'A') { node = node.firstChild; }
193− if (curr[1] === next[1]) return;
194− if (curr[2][0] !== next[2][0]) {
195− return node.parentNode.replaceChild(render(next),node);
196− }
197− var nextE = next[2], currE = curr[2];
198− switch(nextE[0]) {
199− case "EText":
200− if (nextE[1] !== currE[1]) node.style.textAlign = nextE[1];
201− if (nextE[2] !== currE[2]) node.innerHTML = nextE[2];
202− break;
203− case "EImage":
204− if (nextE[1] !== currE[1]) node.src = nextE[1];
205− break;
206− case "EVideo":
207− case "EFittedImage":
208− if (!Value.eq(nextE,currE) || next[3]!==curr[3] || next[4]!==curr[4]) {
209− return node.parentNode.replaceChild(render(next),node);
210− }
211− break;
212− case "ECollage":
213− if (nextE[1] !== currE[1] || nextE[2] !== currE[2] || nextE[3].length !== currE[3].length) {
214− return node.parentNode.replaceChild(render(next),node);
215− }
216− Collage.updateCollage(node,currE[3],nextE[3]);
217− break;
218− case "EFlow":
219− if (nextE[1] !== currE[1]) {
220− return node.parentNode.replaceChild(render(next),node);
221− }
222− var nexts = nextE[2];
223− var kids = node.childNodes;
224− if (nexts.length !== kids.length) {
225− return node.parentNode.replaceChild(render(next),node);
226− }
227− var currs = currE[2];
228− var goDir = function(x) { return x; };
229− switch(nextE[1][0]) {
230− case "DDown": case "DUp": goDir = goDown; break;
231− case "DRight": case "DLeft": goDir = goRight; break;
232− case "DOut": case "DIn": goDir = goIn; break;
233− }
234− for (var i = kids.length; i-- ;) {
235− update(kids[i],currs[i],nexts[i]);
236− goDir(kids[i]);
237− }
238− break;
239− case "EContainer":
240− update(node.childNodes[0],currE[2],nextE[2]);
241− setPos(nextE[1],node.childNodes[0]);
242− break;
243− case "EEmpty":
244− break;
245− case "EHtml":
246− if (next[1] !== curr[1]) {
247− var e = render(next);
248− node.parentNode.replaceChild(e,node);
249− node = e;
250− }
251− if (e.type !== 'button') {
252− var p = Value.getExcess(node);
253− next[3] -= p[0];
254− next[4] -= p[1];
255− }
256− break;
257− case "EExternalHtml":
258− if (next[1] !== curr[1])
259− node.parentNode.replaceChild(render(next),node);
260− break;
261− }
262− if (next[3] !== curr[3]) node.style.width = (~~next[3]) + 'px';
263− if (next[4] !== curr[4]) node.style.height = (~~next[4]) + 'px';
264− if (next[5] !== curr[5]) node.style.opacity = next[5];
265− if (next[6].length === 2) {
266− var clr = Elm.Color.extract(next[6][1]);
267− if (clr !== node.style.backgroundColor) node.style.backgroundColor = clr;
268− }
269− if (next[7].length === 2) {
270− if (curr[7].length === 1 || next[7][1] !== curr[7][1]) node.parentNode.href = next[7][1];
271− }
272− next[1] = curr[1];
273−}
274−
275−return {render:render,update:update,addTo:addTo,newElement:newElement,flowWith:flowWith,goIn:goIn};
276−
277−}();
core-js/Guid.jsdeleted−8
@@ -1,8 +0,0 @@
1−
2−Elm = {};
3−
4−var Guid = function() {
5− var counter = 0;
6− var guid = function() { counter += 1; return counter; };
7− return {guid : guid};
8−}();
core-js/List.jsdeleted−482
@@ -1,482 +0,0 @@
1−Elm.List = function() {
2−
3− var throwError = function(f) {
4− throw new Error("Function '" + f + "' expecting a list!");
5− }
6−
7− function length(xs) {
8− var out = 0;
9− while (xs[0] === "Cons") {
10− out += 1;
11− xs = xs[2];
12− }
13− return out;
14− };
15− var reverse = foldl(function(x_72) {
16− return function(y_73) {
17− return["Cons", x_72, y_73]
18− }
19− })(["Nil"]);
20− var concat = foldr(function(x_74) {
21− return function(y_75) {
22− return Value.append(x_74, y_75)
23− }
24− })(["Nil"]);
25− var and = foldl(function(x_77) {
26− return function(y_78) {
27− return x_77 && y_78
28− }
29− })(true);
30− var or = foldl(function(x_79) {
31− return function(y_80) {
32− return x_79 || y_80
33− }
34− })(false);
35− var sum = foldl(function(x_89) {
36− return function(y_90) {
37− return x_89 + y_90
38− }
39− })(0);
40− var product = foldl(function(x_91) {
41− return function(y_92) {
42− return x_91 * y_92
43− }
44− })(1);
45− var maximum = foldl1(function(x) { return function(y) { return Math.max(x,y) } });
46− var minimum = foldl1(function(x) { return function(y) { return Math.min(x,y) } });
47− function head(v) {
48− if (v[0] !== "Cons") {
49− throw new Error("Error: 'head' only accepts lists of length greater than one.");
50− }
51− return v[1];
52− }
53− function tail(v) {
54− if (v[0] !== "Cons") {
55− throw new Error("Error: 'tail' only accepts lists of length greater than one.");
56− }
57− return v[2];
58− }
59− function last(v) {
60− if (v[0] !== "Cons") {
61− throw new Error("Error: 'last' only accepts lists of length greater than one.");
62− }
63− var out = v[1];
64− while (v[0] === "Cons") {
65− out = v[1];
66− v = v[2];
67− }
68− return out;
69− }
70− function map(f) {
71− return function(xs) {
72− if (xs[0] === "Nil") { return xs; }
73− if (xs[0] !== "Cons") { throwError('map'); }
74− var root = ["Cons", f(xs[1]), ["Nil"]];
75− var curr = root;
76− xs = xs[2];
77− while (xs[0]==="Cons") {
78− curr[2] = ["Cons", f(xs[1]), ["Nil"]];
79− xs = xs[2];
80− curr = curr[2];
81− }
82− return root;
83− }
84− }
85− function foldl(f) {
86− return function(b) {
87− return function(xs) {
88− var acc = b;
89− if (xs[0] === "Nil") { return acc; }
90− if (xs[0] !== "Cons") { throwError('foldl'); }
91− while (xs[0] === "Cons") {
92− acc = f(xs[1])(acc);
93− xs = xs[2];
94− }
95− return acc;
96− }
97− }
98− }
99− function foldr(f) {
100− return function(b) {
101− return function(xs) {
102− var acc = b;
103− if (xs[0] === "Nil") { return acc; }
104− if (xs[0] !== "Cons") { throwError('foldr'); }
105− var arr = [];
106− while (xs[0] === "Cons") {
107− arr.push(xs[1]);
108− xs = xs[2];
109− }
110− for (var i = arr.length; i--; ) {
111− acc = f(arr[i])(acc);
112− }
113− return acc;
114− }
115− }
116− }
117− function foldl1(f_49) {
118− return function(_temp_50) {
119− return function(v) {
120− if("Cons" !== v[0]) {
121− return undefined
122− }else {
123− var x_51 = v[1];
124− var xs_52 = v[2];
125− return foldl(f_49)(x_51)(xs_52)
126− }
127− }(_temp_50)
128− }
129− }
130− function foldr1(f) {
131− return function(xs) {
132− if (xs[0] === "Nil") { throw new Error("'foldr1' requires an non-empty list.") }
133− if (xs[0] !== "Cons") { throwError('foldr1'); }
134− var arr = [];
135− while (xs[0] === "Cons") {
136− arr.push(xs[1]);
137− xs = xs[2];
138− }
139− var acc = arr.pop();
140− for (var i = arr.length; i--; ) {
141− acc = f(arr[i])(acc);
142− }
143− return acc;
144− }
145− }
146− function scanl(f) {
147− return function(b) {
148− return function(xs) {
149− if (xs[0] === "Nil") { return ["Cons",b,["Nil"]]; }
150− if (xs[0] !== "Cons") { throwError('scanl'); }
151− var arr = [b];
152− while (xs[0] === "Cons") {
153− b = f(xs[1])(b);
154− arr.push(b);
155− xs = xs[2];
156− }
157− var out = ["Nil"];
158− for (var i = arr.length; i--; ) {
159− out = ["Cons", arr[i], out];
160− }
161− return out;
162− }
163− }
164− }
165− function scanl1(f) {
166− return function(xs) {
167− if (xs[0] !== "Cons") {
168− throw new Error("Error: 'scanl1' requires a list of at least length 1.");
169− }
170− return scanl(f)(xs[1])(xs[2]);
171− }
172− }
173− function filter(pred) {
174− return function(xs) {
175− if (xs[0] === "Nil") { return xs; }
176− if (xs[0] !== "Cons") { throwError('filter'); }
177− var arr = [];
178− while (xs[0] === "Cons") {
179− if (pred(xs[1])) { arr.push(xs[1]); }
180− xs = xs[2];
181− }
182− var out = ["Nil"];
183− for (var i = arr.length; i--; ) {
184− out = ["Cons", arr[i], out];
185− }
186− return out;
187− }
188− }
189− function concatMap(f_76) {
190− return function(x) {
191− return concat(map(f_76)(x))
192− }
193− }
194− function all(pred) {
195− return foldl(function(x) { return function(acc) {
196− return acc && pred(x);
197− };})(true);
198− }
199− function any(pred) {
200− return foldl(function(x) { return function(acc) {
201− return acc || pred(x);
202− };})(false);
203− }
204− function partition(pred_93) {
205− return function(lst_94) {
206− return function() {
207− var v = lst_94;
208− var c = [function(v) {
209− if("Nil" !== v[0]) {
210− return undefined
211− }else {
212− return["Tuple2", ["Nil"], ["Nil"]]
213− }
214− }, function(v) {
215− if("Cons" !== v[0]) {
216− return undefined
217− }else {
218− var x_95 = v[1];
219− var xs_96 = v[2];
220− return function(v) {
221− if("Tuple2" !== v[0]) {
222− return undefined
223− }else {
224− var as_97 = v[1];
225− var bs_98 = v[2];
226− return pred_93(x_95) ? ["Tuple2", ["Cons", x_95, as_97], bs_98] : ["Tuple2", as_97, ["Cons", x_95, bs_98]]
227− }
228− }(partition(pred_93)(xs_96))
229− }
230− }];
231− for(var i = c.length;i--;) {
232− var r = c[i](v);
233− if(r !== undefined) {
234− return r
235− }
236− }
237− }()
238− }
239− }
240− function zipWith(f) {
241− return function(listA) {
242− return function(listB) {
243− if (listA[0] === "Nil" || listB[0] === "Nil") { return ["Nil"]; }
244− if (listA[0] !== "Cons" || listB[0] !== "Cons") { throwError('zipWith'); }
245− var arr = [];
246− while (listA[0] === "Cons" && listB[0] === "Cons") {
247− arr.push(f(listA[1])(listB[1]));
248− listA = listA[2];
249− listB = listB[2];
250− }
251− var out = ["Nil"];
252− for (var i = arr.length; i--; ) {
253− out = ["Cons", arr[i], out];
254− }
255− return out;
256− }
257− }
258− }
259− function zip(listA) {
260− return function(listB) {
261− if (listA[0] === "Nil" || listB[0] === "Nil") { return ["Nil"]; }
262− if (listA[0] !== "Cons" || listB[0] !== "Cons") { throwError('zip'); }
263− var arr = [];
264− while (listA[0] === "Cons" && listB[0] === "Cons") {
265− arr.push(["Tuple2", listA[1], listB[1]]);
266− listA = listA[2];
267− listB = listB[2];
268− }
269− var out = ["Nil"];
270− for (var i = arr.length; i--; ) {
271− out = ["Cons", arr[i], out];
272− }
273− return out;
274− }
275− }
276− function unzip(pairs_112) {
277− return function() {
278− var v = pairs_112;
279− var c = [function(v) {
280− if("Nil" !== v[0]) {
281− return undefined
282− }else {
283− return["Tuple2", ["Nil"], ["Nil"]]
284− }
285− }, function(v) {
286− if("Cons" !== v[0]) {
287− return undefined
288− }else {
289− var p_113 = v[1];
290− var ps_114 = v[2];
291− return function(v) {
292− if("Tuple2" !== v[0]) {
293− return undefined
294− }else {
295− if("Tuple2" !== v[1][0]) {
296− return undefined
297− }else {
298− var x_115 = v[1][1];
299− var y_116 = v[1][2];
300− if("Tuple2" !== v[2][0]) {
301− return undefined
302− }else {
303− var xs_117 = v[2][1];
304− var ys_118 = v[2][2];
305− return["Tuple2", ["Cons", x_115, xs_117], ["Cons", y_116, ys_118]]
306− }
307− }
308− }
309− }(["Tuple2", p_113, unzip(ps_114)])
310− }
311− }];
312− for(var i = c.length;i--;) {
313− var r = c[i](v);
314− if(r !== undefined) {
315− return r
316− }
317− }
318− }()
319− }
320− function intersperse(sep_119) {
321− return function(xs_120) {
322− return function() {
323− var v = xs_120;
324− var c = [function(v) {
325− if("Nil" !== v[0]) {
326− return undefined
327− }else {
328− return["Nil"]
329− }
330− }, function(v) {
331− if("Cons" !== v[0]) {
332− return undefined
333− }else {
334− var a_124 = v[1];
335− if("Nil" !== v[2][0]) {
336− return undefined
337− }else {
338− return["Cons", a_124, ["Nil"]]
339− }
340− }
341− }, function(v) {
342− if("Cons" !== v[0]) {
343− return undefined
344− }else {
345− var a_121 = v[1];
346− if("Cons" !== v[2][0]) {
347− return undefined
348− }else {
349− var b_122 = v[2][1];
350− var cs_123 = v[2][2];
351− return["Cons", a_121, ["Cons", sep_119, intersperse(sep_119)(["Cons", b_122, cs_123])]]
352− }
353− }
354− }];
355− for(var i = c.length;i--;) {
356− var r = c[i](v);
357− if(r !== undefined) {
358− return r
359− }
360− }
361− }()
362− }
363− }
364− function intercalate(sep_125) {
365− return function(xs_126) {
366− return function() {
367− var v = xs_126;
368− var c = [function(v) {
369− if("Nil" !== v[0]) {
370− return undefined
371− }else {
372− return["Nil"]
373− }
374− }, function(v) {
375− if("Cons" !== v[0]) {
376− return undefined
377− }else {
378− var a_130 = v[1];
379− if("Nil" !== v[2][0]) {
380− return undefined
381− }else {
382− return a_130
383− }
384− }
385− }, function(v) {
386− if("Cons" !== v[0]) {
387− return undefined
388− }else {
389− var a_127 = v[1];
390− if("Cons" !== v[2][0]) {
391− return undefined
392− }else {
393− var b_128 = v[2][1];
394− var cs_129 = v[2][2];
395− return Value.append(a_127, Value.append(sep_125, intercalate(sep_125)(["Cons", b_128, cs_129])))
396− }
397− }
398− }];
399− for(var i = c.length;i--;) {
400− var r = c[i](v);
401− if(r !== undefined) {
402− return r
403− }
404− }
405− }()
406− }
407− }
408− function sort(xs) {
409− if (xs[0] === "Nil") { return xs; }
410− if (xs[0] !== "Cons") { throwError('sort'); }
411− var arr = [];
412− while (xs[0] === "Cons") {
413− arr.push(xs[1]);
414− xs = xs[2];
415− }
416− arr.sort(function(a,b) { return a - b});
417− var out = ["Nil"];
418− for (var i = arr.length; i--; ) {
419− out = [ "Cons", arr[i], out ];
420− }
421− return out;
422− }
423− function take(n) { return function(xs) {
424− if (n <= 0) { return ["Nil"]; }
425− if (xs[0] === "Nil") { return xs; }
426− if (xs[0] !== "Cons") { throwError('take'); }
427− var out = [ "Cons", xs[1], ["Nil"] ];
428− var temp = out;
429− xs = xs[2];
430− --n;
431− while (xs[0] === "Cons" && n > 0) {
432− temp[2] = [ "Cons", xs[1], ["Nil"] ];
433− temp = temp[2];
434− xs = xs[2];
435− --n;
436− }
437− return out;
438− };
439− }
440− function drop(n) { return function(xs) {
441− if (xs[0] === "Nil") { return xs; }
442− if (xs[0] !== "Cons") { throwError('drop'); }
443− while (xs[0] === "Cons" && n > 0) {
444− xs = xs[2];
445− --n;
446− }
447− return xs;
448− };
449− }
450− return {head:head,
451− tail:tail,
452− last:last,
453− map:map,
454− foldl:foldl,
455− foldr:foldr,
456− foldl1:foldl1,
457− foldr1:foldr1,
458− scanl:scanl,
459− scanl1:scanl1,
460− filter:filter,
461− length:length,
462− reverse:reverse,
463− concat:concat,
464− concatMap:concatMap,
465− and:and,
466− or:or,
467− all:all,
468− any:any,
469− sum:sum,
470− product:product,
471− maximum:maximum,
472− minimum:minimum,
473− partition:partition,
474− zipWith:zipWith,
475− zip:zip,
476− unzip:unzip,
477− intersperse:intersperse,
478− intercalate:intercalate,
479− sort:sort,
480− take:take,
481− drop:drop};
482−}();
core-js/Maybe.jsdeleted−62
@@ -1,62 +0,0 @@
1−/*! Maybe
2−!*/
3−
4−/*[Definition]*/
5−
6−/** data Maybe a = Just a | Nothing
7− The Maybe datatype. Useful when a computation may or may not
8− result in a value (e.g. logarithm is defined only for positive numbers).
9−**/
10−
11−/*[Basic Utilities]*/
12−
13−/** maybe : b -> (a -> b) -> Maybe a -> b
14− Apply a function to the contents of a `Maybe`.
15− Return default when given `Nothing`.
16−**/
17−/** isJust : Maybe a -> Bool
18− Check if constructed with `Just`.
19−**/
20−/** isNothing : Maybe a -> Bool
21− Check if constructed with `Nothing`.
22−**/
23−
24−/*[Maybe with Lists]*/
25−
26−/** cons : Maybe a -> [a] -> [a]
27− If `Just`, adds the value to the front of the list.
28− If `Nothing`, list is unchanged.
29−**/
30−/** justs : [Maybe a] -> [a]
31− Filters out Nothings and extracts the remaining values.
32−**/
33−
34−Elm.Maybe = function() {
35− function consMaybe(x) { return function(xs) {
36− if (x[0] === "Just") return ["Cons", x[1], xs];
37− return xs;
38− };
39− }
40− function mapCons(f) { return function(y) { return function(xs) {
41− var x = f(y);
42− if (x[0] === "Just") return ["Cons", x[1], xs];
43− return xs;
44− };
45− };
46− }
47− function maybe(b) { return function(f) { return function(m) {
48− if (m[0] === "Just") return f(m[1]);
49− return b;
50− };
51− };
52− }
53−
54− return {Just : function(x) { return ["Just",x]; },
55− Nothing : ["Nothing"],
56− justs : Elm.List.foldr(consMaybe)(["Nil"]),
57− isJust : function(m) { return m[0] === "Just"; },
58− isNothing : function(m) { return m[0] === "Nothing"; },
59− cons : consMaybe,
60− maybe : maybe
61− };
62−}();
core-js/Prelude.jsdeleted−243
@@ -1,243 +0,0 @@
1−function elmRecordCopy(r) {
2− var o = {};
3− for (var i in r) { o[i] = r[i]; }
4− return o;
5−}
6−
7−function elmRecordRemove(x,r) {
8− var o = elmRecordCopy(r);
9− if (x in o._) {
10− o[x] = o._[x][0];
11− o._[x] = o._[x].slice(1);
12− if (o._[x].length === 0) { delete o._[x]; }
13− } else {
14− delete o[x];
15− }
16− return o;
17−}
18−
19−function elmRecordReplace(kvs,r) {
20− var o = elmRecordCopy(r);
21− for (var i = kvs.length; i--; ) {
22− kvsi = kvs[i];
23− o[kvsi[0]] = kvsi[1];
24− }
25− return o;
26−}
27−
28−function elmRecordInsert(x,v,r) {
29− var o = elmRecordCopy(r);
30− if (x in o) o._[x] = [o[x]].concat(x in o._ ? o._[x].slice(0) : []);
31− o[x] = v;
32− return o;
33−}
34−
35−Value.addListener(document, 'elm_log', function(e) { console.log(e.value); });
36−Value.addListener(document, 'elm_title', function(e) {document.title = e.value;});
37−Value.addListener(document, 'elm_redirect', function(e) {
38− if (e.value.length > 0) { window.location = e.value; }
39− });
40−Value.addListener(document, 'elm_viewport', function(e) {
41− var node = document.getElementById('elm_viewport');
42− if (!node) {
43− node = document.createElement('meta');
44− node.id = 'elm_viewport';
45− node.name = 'viewport';
46− document.head.appendChild(node);
47− }
48− node.content = e.value;
49− Dispatcher.notify(Elm.Window.dimensions.id,
50− Value.Tuple(window.innerWidth, window.innerHeight));
51− });
52−
53−Elm.Prelude = function() {
54− var mod = function(x) { return function(y) {
55− var r = x % y;
56− var m = x==0 ? 0 : (y>0 ? (x>=0 ? r : r+y) : -mod(-x)(-y));
57− return m == y ? 0 : m;
58− }; };
59−
60− var min = function(x) { return function(y) { return Math.min(x,y); }; };
61− var max = function(x) { return function(y) { return Math.max(x,y); }; };
62−
63− var flip=function(f){return function(x){return function(y){return f(y)(x);};};};
64− var clamp = function(lo) { return function(hi) {
65− return function(x) { return Math.min(hi, Math.max(lo, x)); };
66− };
67− };
68− var curry = function(f) { return function(x) { return function(y) {
69− return f(["Tuple2",x,y]); }; };
70− };
71− var uncurry = function(f) { return function(p) {
72− if (p[0] !== "Tuple2") {
73− throw new Error("Function was uncurry'd but was not given a pair.");
74− }
75− return f(p[1])(p[2]); };
76− };
77−
78− var logBase=function(b){return function(x){return Math.log(x)/Math.log(b);};};
79−
80− function readInt(str) {
81− var s = Elm.JavaScript.castStringToJSString(str);
82− var len = s.length;
83− if (len === 0) { return ["Nothing"]; }
84− var start = 0;
85− if (s[0] == '-') {
86− if (len === 1) { return ["Nothing"]; }
87− start = 1;
88− }
89− for (var i = start; i < len; ++i) {
90− if (!Elm.Char.isDigit(s[i])) { return ["Nothing"]; }
91− }
92− return ["Just", parseInt(s)];
93− }
94−
95− function readFloat(str) {
96− var s = Elm.JavaScript.castStringToJSString(str);
97− var len = s.length;
98− if (len === 0) { return ["Nothing"]; }
99− var start = 0;
100− if (s[0] == '-') {
101− if (len === 1) { return ["Nothing"]; }
102− start = 1;
103− }
104− var dotCount = 0;
105− for (var i = start; i < len; ++i) {
106− if (Elm.Char.isDigit(s[i])) { continue; }
107− if (s[i] === '.') {
108− dotCount += 1;
109− if (dotCount <= 1) { continue; }
110− }
111− return ["Nothing"];
112− }
113− return ["Just", parseFloat(s)];
114− }
115−
116− function compare(x) { return function (y) {
117− if (x instanceof Array && y instanceof Array) {
118− var len = x.length;
119− if (len == y.length) {
120− for (var i = 1; i < len; ++i) {
121− var cmp = compare(x[i])(y[i]);
122− if (cmp[0] === 'EQ') continue;
123− return cmp;
124− }
125− return ['EQ'];
126− }
127− return [ y.length == 1 ? 'GT' : 'LT' ];
128− }
129− return [ x === y ? 'EQ' : (x < y ? 'LT' : 'GT') ];
130− };
131− }
132− return {eq : Value.eq,
133− id : function(x) { return x; },
134− not : function(b) { return !b; },
135− xor : function(x) { return function(y) { return x != y; }; },
136− fst : function(p) { return p[1]; },
137− snd : function(p) { return p[2]; },
138− rem : function(x) { return function(y) { return x % y; }; },
139− div : function(x) { return function(y) { return ~~(x / y); }; },
140− otherwise : true,
141− compare : compare,
142− toFloat : function(x) { return x; },
143− round : function(n) { return Math.round(n); },
144− floor : function(n) { return Math.floor(n); },
145− ceiling : function(n) { return Math.ceil(n); },
146− truncate : function(n) { return ~~n; },
147− readInt : readInt,
148− readFloat : readFloat,
149− sqrt : Math.sqrt,
150− abs : Math.abs,
151− pi : Math.PI,
152− e : Math.E,
153− sin : Math.sin,
154− cos : Math.cos,
155− tan : Math.tan,
156− asin : Math.asin,
157− acos : Math.acos,
158− atan : Math.atan,
159− atan2 : function(y) { return function(x) { return Math.atan2(y,x); }; },
160− mod : mod,
161− min : min,
162− max : max,
163− flip : flip,
164− clamp : clamp,
165− curry : curry,
166− uncurry : uncurry,
167− logBase : logBase,
168− Just : Elm.Maybe.Just,
169− Nothing : Elm.Maybe.Nothing,
170− maybe : Elm.Maybe.maybe,
171− map : Elm.List.map,
172− zip : Elm.List.zip,
173− zipWith : Elm.List.zipWith,
174− filter : Elm.List.filter,
175− head : Elm.List.head,
176− tail : Elm.List.tail,
177− last : Elm.List.last,
178− length : Elm.List.length,
179− reverse : Elm.List.reverse,
180− foldr : Elm.List.foldr,
181− foldr1 : Elm.List.foldr1,
182− foldl : Elm.List.foldl,
183− foldl1 : Elm.List.foldl1,
184− and : Elm.List.and,
185− or : Elm.List.or,
186− all : Elm.List.all,
187− any : Elm.List.any,
188− sum : Elm.List.sum,
189− product : Elm.List.product,
190− concat : Elm.List.concat,
191− concatMap : Elm.List.concatMap,
192− maximum : Elm.List.maximum,
193− minimum : Elm.List.minimum,
194− scanl : Elm.List.scanl,
195− scanl1 : Elm.List.scanl1,
196− take : Elm.List.take,
197− drop : Elm.List.drop,
198− zip : Elm.List.zip,
199− unzip : Elm.List.unzip,
200− lift : Elm.Signal.lift,
201− lift2 : Elm.Signal.lift2,
202− lift3 : Elm.Signal.lift3,
203− lift4 : Elm.Signal.lift4,
204− lift5 : Elm.Signal.lift5,
205− lift6 : Elm.Signal.lift6,
206− lift7 : Elm.Signal.lift7,
207− lift8 : Elm.Signal.lift8,
208− foldp : Elm.Signal.foldp,
209− foldp1 : Elm.Signal.foldp1,
210− foldp$ : Elm.Signal.foldp$,
211− constant : Elm.Signal.constant,
212− merge : Elm.Signal.merge,
213− merges : Elm.Signal.merges,
214− mergeEither : Elm.Signal.mergeEither,
215− count : Elm.Signal.count,
216− countIf : Elm.Signal.countIf,
217− average : Elm.Signal.average,
218− keepIf : Elm.Signal.keepIf,
219− dropIf : Elm.Signal.dropIf,
220− keepWhen : Elm.Signal.keepWhen,
221− dropWhen : Elm.Signal.dropWhen,
222− dropRepeats : Elm.Signal.dropRepeats,
223− sampleOn : Elm.Signal.sampleOn,
224− timestamp : Elm.Signal.timestamp,
225− timeOf : Elm.Signal.timeOf
226− };
227−
228−}();
229−
230−(function() {
231− var include = function(library) {
232− for (var i in library) {
233− Elm.Prelude[i] = library[i];
234− }
235− };
236− include (Elm.Color);
237− include (Elm.Text);
238− include (Elm.Graphics);
239− include (Elm.Time);
240−
241− show = Value.show;
242−
243−}());
core-js/Set.jsdeleted−31
@@ -1,31 +0,0 @@
1−
2−Elm.Set=function(){
3− var empty_0=Elm.Dict.empty;
4− var remove_3=Elm.Dict.remove;
5− var member_4=Elm.Dict.member;
6− var union_5=Elm.Dict.union;
7− var intersect_6=Elm.Dict.intersect;
8− var diff_7=Elm.Dict.diff;
9− var toList_8=Elm.Dict.keys;
10− var fromList_9=Elm.List.foldl(function(k_15){
11− return function(t_16){
12− return Elm.Dict.insert(k_15)(["Tuple0"])(t_16);};})(empty_0);
13− function singleton_1(k_13){
14− return Elm.Dict.singleton(k_13)(["Tuple0"]);};
15− function insert_2(k_14){
16− return Elm.Dict.insert(k_14)(["Tuple0"]);};
17− function foldl_10(f_17){
18− return Elm.Dict.foldl(function(k_18){
19− return function(v_19){
20− return function(b_20){
21− return f_17(k_18)(b_20);};};});};
22− function foldr_11(f_21){
23− return Elm.Dict.foldr(function(k_22){
24− return function(v_23){
25− return function(b_24){
26− return f_21(k_22)(b_24);};};});};
27− function map_12(f_25){
28− return function(t_26){
29− return function(x){
30− return fromList_9(Elm.List.map(f_25)(x));}(toList_8(t_26));};};
31− return {empty:empty_0,singleton:singleton_1,insert:insert_2,remove:remove_3,member:member_4,union:union_5,intersect:intersect_6,diff:diff_7,toList:toList_8,fromList:fromList_9,foldl:foldl_10,foldr:foldr_11,map:map_12};}();
core-js/Signal/HTTP.jsdeleted−111
@@ -1,111 +0,0 @@
1−
2−/*! HTTP
3−A library for asynchronous HTTP requests (AJAX). See the
4−[WebSocket](http://elm-lang.org/docs/WebSocket.elm) library if
5−you have very strict latency requirements.
6−!*/
7−
8−Elm.HTTP = function() {
9− var JS = Elm.JavaScript;
10− var toElmString = Elm.JavaScript.castJSStringToString;
11−
12− /*[Creating Requests]*/
13−
14− /** get : String -> Request String
15− Create a GET request to the given url.
16− **/
17− function get(url) { return request("GET")(url)(null)(["Nil"]); }
18−
19− /** post : String -> String -> Request String
20− Create a POST request to the given url, carrying the given data.
21− **/
22− function post(url) { return function(data) {
23− return request("POST")(url)(data)(["Nil"]); }; }
24−
25− /** request : String -> String -> String -> [(String,String)] -> Request String
26− Create a customized request. Arguments are request type (get, post, put,
27− delete, etc.), target url, data, and a list of additional headers.
28− **/
29− function request(verb) { return function(url) { return function(data) {
30− return function(headers) {
31− return {0 : "Request",
32− length : 1,
33− verb : JS.castStringToJSString(verb),
34− url : JS.castStringToJSString(url),
35− data : data === null ? null : JS.castStringToJSString(data),
36− headers : headers }; }; }; };
37− }
38−
39− function registerReq(queue,responses) { return function(req) {
40− if (req.url !== "") { sendReq(queue,responses,req); }
41− };
42− }
43−
44− function updateQueue(queue,responses) {
45− if (queue.length > 0) {
46− Dispatcher.notify(responses.id, queue[0].value);
47− if (queue[0].value[0] !== "Waiting") {
48− queue.shift();
49− setTimeout(function() { updateQueue(queue,responses); }, 0);
50− }
51− }
52− }
53−
54− function sendReq(queue,responses,req) {
55− var response = { value: ["Waiting"] };
56− queue.push(response);
57−
58− var request = null;
59− if (window.ActiveXObject) { request = new ActiveXObject("Microsoft.XMLHTTP"); }
60− if (window.XMLHttpRequest) { request = new XMLHttpRequest(); }
61− request.onreadystatechange = function(e) {
62− if (request.readyState === 4) {
63− response.value = (request.status === 200
64− ? ["Success", toElmString(request.responseText)]
65− : ["Failure", request.status,
66− toElmString(request.statusText)]);
67− setTimeout(function() { updateQueue(queue,responses); }, 0);
68− }
69− };
70− request.open(req.verb, req.url, true);
71− Elm.List.map(function(pair) {
72− request.setRequestHeader(
73− JS.castStringToJSString(pair[1]),
74− JS.castStringToJSString(pair[2]));
75− })(req.headers);
76− request.send(req.data);
77− return null;
78− }
79−
80− /*[Responses]*/
81−
82− /** data Response a = Waiting | Success a | Failure Int String
83− The datatype for responses. Success contains only the returned message.
84− Failures contain both an error code and an error message.
85− **/
86−
87− /*[Sending Requests]*/
88−
89− /** send : Signal (Request a) -> Signal (Response String)
90− Performs an HTTP request with the given requests. Produces a signal
91− that carries the responses.
92− **/
93− function send(requests) {
94− var responses = Elm.Signal.constant(["Waiting"]);
95− var sender = Elm.Signal.lift(registerReq([],responses))(requests);
96− function f(x) { return function(y) { return x; } }
97− return Elm.Signal.lift2(f)(responses)(sender);
98− }
99−
100− /** sendGet : Signal String -> Signal (Response String)
101− Performs an HTTP GET request with the given urls. Produces a signal
102− that carries the responses.
103− **/
104−
105− return {get : get,
106− post : post,
107− request : request,
108− send : send,
109− sendGet : function(urls){return send(Elm.Signal.lift(get)(urls));}
110− };
111−}();
core-js/Signal/Input.jsdeleted−84
@@ -1,84 +0,0 @@
1−
2−Elm.Input = function() {
3− var JS = Elm.JavaScript;
4− var toElmString = Elm.JavaScript.castJSStringToString;
5− var newTextInput = function(elem, ghostText) {
6− elem.placeholder = JS.castStringToJSString(ghostText);
7− var str = Elm.Signal.constant(["Nil"]);
8− Value.addListener(elem, 'keyup', function(e) {
9− Dispatcher.notify(str.id, toElmString(elem.value));
10− elem.focus();
11− });
12− elem.style.padding = "1px";
13− return Value.Tuple(Value.wrap(elem), str);
14− };
15− var newElement = function(name) {
16− var e = document.createElement(name);
17− e.style.padding = "0";
18− e.style.margin = "0";
19− return e;
20− };
21− var textArea = function(cols) { return function(rows) {
22− var textarea = newElement('textarea');
23− textarea.rows = rows;
24− textarea.cols = cols;
25− return newTextInput(textarea, "");
26− };
27− };
28− var textField = function(ghostText) {
29− var field = newElement('input');
30− field.type = 'text';
31− return newTextInput(field, ghostText);
32− };
33− var password = function(ghostText) {
34− var field = newElement('input');
35− field.type = 'password';
36− return newTextInput(field, ghostText);
37− };
38− var checkbox = function(checked) {
39− var box = newElement('input');
40− box.type = 'checkbox';
41− box.checked = checked;
42− var status = Elm.Signal.constant(checked);
43− Value.addListener(box, 'change', function(e) {
44− Dispatcher.notify(status.id, box.checked);
45− });
46− return Value.Tuple(Value.wrap(box), status);
47− };
48− var dropDown = function(options) {
49− var slct = newElement('select');
50− var opts = [];
51− while (options[0] === "Cons") {
52− var opt = newElement('option');
53− var str = Value.toText(options[1][1]);
54− opt.value = str;
55− opt.innerHTML = str;
56− slct.appendChild(opt);
57− opts.push(options[1][2]);
58− options = options[2];
59− }
60− var status = Elm.Signal.constant(opts[0]);
61− Value.addListener(slct, 'change', function(e) {
62− Dispatcher.notify(status.id, opts[slct.selectedIndex]);
63− });
64− return Value.Tuple(Value.wrap(slct), status);
65− };
66− var stringDropDown = function(opts) {
67− return dropDown(Elm.List.map (function(x) {return Value.Tuple(x,x);}) (opts));
68− };
69− var button = function(name) {
70− var b = newElement('button');
71− b.type = "button";
72− b.innerText = JS.castStringToJSString(name);
73− var press = Elm.Signal.constant(false);
74− Value.addListener(b, 'click', function(e) {
75− Dispatcher.notify(press.id, true);
76− Dispatcher.notify(press.id, false);
77− });
78− return Value.Tuple(Value.wrap(b),press);
79− };
80− return {textArea:textArea, textField:textField,
81− password:password, checkbox:checkbox,
82− dropDown:dropDown, stringDropDown:stringDropDown,
83− button:button};
84−}();
core-js/Signal/Keyboard.jsdeleted−123
@@ -1,123 +0,0 @@
1−
2−Elm.Keyboard = { Raw : function() {
3− var keysDown = Elm.Signal.constant(["Nil"]);
4− var charPressed = Elm.Signal.constant(["Nothing"]);
5−
6− function remove(x,xs) {
7− if (xs[0] === "Nil") return xs;
8− if (xs[1] === x) return xs[2];
9− return ["Cons", xs[1], remove(x,xs[2])];
10− }
11− function has(x,xs) {
12− while (xs[0] !== "Nil") {
13− if (xs[1] === x) return true;
14− xs = xs[2];
15− }
16− return false;
17− }
18− Value.addListener(document, 'keydown', function(e) {
19− if (has(e.keyCode, keysDown.value)) return;
20− var hasListener = Dispatcher.notify(keysDown.id, ["Cons", e.keyCode, keysDown.value]);
21− if (!hasListener)
22− this.removeEventListener('keydown',arguments.callee,false);
23− });
24− Value.addListener(document, 'keyup', function(e) {
25− var codes = remove(e.keyCode, keysDown.value);
26− var hasListener = Dispatcher.notify(keysDown.id, codes);
27− if (!hasListener)
28− this.removeEventListener('keyup',arguments.callee,false);
29− });
30− Value.addListener(window, 'blur', function(e) {
31− var hasListener = Dispatcher.notify(keysDown.id, ["Nil"]);
32− if (!hasListener)
33− this.removeEventListener('blur',arguments.callee,false);
34− });
35− Value.addListener(document, 'keypress', function(e) {
36− var hasListener = Dispatcher.notify(charPressed.id, ["Just",e.charCode || e.keyCode]);
37− Dispatcher.notify(charPressed.id, ["Nothing"]);
38− if (!hasListener)
39− this.removeEventListener('keypress',arguments.callee,false);
40− });
41− return {keysDown:keysDown,
42− charPressed:charPressed};
43− }()
44−};
45−
46−/*! Keyboard
47−These are nicely curated inputs from the keyboard. See the
48−[Keyboard.Raw library](/docs/Signal/KeyboardRaw.elm) for a
49−lower-level interface that will let you define more complicated behavior.
50−!*/
51−
52−(function() {
53− function keySignal(f) {
54− var signal = Elm.Signal.lift(f)(Elm.Keyboard.Raw.keysDown);
55− Elm.Keyboard.Raw.keysDown.defaultNumberOfKids += 1;
56− signal.defaultNumberOfKids = 0;
57− return signal;
58− }
59−
60− function dir(left,right,up,down) {
61− function f(ks) {
62− var x = 0, y = 0;
63− while (ks[0] == "Cons") {
64− switch (ks[1]) {
65− case left : --x; break;
66− case right: ++x; break;
67− case up : ++y; break;
68− case down : --y; break;
69− }
70− ks = ks[2];
71− }
72− return { _:[true], x:[x], y:[y] };
73− }
74− return keySignal(f);
75− }
76−
77− function is(key) {
78− function f(ks) {
79− while (ks[0] == "Cons") {
80− if (key == ks[1]) return true;
81− ks = ks[2];
82− }
83− return false;
84− }
85− return keySignal(f);
86− }
87−
88− /*[Directions]*/
89−
90− /** arrows : Signal { x:Int, y:Int }
91− A signal of records indicating which arrow keys are pressed.
92−
93− `{ x = 0, y = 0 }` when pressing no arrows.
94− `{ x =-1, y = 0 }` when pressing the left arrow.
95− `{ x = 1, y = 1 }` when pressing the up and right arrows.
96− `{ x = 0, y =-1 }` when pressing the down, left, and right arrows.
97− **/
98− Elm.Keyboard.arrows = dir(37,39,38,40);
99−
100− /** wasd : Signal { x:Int, y:Int }
101− Just like the arrows signal, but this uses keys w, a, s, and d,
102− which are common controls for many computer games.
103− **/
104− Elm.Keyboard.wasd = dir(65,68,87,83);
105−
106− /*[Modifiers]*/
107−
108− /** shift : Signal Bool
109− Whether the shift key is pressed.
110− **/
111− Elm.Keyboard.shift = is(16);
112−
113− /** ctrl : Signal Bool
114− Whether the control key is pressed.
115− **/
116− Elm.Keyboard.ctrl = is(17);
117−
118− /** space : Signal Bool
119− Whether the space key is pressed.
120− **/
121− Elm.Keyboard.space = is(32);
122−
123−}());
core-js/Signal/Mouse.jsdeleted−106
@@ -1,106 +0,0 @@
1−/*! Mouse
2− !*/
3−
4−Elm.Mouse = function() {
5− /*[Position]*/
6−
7− /** position : Signal (Int,Int)
8− The current mouse position.
9− **/
10− var position = Elm.Signal.constant(Value.Tuple(0,0));
11− position.defaultNumberOfKids = 2;
12−
13− /** x : Signal Int
14− The current x-coordinate of the mouse.
15− **/
16− var x = Elm.Signal.lift(function(p){return p[1];})(position);
17− x.defaultNumberOfKids = 0;
18−
19− /** y : Signal Int
20− The current y-coordinate of the mouse.
21− **/
22− var y = Elm.Signal.lift(function(p){return p[2];})(position);
23− y.defaultNumberOfKids = 0;
24−
25− /*[Button Status]*/
26−
27− /** isDown : Signal Bool
28− The current state of the left mouse-button.
29− True when the button is down, and false otherwise.
30− **/
31− var isDown = Elm.Signal.constant(false);
32−
33− /** isClicked : Signal Bool
34− True immediately after the left mouse-button has been clicked,
35− and false otherwise.
36− **/
37− var isClicked = Elm.Signal.constant(false);
38−
39− /** clicks : Signal ()
40− Always equal to unit. Event triggers on every mouse click.
41− **/
42− var clicks = Elm.Signal.constant(Value.Tuple());
43−
44− function getXY(e) {
45− var posx = 0;
46− var posy = 0;
47− if (!e) e = window.event;
48− if (e.pageX || e.pageY) {
49− posx = e.pageX;
50− posy = e.pageY;
51− } else if (e.clientX || e.clientY) {
52− posx = e.clientX + document.body.scrollLeft +
53− document.documentElement.scrollLeft;
54− posy = e.clientY + document.body.scrollTop +
55− document.documentElement.scrollTop;
56− }
57− return Value.Tuple(posx, posy);
58− }
59−
60− Value.addListener(document, 'click', function(e) {
61− var hasListener1 = Dispatcher.notify(isClicked.id, true);
62− var hasListener2 = Dispatcher.notify(clicks.id, Value.Tuple());
63− Dispatcher.notify(isClicked.id, false);
64− if (!hasListener1 && !hasListener2)
65− this.removeEventListener('click',arguments.callee,false);
66− });
67− Value.addListener(document, 'mousedown', function(e) {
68− var hasListener = Dispatcher.notify(isDown.id, true);
69− if (!hasListener)
70− this.removeEventListener('mousedown',arguments.callee,false);
71− });
72− Value.addListener(document, 'mouseup', function(e) {
73− var hasListener = Dispatcher.notify(isDown.id, false);
74− if (!hasListener)
75− this.removeEventListener('mouseup',arguments.callee,false);
76− });
77− Value.addListener(document, 'mousemove', function(e) {
78− var hasListener = Dispatcher.notify(position.id, getXY(e));
79− if (!hasListener)
80− this.removeEventListener('mousemove',arguments.callee,false);
81− });
82−
83− /** isClickedOn : Element -> (Element, Signal Bool)
84− Determine whether an element has been clicked. The resulting pair
85− is a signal of booleans that is true when its paired element has
86− been clicked. The signal is True immediately after the left
87− mouse-button has been clicked, and false otherwise.
88− **/
89− var clickedOn = function(elem) {
90− var node = Render.render(elem);
91− var click = Elm.Signal.constant(false);
92− Value.addListener(node, 'click', function(e) {
93− Dispatcher.notify(click.id, true);
94− Dispatcher.notify(click.id, false);
95− });
96− return Value.Tuple(Value.wrap(node), click);
97− };
98− return {position: position,
99− x:x,
100− y:y,
101− isClicked: isClicked,
102− isDown: isDown,
103− clicks: clicks,
104− isClickedOn: clickedOn
105− };
106− }();
core-js/Signal/Random.jsdeleted−29
@@ -1,29 +0,0 @@
1−/*! Random
2− !*/
3−
4−Elm.Random = function() {
5− /*[In a Range]*/
6−
7− /** inRange : Int -> Int -> Signal Int
8− Given a range from low to high, this produces a random number
9− between 'low' and 'high' inclusive. The value in the signal does
10− not change after the page has loaded.
11− **/
12− var inRange = function(min) { return function(max) {
13− return Elm.Signal.constant(Math.floor(Math.random() * (max-min+1)) + min);
14− };
15− };
16−
17− /** randomize : Int -> Int -> Signal a -> Signal Int
18− Given a range from low to high and a signal of values, this produces
19− a new signal that changes whenever the input signal changes. The new
20− values are random number between 'low' and 'high' inclusive.
21− **/
22− var randomize = function(min) { return function(max) { return function(signal) {
23− function f(x) { return Math.floor(Math.random() * (max-min+1)) + min; }
24− return Elm.Signal.lift(f)(signal);
25− };
26− };
27− };
28− return { inRange:inRange, randomize:randomize };
29−}();
core-js/Signal/Time.jsdeleted−112
@@ -1,112 +0,0 @@
1−/*! Time
2−Library for working with time. Type `Time` represents some number of
3−milliseconds.
4−!*/
5−
6−Elm.Time = function() {
7−
8− /*[Times]*/
9−
10− /** hour, minute, second, ms : Time
11− Units of time, making it easier to specify things like a
12− half-second `(second / 2)`.
13− **/
14−
15− function timeNow() { return (new window.Date).getTime(); }
16−
17− /*[Tickers]*/
18−
19− /** fps : Number -> Signal Time
20− Takes desired number of frames per second (fps). The resulting signal
21− gives a sequence of time deltas as quickly as possible until it reaches
22− the desired FPS. A time delta is the time between the last frame and the
23− current frame.
24− **/
25−
26− /** fpsWhen : Number -> Signal Bool -> Signal Time
27− Same as the fps function, but you can turn it on and off. Allows you
28− to do brief animations based on user input without major ineffeciencies.
29− The first time delta after a pause is always zero, no matter how long
30− the pause was. This way summing the deltas will actually give the amount
31− of time that the output signal has been running.
32− **/
33− function fpsWhen(desiredFPS) { return function (isOn) {
34− var msPerFrame = 1000 / desiredFPS;
35− var prev = timeNow(), curr = prev, diff = 0, wasOn = true;
36− var ticker = Elm.Signal.constant(diff);
37− function tick(zero) { return function() {
38− curr = timeNow();
39− diff = zero ? 0 : curr - prev;
40− prev = curr;
41− Dispatcher.notify(ticker.id, diff);
42− };
43− }
44− var timeoutID = 0;
45− function f(isOn) { return function(t) {
46− if (isOn) {
47− timeoutID = setTimeout(tick(!wasOn && isOn), msPerFrame);
48− } else if (wasOn) {
49− clearTimeout(timeoutID);
50− }
51− wasOn = isOn;
52− return t;
53− };
54− }
55− return Elm.Signal.lift2(f)(isOn)(ticker);
56− };
57− }
58−
59− /** every : Time -> Signal Time
60− Takes a time interval t. The resulting signal is the current time,
61− updated every t.
62− **/
63− function everyWhen(isOn) { return function(t) {
64− var clock = Elm.Signal.constant(timeNow());
65− function tellTime() { Dispatcher.notify(clock.id, timeNow()); }
66− setInterval(tellTime, t);
67− return clock;
68− };
69− }
70−
71− function since(t) { return function(s) {
72− function cmp(a) { return function(b) { return !Value.eq(a,b); }; }
73− var dcount = Elm.Signal.count(Elm.Signal.delay(t)(s));
74− return Elm.Signal.lift2(cmp)(Elm.Signal.count(s))(dcount);
75− };
76− }
77− function after(t) {
78− t *= 1000;
79− var thread = Elm.Signal.constant(false);
80− setTimeout(function() { Dispatcher.notify(thread.id, true); }, t);
81− return thread;
82− }
83− function before(t) {
84− t *= 1000;
85− var thread = Elm.Signal.constant(true);
86− setTimeout(function() { Dispatcher.notify(thread.id, false); }, t);
87− return thread;
88− }
89− function read(s) {
90− var t = window.Date.parse(s);
91− return isNaN(t) ? ["Nothing"] : ["Just",t];
92− }
93− return {fpsWhen : fpsWhen,
94− fps : function(t) { return fpsWhen(t)(Elm.Signal.constant(true)); },
95− every : everyWhen(Elm.Signal.constant(true)),
96− delay : Elm.Signal.delay,
97− since : since,
98− after : after,
99− before : before,
100− hour : 3600000,
101− minute : 60000,
102− second : 1000,
103− ms : 1,
104− inHours : function(t) { return t / 3600000; },
105− inMinutes : function(t) { return t / 60000; },
106− inSeconds : function(t) { return t / 1000; },
107− inMss : function(t) { return t; },
108− toDate : function(t) { return new window.Date(t); },
109− read : read
110− };
111−
112−}();
core-js/Signal/Touch.jsdeleted−109
@@ -1,109 +0,0 @@
1−/*! Touch
2−This is an early version of the touch library. It will likely grow to
3−include gestures that would be useful for both games and web-pages.
4−!*/
5−
6−Elm.Touch = function() {
7−
8− function Dict() {
9− this.keys = [];
10− this.values = [];
11−
12− this.insert = function(key,value) {
13− this.keys.push(key);
14− this.values.push(value);
15− };
16− this.lookup = function(key) {
17− var i = this.keys.indexOf(key)
18− return i >= 0 ? this.values[i] : {x:0,y:0,t:0};
19− };
20− this.remove = function(key) {
21− var i = this.keys.indexOf(key);
22− if (i < 0) return;
23− var t = this.values[i];
24− this.keys.splice(i,1);
25− this.values.splice(i,1);
26− return t;
27− };
28− }
29−
30− var root = Elm.Signal.constant([]),
31− tapTime = 500,
32− hasTap = false,
33− tap = {_:[true],x:[0],y:[0]},
34− dict = new Dict();
35−
36− function touch(t) {
37− var r = dict.lookup(t.identifier);
38− return {_ : [true], id: [t.identifier],
39− x: [t.pageX], y: [t.pageY],
40− x0: [r.x], y0: [r.y],
41− t0: [r.t] };
42− }
43−
44− function start(e) {
45− dict.insert(e.identifier,{x:e.pageX,y:e.pageY,t:Date.now()});
46− }
47− function end(e) {
48− var t = dict.remove(e.identifier);
49− if (Date.now() - t.t < tapTime) {
50− hasTap = true;
51− tap = {_:[true], x:[t.x], y:[t.y]};
52− }
53− }
54−
55− function listen(name, f) {
56− function update(e) {
57− for (var i = e.changedTouches.length; i--; ) { f(e.changedTouches[i]); }
58− var ts = new Array(e.touches.length);
59− for (var i = e.touches.length; i--; ) { ts[i] = touch(e.touches[i]); }
60− var hasListener = Dispatcher.notify(root.id, ts);
61− if (!hasListener) return document.removeEventListener(name, update);
62− e.preventDefault();
63− }
64− Value.addListener(document, name, update);
65− }
66−
67− listen("touchstart", start);
68− listen("touchmove", function(_){});
69− listen("touchend", end);
70− listen("touchcancel", end);
71− listen("touchleave", end);
72−
73− function dependency(f) {
74− var sig = Elm.Signal.lift(f)(root);
75− root.defaultNumberOfKids += 1;
76− sig.defaultNumberOfKids = 0;
77− return sig;
78− }
79−
80− /*[Touches]*/
81−
82− /** touches : Signal [{ x:Int, y:Int, id:Int, x0:Int, y0:Int, t0:Time }]
83− A list of touches. Each ongoing touch is represented by a set of
84− coordinates and an identifier id that allows you to distinguish
85− between different touches. Each touch also contains the coordinates and
86− time of the initial contact (x0, y0, and t0) which helps compute more
87− complicated gestures.
88− **/
89− var touches = dependency(function(ts) {
90− return Elm.JavaScript.castJSArrayToList(ts);
91− });
92−
93− /*[Gestures]*/
94−
95− /** taps : Signal { x:Int, y:Int }
96− The last position that was tapped. Default value is `{x=0,y=0}`.
97− Updates whenever the user taps the screen.
98− **/
99− var taps = function() {
100− var sig = dependency(function(_) { return tap; });
101− sig.defaultNumberOfKids = 1;
102− function pred(_) { var b = hasTap; hasTap = false; return b; }
103− var sig2 = Elm.Signal.keepIf(pred)({_:[true],x:[0],y:[0]})(sig);
104− sig2.defaultNumberOfKids = 0;
105− return sig2;
106− }();
107−
108− return { touches: touches, taps: taps };
109−}();
core-js/Signal/WebSocket.jsdeleted−41
@@ -1,41 +0,0 @@
1−/*! WebSocket
2−A library for low latency HTTP communication. See the HTTP library for standard
3−requests like GET, POST, etc.
4−!*/
5−
6−Elm.WebSocket = function() {
7− var JS = Elm.JavaScript;
8−
9− /** open : String -> Signal String -> Signal String
10− Create a web-socket. The first argument is the URL of the desired
11− web-socket server. The input signal holds the outgoing messages,
12− and the resulting signal contains the incoming ones.
13− **/
14− function open(url) { return function(outgoing) {
15− var incoming = Elm.Signal.constant(["Nil"]);
16− var ws = new window.WebSocket(JS.castStringToJSString(url));
17−
18− var pending = [];
19− var ready = false;
20−
21− ws.onopen = function(e) {
22− var len = pending.length;
23− for (var i = 0; i < len; ++i) { ws.send(pending[i]); }
24− ready = true;
25− };
26− ws.onmessage = function(event) {
27− Dispatcher.notify(incoming.id, JS.castJSStringToString(event.data));
28− };
29−
30− function send(msg) {
31− var s = JS.castStringToJSString(msg);
32− ready ? ws.send(s) : pending.push(s);
33− }
34−
35− function take1(x) { return function(y) { return x; } }
36− return Elm.Signal.lift2(take1)(incoming)(Elm.Signal.lift(send)(outgoing));
37− };
38− }
39−
40− return {open:open};
41−}();
core-js/Signal/Window.jsdeleted−35
@@ -1,35 +0,0 @@
1−/*! Window !*/
2−
3−Elm.Window = function() {
4−
5− /*[Dimensions]*/
6−
7− /** dimensions : Signal (Int,Int)
8− The current dimensions of the window (i.e. the area viewable to the
9− user, not including scroll bars).
10− **/
11− var dimensions = Elm.Signal.constant(Value.Tuple(window.innerWidth,
12− window.innerHeight));
13− dimensions.defaultNumberOfKids = 2;
14−
15− /** width : Signal Int
16− The current width of the window.
17− **/
18− var width = Elm.Signal.lift(function(p){return p[1];})(dimensions);
19− width.defaultNumberOfKids = 0;
20−
21− /** height : Signal Int
22− The current height of the window.
23− **/
24− var height = Elm.Signal.lift(function(p){return p[2];})(dimensions);
25− height.defaultNumberOfKids = 0;
26−
27− Value.addListener(window, 'resize', function(e) {
28− var w = document.getElementById('widthChecker').offsetWidth;
29− var hasListener = Dispatcher.notify(dimensions.id,
30− Value.Tuple(w, window.innerHeight));
31− if (!hasListener)
32− this.removeEventListener('resize',arguments.callee,false);
33− });
34− return {dimensions:dimensions,width:width,height:height};
35−}();
core-js/String.jsdeleted−81
@@ -1,81 +0,0 @@
1−
2−/*
3−var String = function() {
4−
5− function append(s1) { return function(s2) {
6− return s1.concat(s2);
7− };
8− }
9− function map(f) { return function(s) {
10− for (var i = s.length; i--; ) { s[i] = f(s[i]); }
11− };
12− }
13−
14− function intercalate(sep) { return function(ss) {
15− return Value.listToArray(ss).join(sep);
16− };
17− }
18− function intersperse(sep) { return function(s) {
19− return s.split("").join(sep);
20− };
21− }
22−
23− function foldl(f) { return function(b) { return function(s) {
24− var acc = b;
25− for (var i = 0, len = s.length; i < len; ++i) { acc = f(s[i])(acc); }
26− return acc;
27− };
28− };
29− }
30− function foldr(f) { return function(b) { return function(s) {
31− var acc = b;
32− for (var i = s.length; i--; ) { acc = f(s[i])(acc); }
33− return acc;
34− };
35− };
36− }
37−
38− function concatMap(f) { return function(s) {
39− var a = s.split("");
40− for (var i = a.length; i--; ) { a[i] = f(a[i]); }
41− return a.join("");
42− };
43− }
44−
45− function forall(pred) { return function(s) {
46− for (var i = s.length; i--; ) { if (!pred(s[i])) {return false}; }
47− return true;
48− };
49− }
50− function exists(pred) { return function(s) {
51− for (var i = s.length; i--; ) { if (pred(s[i])) {return true}; }
52− return false;
53− };
54− }
55−
56− return {cons : append,
57− snoc : append,
58− head : function(s) { return s[0]; },
59− last : function(s) { return s[s.length-1]; },
60− tail : function(s) { return s.slice(1); },
61− length : function(s) { return s.length; },
62− map : map,
63− intercalate : intercalate,
64− intersperse : intersperse,
65− reverse : function(s) { return s.split("").reverse().join(""); },
66− toLower : function(s) { return s.toLowerCase(); },
67− toUpper : function(s) { return s.toUpperCase(); },
68− foldl : foldl,
69− foldr : foldr,
70− concat : function(ss) { return Value.listToArray(ss).join(""); },
71− concatMap : concatMap,
72− forall : forall,
73− exists : exists,
74− //filter : filter,
75− //take:,
76− //drop:,
77− toText : Value.toText,
78− properEscape : Value.properEscape
79− };
80−}();
81−*/
core-js/Text.jsdeleted−49
@@ -1,49 +0,0 @@
1−
2−Elm.Text = function() {
3− function fromString(s) { return Value.toText(s); }
4−
5− var addTag = function(tag) { return function(text) {
6− return '<' + tag + ' style="padding:0;margin:0">' + text + '</' + tag + '>';
7− };
8− };
9− var addStyle = function(style, value) { return function(text) {
10− return "<span style='" + style + ":" + value + "'>" + text + "</span>";
11− };
12− };
13−
14− var typeface = function(name) {
15− name = Elm.JavaScript.castStringToJSString(name);
16− return addStyle('font-family', name);
17− };
18− var size = function(px) {
19− return addStyle('font-size', px + 'px');
20− };
21− var header = addTag('h1');
22− var height = function(h) { return addStyle('font-size', h+'em'); }
23− var italic = addStyle('font-style', 'italic');
24− var bold = addTag('b');
25− var color = function(c) {
26− return addStyle('color', Elm.Color.extract(c));
27− };
28− var underline = addStyle('text-decoration', 'underline');
29− var overline = addStyle('text-decoration', 'overline');
30− var strikeThrough = addStyle('text-decoration', 'line-through');
31− var link = function(href) { return function(text) {
32− return "<a href='" + fromString(href) + "'>" + text + "</a>";
33− };
34− };
35−
36− return {fromString : fromString,
37− toText: fromString,
38− header : header,
39− height : height,
40− italic : italic,
41− bold : bold,
42− underline : underline,
43− overline : overline,
44− strikeThrough : strikeThrough,
45− monospace : typeface('monospace'),
46− typeface : typeface,
47− color : color,
48− link : link };
49−}();
core-js/Value.jsdeleted−291
@@ -1,291 +0,0 @@
1−
2−var Value = function(){
3−
4− var eq = function(x,y) {
5− if (typeof x === "object") {
6− if (x !== null && '_' in x) {
7− for (var i in x) { if (x[i] != y[i]) return false; }
8− for (var i in y) { if (!(i in x)) return false; }
9− return true;
10− }
11− if (x === y) return true;
12− if (x.length !== y.length) return false;
13− for (var i = x.length; i--; ) {
14− if (!eq(x[i],y[i])) return false;
15− }
16− return true;
17− }
18− return x === y;
19− };
20−
21− var Tuple = function() {
22− var len = arguments.length;
23− var arr = new Array(len+1);
24− arr[0] = "Tuple" + arguments.length;
25− for (var i = len; i--; ) {
26− arr[i+1] = arguments[i];
27− }
28− return arr;
29− };
30−
31− var listToArray = function(list) {
32− var arr = [];
33− while (list[0] === "Cons") {
34− arr.push(list[1]);
35− list = list[2];
36− }
37− return arr;
38− };
39−
40− function makeSpaces(s) {
41− if (s.length == 0) { return s; }
42− var arr = s.split('');
43− if (arr[0] == ' ') { arr[0] = "&nbsp;" }
44− for (var i = arr.length; --i; ) {
45− if (arr[i][0] == ' ' && arr[i-1] == ' ') {
46− arr[i-1] = arr[i-1] + arr[i];
47− arr[i] = '';
48− }
49− }
50− for (var i = arr.length; i--; ) {
51− if (arr[i].length > 1 && arr[i][0] == ' ') {
52− var spaces = arr[i].split('');
53− for (var j = spaces.length - 2; j >= 0; j -= 2) {
54− spaces[j] = '&nbsp;';
55− }
56− arr[i] = spaces.join('');
57− }
58− }
59− arr = arr.join('');
60− if (arr[arr.length-1] === " ") {
61− return arr.slice(0,-1) + '&nbsp;';
62− }
63− return arr;
64− }
65−
66− function properEscape(str) {
67− if (str.length == 0) return str;
68− str = str //.replace(/&/g, "&#38;")
69− .replace(/"/g, /*"*/ "&#34;")
70− .replace(/'/g, /*'*/ "&#39;")
71− .replace(/</g, "&#60;")
72− .replace(/>/g, "&#62;")
73− .replace(/\n/g, "<br/>");
74− var arr = str.split('<br/>');
75− for (var i = arr.length; i--; ) {
76− arr[i] = makeSpaces(arr[i]);
77− }
78− return arr.join('<br/>');
79− }
80−
81− var toText = function(elmList) {
82− if (typeof elmList === "string") return properEscape(elmList);
83− var a = [];
84− while (elmList[0] === "Cons") {
85− a.push(elmList[1]);
86− elmList = elmList[2];
87− }
88− return properEscape(a.join(''));
89− };
90−
91− function getTextSize(w,h,txt) {
92− var t = document.createElement('div');
93− t.innerHTML = txt;
94− t.style.textAlign = 'left';
95− if (w > 0) { t.style.width = w + "px"; }
96−
97− t.style.visibility = "hidden";
98− t.style.styleFloat = "left";
99− t.style.cssFloat = "left";
100−
101− document.body.appendChild(t);
102− var cStyle = window.getComputedStyle(t,null);
103− var realW = cStyle.getPropertyValue("width").slice(0,-2) - 0;
104− var realH = cStyle.getPropertyValue("height").slice(0,-2) - 0;
105− document.body.removeChild(t);
106− //delete t;
107− return [Math.ceil(realW),Math.ceil(Math.max(h,realH))];
108− }
109−
110− function getSize(e) {
111− var t = e.cloneNode(true);
112−
113− t.style.visibility = "hidden";
114− t.style.styleFloat = "left";
115− t.style.cssFloat = "left";
116−
117− document.body.appendChild(t);
118− var w = t.offsetWidth;
119− var h = t.offsetHeight;
120− document.body.removeChild(t);
121− //delete t;
122− return [w,h];
123− }
124−
125− function getExcess(e) {
126− var t = e.cloneNode(true);
127−
128− t.style.visibility = "hidden";
129− t.style.styleFloat = "left";
130− t.style.cssFloat = "left";
131−
132− document.body.appendChild(t);
133− var ow = t.offsetWidth;
134− var oh = t.offsetHeight;
135− var cStyle = window.getComputedStyle(t,null);
136− var w = cStyle.getPropertyValue("width").slice(0,-2) - 0;
137− var h = cStyle.getPropertyValue("height").slice(0,-2) - 0;
138− document.body.removeChild(t);
139− //delete t;
140− return [ow-w,oh-h];
141− }
142−
143−
144− function groupForms(forms) {
145− forms = Elm.JavaScript.castListToJSArray(forms);
146− var groups = [];
147− var arr = [];
148− for (var i = forms.length; i--; ) {
149− var f = forms[i];
150− switch(f[4][0]) {
151− case "FElement":
152− if (arr.length > 0) {
153− groups.push(arr);
154− arr = [];
155− }
156− groups.push(f);
157− break;
158− default:
159− arr.push(f);
160− }
161− }
162− if (arr.length > 0) groups.push(arr);
163− return groups;
164− }
165−
166− var toString = function(v) {
167− if (typeof v === "function") {
168− return "<function>";
169− } else if (typeof v === "boolean") {
170− return v ? "True" : "False";
171− } else if (typeof v === "number") {
172− return v+"";
173− } else if (typeof v === "string" && v.length < 2) {
174− return "'"+v+"'";
175− } else if (typeof v === "object" && ('_' in v)) {
176− var output = [];
177− for (var k in v._) {
178− console.log(k,v._[k]);
179− for (var i = v._[k].length; i--; ) {
180− output.push(k + " = " + toString(v._[k][i]));
181− }
182− }
183− for (var k in v) {
184− if (k === '_') continue;
185− output.push(k + " = " + toString(v[k]));
186− }
187− if (output.length === 0) return "{}";
188− return "{ " + output.join(", ") + " }";
189− } else if (v[0]) {
190− if (v[0].substring(0,5) === "Tuple") {
191− var output = new Array(v.length-1);
192− for (var i = v.length; --i; ) { output[i-1] = toString(v[i]); }
193− return "(" + output.join(",") + ")";
194− } else if (v[0] === "Cons") {
195− var start = (typeof v[1] === "string") ? '"' : "[";
196− var end = (typeof v[1] === "string") ? '"' : "]";
197− var div = (typeof v[1] === "string") ? "" : ",";
198− var f = (typeof v[1] === "string") ? function(x){return x} : toString;
199− var output = start + f(v[1]);
200− v = v[2];
201− while (true) {
202− if (v[0] === "Cons") {
203− output += div + f(v[1]);
204− v = v[2];
205− } else {
206− return output + end;
207− }
208− }
209− } else if (v[0] === "Nil") {
210− return "[]";
211− } else if (v[0] === "JSON") {
212− return "(JSON.fromList " + toString(Elm.JSON.toList(v)) + ")";
213− } else if (v[0] === "RBNode" || v[0] === "RBEmpty") {
214− function cons(k){ return function(v) { return function(acc) { return ["Cons",["Tuple2",k,v],acc]; }; }; }
215− var list = Elm.Dict.foldr(cons)(["Nil"])(v);
216− var name = "Dict";
217− if (list[0] === "Cons" && list[1][2][0] === "Tuple0") {
218− name = "Set";
219− list = Elm.List.map(function(x) { return x[1]; })(list);
220− }
221− return "(" + name + ".fromList " + toString(list) + ")";
222− } else {
223− var output = "";
224− for (var i = v.length; --i; ) { output = ' ' + toString(v[i]) + output; }
225− output = v[0] + output;
226− return (v.length > 1) ? "(" + output + ")" : output;
227− }
228− }
229− return v+"";
230− };
231− var show = function(v) { return str(toString(v)); };
232− var append = function(xs,ys) {
233− if (typeof xs === "string" && typeof ys === "string") {
234− return xs.concat(ys);
235− }
236− if (xs[0] === "Nil") {
237− return ys;
238− }
239− var root = ["Cons", xs[1], ["Nil"]];
240− var curr = root;
241− xs = xs[2];
242− while (xs[0]==="Cons") {
243− curr[2] = ["Cons", xs[1], ["Nil"]];
244− xs = xs[2];
245− curr = curr[2];
246− }
247− curr[2] = ys;
248− return root;
249− };
250−
251− var str = function(s) {
252− var out = ["Nil"];
253− for (var i = s.length; i--; ) {
254− out = ["Cons", s[i], out];
255− }
256− return out;
257− };
258−
259− function wrap(elem) {
260− var p = Value.getSize(elem);
261− return ["Element", Guid.guid(), ["EHtml",elem],
262− p[0], p[1], 1, ["Nothing"], ["Nothing"]];
263− }
264− var addListener = function() {
265− if(document.addEventListener) {
266− return function(element, event, handler) {
267− element.addEventListener(event, handler, false);
268− };
269− } else {
270− return function(element, event, handler) {
271− element.attachEvent('on' + event, handler);
272− };
273− }
274− }();
275−
276− return {eq:eq,
277− str:str,
278− show:show,
279− Tuple:Tuple,
280− append:append,
281− listToArray:listToArray,
282− toText : toText,
283− properEscape : properEscape,
284− getTextSize : getTextSize,
285− getSize : getSize,
286− getExcess : getExcess,
287− groupForms : groupForms,
288− wrap : wrap,
289− addListener : addListener
290− };
291−}();
core-js/cat.batdeleted−5
@@ -1,5 +0,0 @@
1−copy /B Guid.js+foreign\JavaScript.js+foreign\JSON.js+Value.js+List.js+Maybe.js+Either.js+Char.js+Graphics\Color.js+Graphics\Collage.js+Graphics\Element.js+Text.js+Graphics\Render.js+runtime\Signal.js+runtime\Dispatcher.js+Signal\HTTP.js+Signal\WebSocket.js+Signal\Input.js+Signal\Keyboard.js+Signal\Mouse.js+Signal\Random.js+Signal\Time.js+Signal\Window.js+Date.js+Prelude.js+Signal\Touch.js+Dict.js+Set.js+Automaton.js ..\elm-mini.js
2−
3−cd ..\elm
4−
5−copy /B ..\elm-mini.js elm-runtime-0.7.2.js
core-js/cat.shdeleted−33
@@ -1,33 +0,0 @@
1−# I do not use this script, so it may be out of date.
2−# Please make sure that this matches with cat.bat to
3−# avoid confusing "errors".
4−
5−cat \
6− Guid.js\
7− foreign/JavaScript.js\
8− List.js\
9− Maybe.js\
10− foreign/JSON.js\
11− Value.js\
12− Char.js\
13− Graphics/Color.js\
14− Graphics/Collage.js\
15− Graphics/Element.js\
16− Text.js\
17− Graphics/Render.js\
18− runtime/Signal.js\
19− runtime/Dispatcher.js\
20− Signal/HTTP.js\
21− Signal/Input.js\
22− Signal/Keyboard.js\
23− Signal/Mouse.js\
24− Signal/Random.js\
25− Signal/Time.js\
26− Signal/Window.js\
27− Date.js\
28− Prelude.js\
29− Dict.js\
30− Set.js\
31− Automaton.js\
32− Signal/WebSocket.js\
33− > ../elm/elm-runtime.js
core-js/collage/Color.jsdeleted−42
@@ -1,42 +0,0 @@
1−
2−var Color = function() {
3−
4− var create = function(r,g,b,a) {
5− return { r: r,
6− g: g,
7− b: b,
8− a: a };
9− };
10−
11− var extract = function(c) {
12− if (c.a === 1) {
13− return 'rgb(' + c.r + ',' + c.g + ',' + c.b + ')';
14− }
15− return 'rgba(' + c.r + ',' + c.g + ',' + c.b + ',' + c.a + ')';
16− };
17−
18− var rgba = function(r) { return function(g) { return function(b) {
19− return function(a) { return create(r,g,b,a); }; }; };
20− };
21−
22− var rgb = function(r) { return function(g) { return function(b) {
23− return create(r,g,b,1); }; };
24− };
25− return {black: create( 0, 0, 0,1),
26− white: create(255,255,255,1),
27− red : create(255, 0, 0,1),
28− green: create( 0,255, 0,1),
29− blue : create( 0, 0,255,1),
30−
31− gray : create(128,128,128,1),
32− grey : create(128,128,128,1),
33−
34− yellow : create(255,255, 0,1),
35− cyan : create( 0,255,255,1),
36− magenta : create(255, 0,255,1),
37−
38− rgba : rgba,
39− rgb : rgb,
40− Internal : { extract:extract }
41− };
42−}();
core-js/collage/Form.jsdeleted−33
@@ -1,33 +0,0 @@
1−
2−var Form = function() {
3− var move = function(x) { return function(y) { return function(form) {
4− var t = form[1];
5− return [form[0], [[x + t[0][0], y + t[0][1]], t[1], t[2]]];
6− };
7− };
8− };
9− var rotate = function(theta) { return function(form) {
10− var t = form[1];
11− return [form[0], [t[0], t[1] + 2* Math.PI*theta, t[2]]];
12− };
13− };
14− var scale = function(s) { return function(form) {
15− var t = form[1];
16− return [form[0], [t[0], t[1], t[2] * s]];
17− };
18− };
19− var create = function(howToDraw, center) {
20− return [howToDraw, Transforms.create(center, 0, 1)];
21− };
22− var draw = function(form) {
23− ctx.save();
24− var trans = form[1];
25− ctx.translate(trans[0][0], trans[0][1]);
26− ctx.rotate(trans[1]);
27− ctx.scale(trans[2], trans[2]);
28− form[0](ctx);
29− ctx.restore();
30− return ctx;
31− };
32− return {create:create, move:move, rotate:rotate, scale:scale, draw:draw};
33−}();
core-js/collage/Image.jsdeleted−9
@@ -1,9 +0,0 @@
1−
2−var Image = function() {
3− var image = function(src) {
4− var img = new Image(src);
5− img.onload = function() {
6−
7− };
8− };
9−}();
core-js/collage/Line.jsdeleted−103
@@ -1,103 +0,0 @@
1−
2−var Line = function() {
3−
4− var pair = function(a,b) { return [a,b]; };
5−
6− var create = function(center, ps, theta, s) {
7− return { center: center, points: ps, theta: theta, scale: s };
8− };
9−
10−
11− //// Construction ////
12−
13− var line = function(ps) {
14− var parr = [];
15− while (ps[0] === "Cons") {
16− parr.push(pair(ps[1][1], ps[1][2]));
17− ps = ps[2];
18− }
19− return create(pair(0,0), parr, 0, 1);
20− };
21−
22− //// Atomize ////
23−
24− var solid = function(color) { return function(line) { return function(ctx) {
25− ctx.save();
26− ctx.beginPath();
27− ctx.translate(line.center[0], line.center[1]);
28− ctx.rotate(line.theta);
29− ctx.scale(line.scale, line.scale);
30− var points = line.points;
31− var i = points.length;
32− ctx.moveTo(points[i-1][0], points[i-1][1]);
33− while (i--) {
34− ctx.lineTo(points[i][0], points[i][1]);
35− }
36− ctx.strokeStyle = Color.Internal.extract(color);
37− ctx.stroke();
38− ctx.restore();
39− return ctx;
40− };
41− };
42− };
43−
44− var customLine = function(pattern) {
45− return function(color) { return function(line) {
46− if (typeof pattern[0] === "string") {
47− var temp = [];
48− while (pattern[0] === "Cons") {
49− temp.push(pattern[1]);
50− pattern = pattern[2];
51− }
52− pattern = temp;
53− }
54− if (pattern.length === 0) { pattern = [8,4]; }
55− return function(ctx) {
56− ctx.save();
57− ctx.beginPath();
58− ctx.translate(line.center[0], line.center[1]);
59− ctx.rotate(line.theta);
60− ctx.scale(line.scale, line.scale);
61− customLineHelp(ctx, pattern, line.points);
62− ctx.strokeStyle = Color.Internal.extract(color);
63− ctx.stroke();
64− ctx.restore();
65− return ctx;
66− };
67− };
68− };
69− };
70− var customLineHelp = function(ctx, pattern, points) {
71− var i = points.length - 1;
72− var x0 = points[i][0], y0 = points[i][1];
73− var x1=0, y1=0, dx=0, dy=0, remaining=0, nx=0, ny=0;
74− var pindex = 0, plen = pattern.length;
75− var draw = true, segmentLength = pattern[0];
76− ctx.moveTo(x0,y0);
77− while (i--) {
78− x1 = points[i][0]; y1 = points[i][1];
79− dx = x1 - x0; dy = y1 - y0;
80− remaining = Math.sqrt(dx * dx + dy * dy);
81− while (segmentLength <= remaining) {
82− x0 += dx * segmentLength / remaining;
83− y0 += dy * segmentLength / remaining;
84− ctx[draw ? 'lineTo' : 'moveTo'](x0, y0);
85− // update starting position
86− dx = x1 - x0; dy = y1 - y0;
87− remaining = Math.sqrt(dx * dx + dy * dy);
88− // update pattern
89− draw = !draw;
90− pindex = (pindex + 1) % plen;
91− segmentLength = pattern[pindex];
92− }
93− if (remaining > 0) {
94− ctx[draw ? 'lineTo' : 'moveTo'](x1, y1);
95− segmentLength -= remaining;
96− }
97− x0 = x1; y0 = y1;
98− }
99− };
100−
101− return {line:line, customLine:customLine, solid:solid,
102− dashed: customLine([8,4]), dotted: customLine([3,3]) };
103−}();
core-js/collage/Shape.jsdeleted−110
@@ -1,110 +0,0 @@
1−
2−var Shape = function() {
3−
4− var create = function(center, ps, theta, s) {
5− return { center: center, points: ps, theta: theta, scale: s };
6− };
7−
8− //// Construction ////
9−
10− var polygon = function(ps) { return function(center) {
11− var parr = [];
12− while (ps[0] === "Cons") {
13− parr.push([ps[1][1], ps[1][2]]);
14− ps = ps[2];
15− }
16− center = [center[1], center[2]];
17− return create(center, parr, 0, 1);
18− };
19−};
20− var ngon = function(n) { return function(r) { return function(center) {
21− var ps = [];
22− for (var i = n; i--;) {
23− ps.push([r * Math.cos(Math.PI * 2 * i/n),
24− r * Math.sin(Math.PI * 2 * i/n)]);
25− }
26− center = [center[1], center[2]];
27− return create(center, ps, 0, 1);
28− };
29− };
30−};
31− var rect = function(w) { return function(h) { return function(center) {
32− var ps = [[- w/2, - h/2],
33− [ w/2, - h/2],
34− [ w/2, h/2],
35− [- w/2, h/2]];
36− center = [center[1], center[2]];
37− return create(center, ps, 0, 1);
38− };
39− };
40− };
41− var oval = function(w) { return function(h) { return function(center) {
42− var ps = [];
43− for (var theta = 2 * Math.PI; theta > 0; theta -= Math.PI /50) {
44− ps.push([w/2 * Math.cos(theta), h/2 * Math.sin(theta)]);
45− }
46− center = [center[1], center[2]];
47− return create(center, ps, 0, 1);
48− };
49− };
50− };
51−
52−//// Transforms ////
53−
54− var move = function(x) { return function(y) { return function(shape) {
55− var newCenter = [x + shape.center[0],y + shape.center[1]];
56− return create(newCenter, shape.points, shape.theta, shape.scale);
57− };
58− };
59− };
60− var rotate = function(theta) { return function(shape) {
61− var newTheta = shape.theta + 2 * Math.PI * theta;
62− return create(shape.center, shape.points, newTheta, shape.scale);
63− };
64− };
65− var scale = function(s) { return function(shape) {
66− return create(shape.center, shape.points, shape.theta, shape.scale * s);
67− };
68− };
69−
70−
71− //// Atomize ////
72−
73− var draw = function(fill) {
74− return function(color) { return function(shape) { return function(ctx) {
75− ctx.save();
76− ctx.translate(shape.center[0], shape.center[1]);
77− ctx.rotate(shape.theta);
78− ctx.scale(shape.scale, shape.scale);
79− ctx.beginPath();
80− var points = shape.points;
81− ctx.moveTo(points[0][0], points[0][1]);
82− for (var i = points.length; i--; ) {
83− ctx.lineTo(points[i][0], points[i][1]);
84− }
85− ctx.closePath();
86− if (fill) {
87− ctx.fillStyle = Color.Internal.extract(color);
88− ctx.fill();
89− } else {
90− ctx.strokeStyle = Color.Internal.extract(color);
91− ctx.stroke();
92− }
93− ctx.restore();
94− return ctx;
95− };
96− };
97− };
98− };
99−
100− var customOutline = function(p) {
101− return function(c) { return function(shape) {
102− shape.points.push(shape.points[0]);
103− return Line.customLine(p)(c)(shape);
104− };
105− };
106− };
107− return {polygon:polygon, ngon:ngon, rect:rect, oval:oval,
108− move:move, rotate:rotate, scale:scale,
109− filled:draw(true), outlined:draw(false), customOutline:customOutline };
110−}();
core-js/foreign/JSON.jsdeleted−158
@@ -1,158 +0,0 @@
1−
2−var JSjson = window.JSON;
3−Elm.JSON = function() {
4− var JS = Elm.JavaScript;
5− var empty = ['JSON',{}];
6− function singleton(k) { return function(v) {
7− var obj = {};
8− obj[JS.castStringToJSString(k)] = v;
9− return ['JSON', obj ];
10− };
11− }
12− function insert(k) { return function(v) { return function(inObj) {
13− var obj = inObj[1];
14− var outObj = {};
15− for (var i in obj) {
16− outObj[i] = obj[i];
17− }
18− outObj[JS.castStringToJSString(k)] = v;
19− return ['JSON', outObj ];
20− };
21− };
22− }
23−
24− function lookup(key) { return function(obj) {
25− var k = JS.castStringToJSString(key);
26− return (k in obj[1]) ? ["Just", obj[1][k]] : ["Nothing"] ;
27− };
28− }
29− function find(tipe,base) { return function (key) { return function(obj) {
30− var k = JS.castStringToJSString(key);
31− if (k in obj[1]) {
32− var v = obj[1][k];
33− if (v[0] === tipe) { return v[1]; }
34− }
35− return base;
36− };
37− }
38− }
39− function lookupWithDefault(base) { return function(key) { return function(obj) {
40− var k = JS.castStringToJSString(key);
41− return (k in obj[1]) ? obj[1][k] : base ;
42− };
43− };
44− }
45−
46− function remove(k) { return function(inObj) {
47− var obj = inObj[1];
48− var outObj = {};
49− for (var i in obj) {
50− outObj[i] = obj[i];
51− }
52− delete outObj[JS.castStringToJSString(k)];
53− return ['JSON', outObj];
54− };
55− }
56−
57− function JsonString(v) { return [ "JsonString", v ]; }
58− function JsonNumber(v) { return [ "JsonNumber", v ]; }
59− function JsonBool(v) { return [ "JsonBool", v ]; }
60− var JsonNull = [ "JsonNull" ];
61− function JsonArray(v) { return [ "JsonArray", v ]; }
62− function JsonObject(v) { return [ "JsonObject", v ]; }
63−
64− function toList(json) {
65− var obj = json[1];
66− var arr = [];
67− for (var i in obj) {
68− arr.push(Value.Tuple(JS.castJSStringToString(i), obj[i]));
69− }
70− return JS.castJSArrayToList(arr);
71− }
72− function fromList(list) {
73− var arr = JS.castListToJSArray(list);
74− var obj = {};
75− for (var i = arr.length; i--; ) {
76− obj[JS.castStringToJSString(arr[i][1])] = arr[i][2];
77− }
78− return [ "JSON", obj ];
79− }
80−
81− function toPrettyJSString(sep) { return function (obj) {
82− function fromValue(v) {
83− switch (v[0]) {
84− case 'JsonNull' : return null;
85− case 'JsonString' : return JS.castStringToJSString(v[1]);
86− case 'JsonObject' :
87− var o = {};
88− var from = v[1][1];
89− for (var i in from) {
90− o[i] = fromValue(from[i]);
91− }
92− return o;
93− case 'JsonArray' :
94− var a = JS.castListToJSArray(v[1]);
95− for (var i = a.length; i--; ) {
96− a[i] = fromValue(a[i]);
97− }
98− return a;
99− default :
100− return v[1];
101− }
102− }
103− return JSjson.stringify(fromValue([ 'JsonObject', obj ]), null, JS.castStringToJSString(sep));
104− };
105− }
106− function fromJSString(str) {
107− var obj;
108− try {
109− obj = JSjson.parse(str);
110− } catch (e) {
111− return Elm.Maybe.Nothing;
112− }
113− function toValue(v) {
114− switch (typeof v) {
115− case 'string' : return [ "JsonString", JS.castJSStringToString(v) ];
116− case 'number' : return [ "JsonNumber", JS.castJSNumberToFloat(v) ];
117− case 'boolean' : return [ "JsonBool", JS.castJSBoolToBool(v) ];
118− case 'object' :
119− if (v === null) return [ "JsonNull" ];
120− for (var i in v) {
121− v[i] = toValue(v[i]);
122− }
123− if (v instanceof Array) return [ "JsonArray", JS.castJSArrayToList(v) ];
124− return [ "JsonObject", [ "JSON", v ] ];
125− }
126− }
127− for (var i in obj) {
128− obj[i] = toValue(obj[i]);
129− }
130− return Elm.Maybe.Just( ['JSON',obj] );
131− }
132− return {empty : empty,
133− singleton : singleton,
134− insert : insert,
135− lookup : lookup,
136− findNumber : find("JsonNumber",0),
137− findString : find("JsonString",["Nil"]),
138− findObject : find("JsonObject", empty ),
139− findArray : find("JsonArray" ,["Nil"]),
140− findWithDefault : lookupWithDefault,
141− remove : remove,
142− toPrettyJSString : toPrettyJSString,
143− toJSString : toPrettyJSString(''),
144− fromJSString : fromJSString,
145− toPrettyString : function(sep) { return function(v) {
146− return JS.castJSStringToString(toPrettyJSString(sep)(v)); }; },
147− toString : function(v) { return JS.castJSStringToString(toPrettyJSString('')(v)); },
148− fromString : function(v) { return fromJSString(JS.castStringToJSString(v)); },
149− toList : toList,
150− fromList : fromList,
151− JsonString : JsonString,
152− JsonNumber : JsonNumber,
153− JsonBool : JsonBool,
154− JsonNull : JsonNull,
155− JsonArray : JsonArray,
156− JsonObject : JsonObject
157− };
158−}();
core-js/foreign/JavaScript.jsdeleted−69
@@ -1,69 +0,0 @@
1−
2−Elm.JavaScript = function() {
3− function castJSBoolToBool(b) { return b; }
4− function castBoolToJSBool(b) { return b; }
5−
6− function castJSNumberToFloat(n) { return n; }
7− function castFloatToJSNumber(n) { return n; }
8−
9− function castJSNumberToInt(n) { return ~~n; }
10− function castIntToJSNumber(n) { return n; }
11−
12− function castJSElementToElement(w) {
13− return function(h) {
14− return function(node) {
15− return ["Element",Guid.guid(),
16− ["EExternalHtml",node],
17− w,h,1,["Nothing"],["Nothing"]];
18− }
19− }
20− }
21− function castElementToJSElement(elem) { return Render.render(elem); }
22−
23− function castJSArrayToList(arr) {
24− var list = ["Nil"];
25− for (var i = arr.length; i--; ) {
26− list = [ "Cons", arr[i], list ];
27− }
28− return list;
29− }
30− function castListToJSArray(list) {
31− var a = [];
32− while (list[0] === "Cons") {
33− a.push(list[1]);
34− list = list[2];
35− }
36− return a;
37− }
38−
39− var castJSStringToString = castJSArrayToList;
40− function castStringToJSString(str) {
41− if (typeof str === "string") return str;
42− return castListToJSArray(str).join('');
43− }
44−
45− function fromTuple(t) { return t.slice(1); }
46− function toTuple(a) { return ["Tuple" + a.length].concat(a); }
47−
48− return {castJSBoolToBool:castJSBoolToBool,
49− castBoolToJSBool:castBoolToJSBool,
50− castJSNumberToFloat:castJSNumberToFloat,
51− castFloatToJSNumber:castFloatToJSNumber,
52− castJSNumberToInt:castJSNumberToInt,
53− castIntToJSNumber:castIntToJSNumber,
54− Experimental : {castJSElementToElement:castJSElementToElement,
55− castElementToJSElement:castElementToJSElement},
56− castJSArrayToList:castJSArrayToList,
57− castListToJSArray:castListToJSArray,
58− castJSStringToString:castJSStringToString,
59− castStringToJSString:castStringToJSString,
60− castTupleToJSTuple2:fromTuple,
61− castTupleToJSTuple3:fromTuple,
62− castTupleToJSTuple4:fromTuple,
63− castTupleToJSTuple5:fromTuple,
64− castJSTupleToTuple2:toTuple,
65− castJSTupleToTuple3:toTuple,
66− castJSTupleToTuple4:toTuple,
67− castJSTupleToTuple5:toTuple
68− };
69−}();
core-js/runtime/Dispatcher.jsdeleted−58
@@ -1,58 +0,0 @@
1−
2−var Dispatcher = function() {
3− var program = null;
4− var inputs = [];
5− var currentElement = null;
6−
7− var initialize = function() {
8− program = Elm.main();
9− if (!('recv' in program)) {
10− program = Elm.Signal.constant(program);
11− }
12−
13− currentElement = program.value;
14− filterDeadInputs();
15−
16− var content = document.getElementById('content');
17− content.appendChild(Render.render(currentElement));
18− var w = document.getElementById('widthChecker').offsetWidth;
19− if (w !== window.innerWidth) {
20− Dispatcher.notify(Elm.Window.dimensions.id, Value.Tuple(w, window.innerHeight));
21− }
22− program = Elm.Signal.lift(function(value) {
23− var content = document.getElementById('content');
24− Render.update(content.firstChild,currentElement,value);
25− currentElement = value;
26− return value;
27− })(program);
28− };
29− var notify = function(id, v) {
30− var timestep = (new window.Date).getTime();
31− var hasListener = false;
32− for (var i = inputs.length; i--; ) {
33− hasListener = inputs[i].recv(timestep, id, v) || hasListener;
34− }
35− return hasListener;
36− };
37−
38− function isAlive(input) {
39− if (!('defaultNumberOfKids' in input)) return true;
40− var len = input.kids.length;
41− if (len == 0) return false;
42− if (len > input.defaultNumberOfKids) return true;
43− var alive = false;
44− for (var i = len; i--; ) {
45− alive = alive || isAlive(input.kids[i]);
46− }
47− return alive;
48− }
49− function filterDeadInputs() {
50− var temp = [];
51− for (var i = inputs.length; i--; ) {
52− if (isAlive(inputs[i])) temp.push(inputs[i]);
53− }
54− inputs = temp;
55− }
56−
57− return {initialize:initialize, notify:notify, inputs:inputs};
58−}();
core-js/runtime/Signal.jsdeleted−260
@@ -1,260 +0,0 @@
1−
2−Elm.Signal = function() {
3− var send = function(node, timestep, changed) {
4− var kids = node.kids;
5− for (var i = kids.length; i--; ) {
6− kids[i].recv(timestep, changed, node.id);
7− }
8− };
9− function input(base) {
10− this.id = Guid.guid();
11− this.value = base;
12− this.kids = [];
13− this.defaultNumberOfKids = 0;
14− this.recv = function(timestep, eid, v) {
15− var changed = eid === this.id;
16− if (changed) { this.value = v; }
17− send(this, timestep, changed);
18− return changed;
19− };
20− Dispatcher.inputs.push(this);
21− };
22− function lift(func,args) {
23− this.id = Guid.guid();
24− this.value = null;
25− this.kids = [];
26− this.count = 0;
27− this.changed = false;
28−
29− args.reverse();
30− this.recalc = function() {
31− var f = func;
32− for (var i = args.length; i--; ) {
33− f = f(args[i].value);
34− }
35− this.value = f;
36− };
37− this.recalc();
38−
39− this.recv = function(timestep, changed, parentID) {
40− this.count += 1;
41− if (changed) { this.changed = true; }
42− if (this.count == args.length) {
43− if (this.changed) { this.recalc() }
44− send(this, timestep, this.changed);
45− this.changed = false;
46− this.count = 0;
47− }
48− };
49− for (var i = args.length; i--; ) {
50− args[i].kids.push(this);
51− }
52− };
53− function fold(func,base,baseIsFunc,input) {
54− this.id = Guid.guid();
55− this.value = baseIsFunc ? base(input.value) : base;
56− this.kids = [];
57− this.recv = function(timestep, changed, parentID) {
58− if (changed) { this.value = func(input.value)(this.value); }
59− send(this, timestep, changed);
60− };
61− input.kids.push(this);
62− };
63−
64− function dropIf(pred,base,input) {
65− this.id = Guid.guid();
66− this.value = pred(input.value) ? base : input.value;
67− this.kids = [];
68− this.recv = function(timestep, changed, parentID) {
69− var chng = changed && !pred(input.value);
70− if (chng) { this.value = input.value; }
71− send(this, timestep, chng);
72− };
73− input.kids.push(this);
74− };
75−
76− function dropRepeats(input) {
77− this.id = Guid.guid();
78− this.value = input.value;
79− this.kids = [];
80− this.recv = function(timestep, changed, parentID) {
81− var chng = changed && !Value.eq(this.value,input.value);
82− if (chng) { this.value = input.value; }
83− send(this, timestep, chng);
84− };
85− input.kids.push(this);
86− };
87−
88− var dropWhen = function(s1) { return function(b) { return function(s2) {
89− var pairs = new lift(function(x){return function(y){return [x,y];};},[s1,s2]);
90− var dropped = new dropIf(function(p){return p[0];},[true,b],pairs);
91− return new lift(function(p){return p[1];},[dropped]); }; };
92− };
93−
94− function timeIndex(pair,s) {
95− this.id = Guid.guid();
96− var t = (new window.Date).getTime();
97− this.value = pair ? Value.Tuple(t,s.value) : t;
98− this.kids = [];
99− this.recv = function(timestep, changed, parentID) {
100− if (changed) this.value = pair ? Value.Tuple(timestep, s.value) : timestep;
101− send(this, timestep, changed);
102− };
103− s.kids.push(this);
104− }
105−
106− function sampleOn(s1,s2) {
107− this.id = Guid.guid();
108− this.value = s2.value;
109− this.kids = [];
110− this.count = 0;
111− this.changed = false;
112−
113− this.recv = function(timestep, changed, parentID) {
114− if (parentID === s1.id) this.changed = changed;
115− this.count += 1;
116− if (this.count == 2) {
117− if (this.changed) { this.value = s2.value; }
118− send(this, timestep, this.changed);
119− this.count = 0;
120− this.changed = false;
121− }
122− };
123− s1.kids.push(this);
124− s2.kids.push(this);
125− };
126−
127− function delay(t) { return function(s) {
128− var delayed = new input(s.value);
129− var firstEvent = true;
130− function update(v) {
131− if (firstEvent) return;
132− setTimeout(function() { Dispatcher.notify(delayed.id,v); },t);
133− }
134− function first(a) { return function(b) { return a; }; }
135− var out = new sampleOn(delayed,new lift(first, [delayed, new lift(update,[s])]));
136− firstEvent = false;
137− return out;
138− };
139− }
140−
141− function merge(s1,s2) {
142− this.id = Guid.guid();
143− this.value = s1.value;
144− this.kids = [];
145− this.next = null;
146− this.count = 0;
147− this.changed = false;
148−
149− this.recv = function(timestep, changed, parentID) {
150− this.count += 1;
151− if (changed) {
152− this.changed = true;
153− if (parentID == s2.id && this.next === null) { this.next = s2.value; }
154− if (parentID == s1.id) { this.next = s1.value; }
155− }
156−
157− if (this.count == 2) {
158− if (this.changed) {
159− this.value = this.next;
160− this.next = null;
161− }
162− send(this, timestep, this.changed);
163− this.changed = false;
164− this.count = 0;
165− }
166− };
167− s1.kids.push(this);
168− s2.kids.push(this);
169− };
170−
171− function merges(ss) {
172− function mrg(x) { return function(y) { return new merge(x,y); }; }
173− return Elm.List.foldl1(mrg)(ss);
174− }
175−
176− function mergeEither(s1) { return function(s2) {
177− function f(s) { return function(x) { return [s,x]; }; }
178− return new merge(new lift(f('Left'),[s1]), new lift(f('Right'),[s2]));
179− };
180− }
181−
182− function average(sampleSize) { return function(s) {
183− var sample = new Array(sampleSize);
184− var i = sampleSize;
185− while (i--) sample[i] = 0;
186− i = 0;
187− var full = false;
188− var total = 0;
189− function f(n) {
190− total += n - sample[i];
191− sample[i] = n;
192− var avg = total / Math.max(1, full ? sampleSize : i);
193− if (++i == sampleSize) { full = true; i = 0; }
194− return avg;
195− }
196− return new lift(f, [s]);
197− };
198− }
199−
200− return {
201− constant : function(v) { return new input(v); },
202− lift : function(f){return function(e){return new lift(f,[e]);};},
203− lift2 : function(f) {
204− return function(e1) { return function(e2) {
205− return new lift(f, [e1,e2]); };};},
206− lift3 : function(f) {
207− return function(e1) { return function(e2) {
208− return function(e3){return new lift(f,[e1,e2,e3]);};};};},
209− lift4 : function(f) {
210− return function(e1) { return function(e2) {
211− return function(e3) { return function(e4) {
212− return new lift(f, [e1,e2,e3,e4]);};};};};},
213− lift5 : function(f) {
214− return function(e1) { return function(e2) {
215− return function(e3) { return function(e4) {
216− return function(e5) {
217− return new lift(f, [e1,e2,e3,e4,e5]);};};};};};},
218− lift6 : function(f) { return function(e1) { return function(e2) {
219− return function(e3) { return function(e4) {
220− return function(e5) { return function(e6) {
221− return new lift(f, [e1,e2,e3,e4,e5,e6]); };};};};};};},
222− lift7 : function(f) { return function(e1) { return function(e2) {
223− return function(e3) { return function(e4) {
224− return function(e5) { return function(e6) {
225− return function(e7) {
226− return new lift(f, [e1,e2,e3,e4,e5,e6,e7]);};};};};};};};},
227− lift8 : function(f) { return function(e1) { return function(e2) {
228− return function(e3) { return function(e4) {
229− return function(e5) { return function(e6) {
230− return function(e7) { return function(e8) {
231− return new lift(f, [e1,e2,e3,e4,e5,e6,e7,e8]);};};};};};};};};},
232− foldp : function(f) { return function(b) { return function(e) {
233− return new fold(f,b,false,e); }; }; },
234− foldp$ : function(f) { return function(b) { return function(e) {
235− return new fold(f,b,true,e); }; }; },
236− foldp1 : function(f) { return function(e) {
237− return new fold(f,function(x){return x;},true,e); }; },
238− delay : delay,
239− merge : function(s1) { return function(s2) { return new merge(s1,s2)}; },
240− merges : merges,
241− mergeEither : mergeEither,
242− average : average,
243− count : function(sig) {
244− var incr = function(_){return function(c){return c+1;};};
245− return new fold(incr,0,false,sig) },
246− countIf : function(pred) { return function(sig) {
247− var incr = function(x){return function(c){return pred(x) ? c+1 : c;};};
248− return new fold(incr,0,false,sig) }; },
249− keepIf : function(pred) { return function(base) { return function(sig) {
250− return new dropIf(function(x) { return !pred(x)},base,sig); }; }; },
251− dropIf : function(pred) { return function(base) { return function(sig) {
252− return new dropIf(pred,base,sig); }; }; },
253− keepWhen : function(s) { return dropWhen(new lift(function(b){return !b;},[s])); },
254− dropWhen : dropWhen,
255− dropRepeats : function(s) { return new dropRepeats(s);},
256− sampleOn : function(s1){return function(s2){return new sampleOn(s1,s2);};},
257− timestamp : function(s) { return new timeIndex(true, s); },
258− timeOf : function(s) { return new timeIndex(false, s); }
259− };
260−}();
core/Automaton.elmdeleted−79
@@ -1,79 +0,0 @@
1−
2−module Automaton where
3−
4−data Automaton a b = Automaton (a -> (b, Automaton a b))
5−
6−{--- API possibilies: All names and types are up for debate!
7−(^>>) :: (a -> b) -> Automaton b c -> Automaton a c
8−(>>^) :: Automaton a b -> (b -> c) -> Automaton a c
9−(^<<) :: (b -> c) -> Automaton a b -> Automaton a c
10−(<<^) :: Automaton b c -> (a -> b) -> Automaton a c
11−--}
12−
13−
14−run : Automaton a b -> Signal a -> Signal b
15−run (Automaton m0) input =
16− lift fst $ foldp' (\a (b, Automaton m) -> m a) m0 input
17−
18−step : Automaton a b -> a -> (b, Automaton a b)
19−step (Automaton m) a = m a
20−
21−
22−(>>>) : Automaton a b -> Automaton b c -> Automaton a c
23−a1 >>> a2 =
24− let Automaton m1 = a1
25− Automaton m2 = a2
26− in Automaton (\a -> let (b,m1') = m1 a
27− (c,m2') = m2 b
28− in (c, m1' >>> m2'))
29−
30−(<<<) : Automaton b c -> Automaton a b -> Automaton a c
31−a2 <<< a1 = a1 >>> a2
32−
33−combine : [Automaton a b] -> Automaton a [b]
34−combine autos =
35− Automaton (\a -> let (bs,autos') = unzip $ map (\(Automaton m) -> m a) autos in
36− (bs, combine autos'))
37−
38−pure : (a -> b) -> Automaton a b
39−pure f = Automaton (\x -> (f x, pure f))
40−
41−init : b -> (a -> b -> b) -> Automaton a b
42−init s step = Automaton (\a -> let s' = step a s in (s', init s' step))
43−
44−init' : s -> (a -> s -> (b,s)) -> Automaton a b
45−init' s step = Automaton (\a -> let (b,s') = step a s in (b , init' s' step))
46−
47−count : Automaton a Int
48−count = init 0 (\_ c -> c + 1)
49−
50−
51−data DragState = Listen | Ignore | DragFrom (Int,Int)
52−
53−vecSub (x1,y1) (x2,y2) = (x1-x2,y1-y2)
54−
55−stepDrag (press,pos) (ds,form) =
56− let wrap ds' = (form, (ds',form)) in
57− case ds of
58− Listen -> wrap (if | not press -> Listen
59− | pos `isWithin` form -> DragFrom pos
60− | otherwise -> Ignore)
61− Ignore -> wrap (if press then Ignore else Listen)
62− DragFrom p0 ->
63− if press then (uncurry move (vecSub pos p0) form, (DragFrom p0, form))
64− else (let form' = uncurry move (vecSub pos p0) form in
65− (form', (Listen,form')))
66−
67−draggable : Form -> Automaton (Bool,(Int,Int)) Form
68−draggable form = init' (Listen,form) stepDrag
69−
70−
71−{--- See the following papers for ideas on how to make this faster:
72−
73−- Functional Reactive Programming, Continued
74−- Causal commutative arrows and their optimization
75−
76−Speeding things up is a really low priority. Language features and
77−libraries with nice APIs and are way more important!
78−
79−--}
core/Color.elmdeleted−44
@@ -1,44 +0,0 @@
1−
2−module Graphics.Color (rgba,rgb,hsva,hsv,
3− complement,
4− red,lime,blue,
5− yellow,cyan,magenta,
6− maroon,navy,green,
7− teal,purple,
8− violet,forestGreen,
9− black,white,gray,grey) where
10−
11−import Native.Color as Native
12−
13−data Color = Color Int Int Int Float
14−
15−rgba = Color
16−rgb r g b = Color r g b 1
17−
18−red = Color 255 0 0 1
19−lime = Color 0 255 0 1
20−blue = Color 0 0 255 1
21−
22−yellow = Color 255 255 0 1
23−cyan = Color 0 255 255 1
24−magenta = Color 255 0 255 1
25−
26−black = Color 0 0 0 1
27−white = Color 255 255 255 1
28−
29−gray = Color 128 128 128 1
30−grey = Color 128 128 128 1
31−
32−maroon = Color 128 0 0 1
33−navy = Color 0 0 128 1
34−green = Color 0 128 0 1
35−
36−teal = Color 0 128 128 1
37−purple = Color 128 0 128 1
38−
39−forestGreen = Color 34 139 34 1
40−violet = Color 238 130 238 1
41−
42−complement = Native.complement
43−hsva = Native.hsva
44−hsv = Native.hsv
core/Date.elmdeleted−8
@@ -1,8 +0,0 @@
1−
2−module Date where
3−
4−data Weekday = Mon | Tue | Wed | Thu | Fri | Sat | Sun
5−
6−data Month = Jan | Feb | Mar | Apr
7− | May | Jun | Jul | Aug
8− | Sep | Oct | Nov | Dec
core/Either.elmdeleted−22
@@ -1,22 +0,0 @@
1−
2−data Either a b = Left a | Right b
3−
4−either : (a -> c) -> (b -> c) -> Either a b -> c
5−either f g e = case e of { Left x -> f x ; Right y -> g y }
6−
7−
8−isLeft : Either a b -> Bool
9−isLeft e = case e of { Left _ -> True ; _ -> False }
10−
11−isRight : Either a b -> Bool
12−isRight e = case e of { Right _ -> True ; _ -> False }
13−
14−
15−lefts : [Either a b] -> [a]
16−lefts = Elm.List.filter isLeft
17−
18−rights : [Either a b] -> [b]
19−rights = Elm.List.filter isRight
20−
21−partition : [Either a b] -> ([a],[b])
22−partition = Elm.List.partition isLeft
core/Element.elmdeleted−195
@@ -1,195 +0,0 @@
1−
2−module Graphics.Element
3− (left,right,down,up,inward,outward
4− ,topLeft,topRight,bottomLeft,bottomRight
5− ,midLeft,midRight,midTop,midBottom
6− ,middle,absolute,relative
7− ,topLeftAt,topRightAt,bottomLeftAt,bottomRightAt
8− ,width,height,size,widthOf,heightOf,sizeOf
9− ,color,opacity
10− ,text,image,fittedImage,video
11− ,flow,above,below,beside,layers
12− ,collage,spacer,container
13− ,line,segment
14− ,polygon,ngon,rect,oval,circle
15− ,solid,dotted,dashed,customLine
16− ,filled,outlined,customOutline,textured
17− ,sprite,toForm
18− ,rotate,scale,move
19− ) where
20−
21−import Graphics.Color
22−
23−data Direction = DLeft | DRight | DUp | DDown | DIn | DOut
24−
25−left = DLeft
26−right = DRight
27−down = DDown
28−up = DUp
29−inward = DIn
30−outward = DOut
31−
32−data Pos1 = Absolute Int | Relative Float
33−data Pos2 = Near | Mid | Far
34−
35−data Position
36− = Position Pos2 Pos2
37− | PositionAt Pos1 Pos1
38− | PositionTL Pos1 Pos1
39− | PositionTR Pos1 Pos1
40− | PositionBL Pos1 Pos1
41− | PositionBR Pos1 Pos1
42−
43−topLeft = Position Near Near
44−topRight = Position Far Near
45−bottomLeft = Position Near Far
46−bottomRight = Position Far Far
47−
48−midLeft = Position Near Mid
49−midRight = Position Far Mid
50−midTop = Position Mid Near
51−midBottom = Position Mid Far
52−
53−middle = Position Mid Mid
54−
55−middleAt = PositionAt
56−topLeftAt = PositionTL
57−topRightAt = PositionTR
58−bottomLeftAt = PositionBL
59−bottomRightAt = PositionBR
60−
61−absolute = Absolute
62−relative = Relative
63−
64−data Element = Element Int BasicElement Int Int Float (Maybe Color) (Just String)
65−
66−newElement = Element 0
67−basicNewElement e w h = Element 0 e w h 1 Nothing Nothing
68−
69−data BasicElement
70− = EText Text Text
71− | EImage String
72− | EVideo String
73− | EFittedImage String
74− | EFlow Direction [Element]
75− | ECollage Int Int [Form]
76− | EEmpty
77− | EContainer Position Element
78−
79−width w' (Element _ e w h o c l) =
80− case e of
81− { EText _ -> newElement e w' h o c l
82− ; EImage _ -> newElement e w' h o c l
83− ; EVideo _ -> newElement e w' h o c l
84− ; _ -> newElement e w' h o c l }
85−height h' (Element _ e w h o c l) =
86− case e of
87− { EText _ -> newElement e w h' o c l
88− ; EImage _ -> newElement e w h' o c l
89− ; EVideo _ -> newElement e w h' o c l
90− ; _ -> newElement e w h' o c l }
91−size w' h' (Element _ e w h o c l) = newElement e w' h' o c l
92−opacity o' (Element _ e w h o c l) = newElement e w h o' c l
93−color c' (Element _ e w h o c l) = newElement e w h o (Just c') l
94−link l' (Element _ e w h o c l) = newElement e w h o c (Just l')
95−
96−widthOf (Element _ _ w _ _ _ _) = w
97−heightOf (Element _ _ _ h _ _ _) = h
98−sizeOf (Element _ _ w h _ _ _) = (w,h)
99−
100−n1 = 0-1
101−
102−text t = basicNewElement (EText t) n1 n1
103−image w h s = basicNewElement (EImage s) w h
104−video w h s = basicNewElement (EVideo s) w h
105−fittedImage w h s = basicNewElement (EFittedImage s) w h
106−
107−flow dir es =
108− let { w = let ws = map widthOf es in
109− case dir of { DLeft -> sum ws
110− ; DRight -> sum ws
111− ; _ -> maximum ws }
112− ; h = let hs = map heightOf es in
113− case dir of { DDown -> sum hs
114− ; DUp -> sum hs
115− ; _ -> maximum hs }
116− } in basicNewElement (EFlow dir es) w h
117−
118−above e1 e2 =
119− newElement
120− (EFlow DDown [e1,e2])
121− (max (widthOf e1) (widthOf e2))
122− (heightOf e1 + heightOf e2) 1 Nothing Nothing
123−
124−below e1 e2 =
125− basicNewElement (EFlow DDown [e2,e1])
126− (max (widthOf e1) (widthOf e2))
127− (heightOf e1 + heightOf e2)
128−
129−beside e1 e2 =
130− basicNewElement (EFlow DRight [e1,e2])
131− (widthOf e1 + widthOf e2)
132− (max (heightOf e1) (heightOf e2))
133−
134−layers es =
135− basicNewElement (EFlow DIn es)
136− (maximum (map widthOf es))
137− (maximum (map heightOf es))
138−
139−collage w h forms = basicNewElement (ECollage w h forms) w h
140−
141−spacer w h = basicNewElement EEmpty w h
142−
143−container w h pos e =
144− basicNewElement (EContainer pos e) w h
145−
146−
147−
148−data LineStyle = Solid | Dotted | Dashed | Custom [Int]
149−data ShapeStyle = Filled | Outlined | CustomOutline [Int] | Textured String
150−
151−data Line = Line [(Float,Float)]
152−
153−line = Line
154−segment p1 p2 = Line [p1,p2]
155−
156−data Shape = Shape [(Float,Float)] (Float,Float)
157−
158−polygon = Shape
159−rect w h pos = Shape [(0-w/2,0-h/2),(0-w/2,h/2),(w/2,h/2),(w/2,0-h/2)] pos
160−oval w h pos =
161− let n = 50 in
162− let f i = ( w/2 * cos (2*pi/n * i), h/2 * sin (2*pi/n * i)) in
163− Shape (map f [0..n-1]) pos
164−circle r = oval (2*r) (2*r)
165−ngon n r pos =
166− let m = toFloat n in
167− let f i = ( r * cos (2*pi/m * i), r * sin (2*pi/m * i)) in
168− Shape (map f [0..n-1]) pos
169−
170−data Form = Form Float Float (Float,Float) BasicForm
171−
172−data BasicForm
173− = FLine LineStyle Color Line
174− | FShape ShapeStyle Color Shape
175− | FImage Int Int String
176− | FElement Element
177−
178−solid clr ln = Form 0 1 (0,0) (FLine Solid clr ln)
179−dotted clr ln = Form 0 1 (0,0) (FLine Dotted clr ln)
180−dashed clr ln = Form 0 1 (0,0) (FLine Dashed clr ln)
181−customLine pattern clr ln =
182− Form 0 1 (0,0) (FLine (Custom pattern) clr ln)
183−
184−filled clr (Shape ps pos) = Form 0 1 pos (FShape Filled clr (Shape ps pos))
185−outlined clr (Shape ps pos) = Form 0 1 pos (FShape Outlined clr (Shape ps pos))
186−customOutline pattern clr (Shape ps pos) =
187− Form 0 1 pos (FShape (CustomOutline pattern) clr (Shape ps pos))
188−textured src (Shape ps pos) = Form 0 1 pos (FShape (Textured src) black (Shape ps pos))
189−
190−sprite w h pos src = Form 0 1 pos (FImage w h src)
191−toForm pos e = Form 0 1 pos (FElement e)
192−
193−rotate t (Form theta scale pos form) = Form (t+theta) scale pos form
194−scale s (Form theta scale pos form) = Form theta (s*scale) pos form
195−move x y (Form theta scale (px,py) form) = Form theta scale (x+px,y+py) form
core/Form.elmdeleted−114
@@ -1,114 +0,0 @@
1−
2−module Collage where
3−
4−data Line
5− = Start (Float,Float)
6− | Arc (Float,Float) Float (Float,Float) Path
7− | Line (Float,Float) Path
8− | Bezier (Float,Float) (Float,Float) (Float,Float) Path
9− | Quadratic (Float,Float) (Float,Float) Path
10−
11−path ps = case ps of
12− [] -> Start (0,0)
13− hd:tl -> foldl Line (Start hd) tl
14−
15−segment p1 p2 = Line p1 (Start p2)
16−
17−start = Start
18−arcTo = Arc
19−lineTo = Line
20−bezierTo = Bezier
21−quadraticTo = Quadratic
22−
23−data Shape = Shape Line
24−
25−polygon ps = Shape (case ps of
26− [] -> Start (0,0)
27− hd:tl -> Line hd $ foldl Line (Start hd) tl)
28−
29−rect w h = polygon [ (0-w/2,0-h/2), (0-w/2,h/2), (w/2,h/2), (w/2,0-h/2) ]
30−oval w h =
31− let n = 50
32− f i = ( w/2 * cos (2*pi/n * i), h/2 * sin (2*pi/n * i))
33− in Shape $ map f [0..n-1]
34−circle r = oval (2*r) (2*r)
35−ngon n r =
36− let m = toFloat n
37− f i = ( r * cos (2*pi/m * i), r * sin (2*pi/m * i))
38− in Shape $ map f [0..n-1]
39−
40−data Transform
41− = Rotate Float
42− | Move Float Float
43− | Scale Float Float
44− | Transform Float Float Float Float Float Float
45−
46−data Form = Form [Transform] BasicForm
47−
48−
49−data LineCap = Butt | Round | Square
50−data LineJoin = Round | Bevel | Miter
51−
52−data FillStyle
53− = NoFill
54− | Solid Color
55− | Texture String
56− | LinearGradient [(Float,Color)] (Float,Float) (Float,Float)
57− | RadialGradient [(Float,Color)] (Float,Float) Float (Float,Float) Float
58−
59−data LineStyle = NoLine | Line [Int] Int Float LineCap LineJoin Float FillStyle
60−
61−data BasicForm
62− = FLine LineStyle FillStyle Line
63− | FShape LineStyle FillStyle Shape
64− | FImage Int Int String
65− | FElement Element
66− | FGroup [Form]
67−
68−setFillStyle fs form =
69− case form of
70− FLine ls _ ln -> FLine ls fs ln
71− FShape ls _ shp -> FLine ls fs shp
72− _ -> form
73−
74−noFill = setFillStyle NoFill
75−fillColor clr = setFillStyle (Solid clr)
76−texture src = setFillStyle (Texture src)
77−linearGradient stops start end = setFillStyle (LinearGradient stops start end)
78−radialGradient stops innerP innerR outerP outerR =
79− setFillStyle (RadialGradient stops innerP innerR outerP outerR)
80−
81−solid clr ln = Form [] (FLine ln)
82−dotted clr ln = Form [] (FLine ln)
83−dashed clr ln = Form [] (FLine ln)
84−customLine pattern clr ln = Form [] (FLine (Custom pattern) clr ln)
85−
86−
87−filled clr shp = Form [] (FShape shp)
88−outlined clr shp = Form [] (FShape shp)
89−customOutline pattern clr (Shape ps pos) =
90− Form [] (FShape (CustomOutline pattern) clr (Shape ps pos))
91−textured src (Shape ps pos) = Form [] (FShape (Textured src) black (Shape ps pos))
92−
93−fromLine = FLine
94−fromShape = FShape
95−fromElement = FElement
96−
97−sprite w h pos src = Form 0 1 pos (FImage w h src)
98−toForm pos e = Form 0 1 pos (FElement e)
99−
100−addTransform t (Form ts form) = Form (t:ts) form
101−
102−rotateRad rad = addTransform $ Rotate rad
103−rotateDeg deg = addTransform $ Rotate (pi * deg / 180)
104−rotate rot = addTransform $ Rotate (2 * pi * rot)
105−
106−scale s = addTransform (Scale s s)
107−scaleX s = addTransform (Scale s 1)
108−scaleY s = addTransform (Scale 1 s)
109−
110−move x y = addTransform (Move x y)
111−moveX x = addTransform (Move x 0)
112−moveY y = addTransform (Move 0 y)
113−
114−transform a b c d e f = addTransform (Transform a b c d e f)
core/List.elmdeleted−97
@@ -1,97 +0,0 @@
1−
2−module List where
3−
4−import Native.List as Native
5−
6−head : [a] -> a
7−head = Native.head
8−
9−tail : [a] -> [a]
10−tail = Native.tail
11−
12−last : [a] -> a
13−last = Native.last
14−
15−map : (a -> b) -> [a] -> [b]
16−map = Native.map
17−
18−foldl : (a -> b -> b) -> b -> [a] -> b
19−foldl = Native.foldl
20−
21−foldr : (a -> b -> b) -> b -> [a] -> b
22−foldr = Native.foldr
23−
24−foldl1 : (a -> a -> a) -> [a] -> a
25−foldl1 = Native.foldl1
26−
27−foldr1 : (a -> a -> a) -> [a] -> a
28−foldr1 = Native.foldr1
29−
30−scanl : (a -> b -> b) -> b -> [a] -> [b]
31−scanl = Native.scanl
32−
33−scanl1 : (a -> a -> a) -> [a] -> [a]
34−scanl1 = Native.scanl1
35−
36−filter : (a -> Bool) -> [a] -> [a]
37−filter = Native.filter
38−
39−length : [a] -> Int
40−length = Native.length
41−
42−reverse : [a] -> [a]
43−reverse = Native.reverse
44−
45−concat : [[a]] -> [a]
46−concat = Native.foldr (++) []
47−
48−concatMap : (a -> [b]) -> [a] -> [b]
49−concatMap f = concat . Native.map f
50−
51−all : (a -> Bool) -> [a] -> Bool
52−all pred = Native.all
53−
54−any : (a -> Bool) -> [a] -> Bool
55−any = Native.any
56−
57−and : [Bool] -> Bool
58−and = Native.all id
59−
60−or : [Bool] -> Bool
61−or = Native.any id
62−
63−sum = foldl (+) 0
64−product = foldl (*) 1
65−maximum = foldl1 max
66−minimum = foldl1 min
67−
68−partition : (a -> Bool) -> [a] -> ([a],[a])
69−partition pred lst =
70− case lst of
71− [] -> ([],[])
72− x::xs -> let (as,bs) = partition pred xs in
73− if pred x then (x::as,bs) else (as,x::bs)
74−
75−zipWith : (a -> b -> c) -> [a] -> [b] -> [c]
76−zipWith = Native.zipWith
77−
78−zip : [a] -> [b] -> [(a,b)]
79−zip = Native.zip
80−
81−unzip : [(a,b)] -> ([a],[b])
82−unzip pairs =
83− case pairs of
84− [] -> ([],[])
85− (x,y)::ps -> let (xs,ys) = (unzip ps) in (x::xs,y::ys)
86−
87−intersperse sep xs =
88− case xs of
89− a::b::cs -> a :: sep :: intersperse sep (b::cs)
90− [a] -> [a]
91− [] -> []
92−
93−intercalate sep xs =
94− case xs of
95− a::b::cs -> a ++ sep ++ intercalate sep (b::cs)
96− [a] -> a
97− [] -> []
core/Native/Color.jsdeleted−64
@@ -1,64 +0,0 @@
1−function nativeColor(elm) {
2−
3−function extract(c) {
4− if (c[4] === 1) { return 'rgb(' + c[1] + ',' + c[2] + ',' + c[3] + ')'; }
5− return 'rgba(' + c[1] + ',' + c[2] + ',' + c[3] + ',' + c[4] + ')';
6−}
7−function complement(rgb) {
8− var hsv = toHSV(rgb);
9− hsv.hue = (hsv.hue + 180) % 360;
10− return toRGB(hsv);
11−}
12−
13−function hsva(h) { return function(s) { return function(v) { return function(a) {
14− var clr = toRGB({hue:h, saturation:s, value:v});
15− clr[4] = a;
16− return clr;
17− }; }; };
18−}
19−
20−function hsv(h) { return function(s) { return function(v) {
21− return toRGB({hue:h, saturation:s, value:v}); }; }; }
22−
23−function toHSV(rgb) {
24− var hsv = {};
25− var r = rgb[1] / 255.0, g = rgb[2] / 255.0, b = rgb[3] / 255.0;
26− var M = Math.max(r,g,b);
27− var m = Math.min(r,g,b);
28− var c = M - m;
29−
30− var h = 0;
31− if (c === 0) { h = 0; }
32− else if (M === r) { h = ((g - b) / c) % 6; }
33− else if (M === g) { h = ((b - r) / c) + 2; }
34− else if (M === b) { h = ((r - g) / c) + 4; }
35− h *= 60;
36−
37− return { value : M, hue : h, saturation : (M === 0 ? 0 : c / M) };
38−}
39−
40−function between(lo,hi,x) { return lo <= x && x < hi; }
41−function norm(n) { return Math.round(n*255); }
42−
43−function toRGB(hsv) {
44− var c = hsv.value * hsv.saturation;
45− var hue = hsv.hue / 60;
46− var x = c * (1 - Math.abs((hue % 2) - 1));
47− var r = 0, g = 0, b = 0;
48− if (between(0,1,hue)) { r = c; g = x; b = 0; }
49− else if (between(1,2,hue)) { r = x; g = c; b = 0; }
50− else if (between(2,3,hue)) { r = 0; g = c; b = x; }
51− else if (between(3,4,hue)) { r = 0; g = x; b = c; }
52− else if (between(4,5,hue)) { r = x; g = 0; b = c; }
53− else if (between(5,6,hue)) { r = c; g = 0; b = x; }
54−
55− var m = hsv.value - c;
56− return [ "Color", norm(r+m), norm(g+m), norm(b+m), 1 ];
57−}
58−
59−elm.Native.Color = {
60− hsva:hsva,
61− hsv:hsv,
62− complement:complement,
63− extract:extract};
64−}
core/Native/List.jsdeleted−214
@@ -1,214 +0,0 @@
1−function nativeList(elm) {
2−
3− function throwError(f) {
4− throw new Error("Function '" + f + "' expects a non-empty list!");
5− }
6−
7− function toArray(xs) {
8− var out = [];
9− while (xs[0] === "Cons") {
10− out.push(xs[1]);
11− xs = xs[2];
12− }
13− return out;
14− }
15−
16− function fromArray(arr) {
17− var out = ["Nil"];
18− for (var i = arr.length; i--; ) {
19− out = ["Cons", arr[i], out];
20− }
21− return out;
22− }
23−
24− function head(v) { v[0] === "Nil" ? throwError('head') : return v[1]; }
25− function tail(v) { v[0] === "Nil" ? throwError('tail') : return v[2]; }
26−
27− function last(xs) {
28− if (xs[0] === "Nil") { throwError('last'); }
29− var out = xs[1];
30− while (xs[0] === "Cons") {
31− out = xs[1];
32− xs = xs[2];
33− }
34− return out;
35− }
36−
37− function map(f) { return function(xs) {
38− var arr = [];
39− while (xs[0] === "Cons") {
40− arr.push(f(xs[1]));
41− xs = xs[2];
42− }
43− return fromArray(arr);
44− }
45− }
46−
47− function foldl(f) { return function(b) { return function(xs) {
48− var acc = b;
49− while (xs[0] === "Cons") {
50− acc = f(xs[1])(acc);
51− xs = xs[2];
52− }
53− return acc;
54− }
55− }
56− }
57−
58− function foldr(f) { return function(b) { return function(xs) {
59− var arr = toArray(xs);
60− var acc = b;
61− for (var i = arr.length; i--; ) {
62− acc = f(arr[i])(acc);
63− }
64− return acc;
65− }
66− }
67− }
68−
69− function foldl1(f) { return function(xs) {
70− xs[0] === "Nil" ? throwError('foldl1') : return foldl(f)(xs[1])(xs[2]);
71− }
72− }
73−
74− function foldr1(f) { return function(xs) {
75− if (xs[0] === "Nil") { throwError('foldr1'); }
76− var arr = toArray(xs);
77− var acc = arr.pop();
78− for (var i = arr.length; i--; ) {
79− acc = f(arr[i])(acc);
80− }
81− return acc;
82− }
83− }
84−
85− function scanl(f) { return function(b) { return function(xs) {
86− var arr = toArray(xs);
87− arr.unshift(b);
88− var len = arr.length;
89− for (var i = 1; i < len; ++i) {
90− arr[i] = f(arr[i])(arr[i-1]);
91− }
92− return fromArray(arr);
93− }
94− }
95− }
96−
97− function scanl1(f) { return function(xs) {
98− xs[0] === "Nil" ? throwError('scanl1') : return scanl(f)(xs[1])(xs[2]);
99− }
100− }
101−
102− function filter(pred) { return function(xs) {
103− var arr = [];
104− while (xs[0] === "Cons") {
105− if (pred(xs[1])) { arr.push(xs[1]); }
106− xs = xs[2];
107− }
108− return fromArray(arr);
109− }
110− }
111−
112− function length(xs) {
113− var out = 0;
114− while (xs[0] === "Cons") {
115− out += 1;
116− xs = xs[2];
117− }
118− return out;
119− }
120−
121− function reverse(xs) { return fromArray(toArray(xs).reverse()); }
122−
123− function all(pred) { return function(xs) {
124− while (xs[0] === "Cons") {
125− if (!pred(xs[1])) return false;
126− xs = xs[2];
127− }
128− return true;
129− }
130− }
131−
132− function any(pred) { return function(xs) {
133− while (xs[0] === "Cons") {
134− if (pred(xs[1])) return true;
135− xs = xs[2];
136− }
137− return false;
138− }
139− }
140−
141− function zipWith(f) { return function(xs) { return function(ys) {
142− var arr = [];
143− while (xs[0] === "Cons" && ys[0] === "Cons") {
144− arr.push(f(xs[1])(ys[1]));
145− xs = xs[2];
146− ys = ys[2];
147− }
148− return fromArray(arr);
149− }
150− }
151− }
152−
153− function zip(xs) { return function(ys) {
154− var arr = [];
155− while (xs[0] === "Cons" && ys[0] === "Cons") {
156− arr.push(["Tuple2",xs[1],ys[1]]);
157− xs = xs[2];
158− ys = ys[2];
159− }
160− return fromArray(arr);
161− }
162− }
163−
164− function sort(xs) {
165− return fromArray(toArray(xs).sort(function(a,b) { return a - b}));
166− }
167−
168− function take(n) { return function(xs) {
169− var arr = [];
170− while (xs[0] === "Cons" && n > 0) {
171− arr.push(xs[1]);
172− xs = xs[2];
173− --n;
174− }
175− return fromArray(arr);
176− }
177− }
178−
179− function drop(n) { return function(xs) {
180− while (xs[0] === "Cons" && n > 0) {
181− xs = xs[2];
182− --n;
183− }
184− return xs;
185− }
186− }
187−
188− function concatA(
189−
190− elm.Native.List = {
191− head:head,
192− tail:tail,
193− last:last,
194−
195− map:map,
196− foldl:foldl,
197− foldr:foldr,
198−
199− foldl1:foldl1,
200− foldr1:foldr1,
201− scanl:scanl,
202− scanl1:scanl1,
203− filter:filter,
204− length:length,
205− reverse:reverse,
206−
207− all:all,
208− any:any,
209− zipWith:zipWith,
210− zip:zip,
211− sort:sort,
212− take:take,
213− drop:drop};
214−}
core/Set.elmdeleted−48
@@ -1,48 +0,0 @@
1−
2−module Set (empty,singleton,insert,remove
3− ,member
4− ,foldl,foldr,map
5− ,union,intersect,diff
6− ,toList,fromList
7− ) where
8−
9−type Set t = Dict t ()
10−
11−empty : Set t
12−empty = Dict.empty
13−
14−singleton : t -> Set t
15−singleton k = Dict.singleton k ()
16−
17−insert : t -> Set t -> Set t
18−insert k = Dict.insert k ()
19−
20−remove : t -> Set t -> Set t
21−remove = Dict.remove
22−
23−member : t -> Set t -> Bool
24−member = Dict.member
25−
26−union : Set t -> Set t -> Set t
27−union = Dict.union
28−
29−intersect : Set t -> Set t -> Set t
30−intersect = Dict.intersect
31−
32−diff : Set t -> Set t -> Set t
33−diff = Dict.diff
34−
35−toList : Set t -> [t]
36−toList = Dict.keys
37−
38−fromList : [t] -> Set t
39−fromList = List.foldl (\k t -> Dict.insert k () t) empty
40−
41−foldl : (a -> b -> b) -> b -> Set a -> b
42−foldl f = Dict.foldl (\k _ b -> f k b)
43−
44−foldr : (a -> b -> b) -> b -> Set a -> b
45−foldr f = Dict.foldr (\k _ b -> f k b)
46−
47−map : (a -> b) -> Set a -> Set b
48−map f = fromList . List.map f . toList
elm/Setup.hsdeleted−2
@@ -1,2 +0,0 @@
1−import Distribution.Simple
2−main = defaultMain
elm/elm-runtime-0.5.0.2.jsdeleted−123
@@ -1,123 +0,0 @@
1−var Guid=function(){var d=0;return{guid:function(){return d+=1}}}(),Elm=Elm||{};
2−Elm.JavaScript=function(){function d(a){for(var b=["Nil"],l=a.length;l--;)b=["Cons",a[l],b];return b}function a(a){for(var b=[];"Cons"===a[0];)b.push(a[1]),a=a[2];return b}function g(a){return a.slice(1)}function i(a){return["Tuple"+a.length].concat(a)}return{castJSBoolToBool:function(a){return a},castBoolToJSBool:function(a){return a},castJSNumberToFloat:function(a){return a},castFloatToJSNumber:function(a){return a},castJSNumberToInt:function(a){return~~a},castIntToJSNumber:function(a){return a},
3−Experimental:{castJSElementToElement:function(a){return function(b){return function(l){return["Element",Guid.guid(),["EExternalHtml",l],a,b,1,Nothing,Nothing]}}},castElementToJSElement:function(a){return Render.render(a)}},castJSArrayToList:d,castListToJSArray:a,castJSStringToString:d,castStringToJSString:function(g){return"string"===typeof g?g:a(g).join("")},castTupleToJSTuple2:g,castTupleToJSTuple3:g,castTupleToJSTuple4:g,castTupleToJSTuple5:g,castJSTupleToTuple2:i,castJSTupleToTuple3:i,castJSTupleToTuple4:i,
4−castJSTupleToTuple5:i}}();var Elm=Elm||{},JSjson=JSON;
5−Elm.JSON=function(){function d(b,a){return function(h){return function(e){var c=i.castStringToJSString(h);return e[1].hasOwnProperty(c)&&(e=e[1][c],e[0]===b)?e[1]:a}}}function a(b){return function(a){function h(b){switch(b[0]){case "JsonNull":return null;case "JsonString":return i.castStringToJSString(b[1]);case "JsonObject":var c={},b=b[1][1],f;for(f in b)c[f]=h(b[f]);return c;case "JsonArray":c=i.castListToJSArray(b[1]);for(f=c.length;f--;)c[f]=h(c[f]);return c;default:return b[1]}}return JSjson.stringify(h(["JsonObject",
6−a]),null,i.castStringToJSString(b))}}function g(b){function a(b){switch(typeof b){case "string":return["JsonString",i.castJSStringToString(b)];case "number":return["JsonNumber",i.castJSNumberToFloat(b)];case "boolean":return["JsonBool",i.castJSBoolToBool(b)];case "object":if(null===b)return["JsonNull"];for(var c in b)b[c]=a(b[c]);return b instanceof Array?["JsonArray",i.castJSArrayToList(b)]:["JsonObject",["JSON",b]]}}var b=JSjson.parse(b),h;for(h in b)b[h]=a(b[h]);return["JSON",b]}var i=Elm.JavaScript,
7−j=["JSON",{}];return{empty:j,singleton:function(b){return function(a){var h={};h[i.castStringToJSString(b)]=a;return["JSON",h]}},insert:function(b){return function(a){return function(h){var h=h[1],e={},c;for(c in h)e[c]=h[c];e[i.castStringToJSString(b)]=a;return["JSON",e]}}},lookup:function(b){return function(a){var h=i.castStringToJSString(b);return a[1].hasOwnProperty(h)?Just(a[1][h]):Nothing}},findString:d("JsonString",["Nil"]),findObject:d("JsonObject",j),findArray:d("JsonArray",["Nil"]),findWithDefault:function(b){return function(a){return function(h){var e=
8−i.castStringToJSString(a);return h[1].hasOwnProperty(e)?h[1][e]:b}}},remove:function(b){return function(a){var a=a[1],h={},e;for(e in a)h[e]=a[e];delete h[i.castStringToJSString(b)];return["JSON",h]}},toPrettyJSString:a,toJSString:a(""),fromJSString:g,toPrettyString:function(b){return function(g){return i.castJSStringToString(a(b)(g))}},toString:function(b){return i.castJSStringToString(a("")(b))},fromString:function(b){return g(i.castStringToJSString(b))},toList:function(b){var b=b[1],a=[],h;for(h in b)a.push(Value.Tuple(i.castJSStringToString(h),
9−b[h]));return i.castJSArrayToList(a)},fromList:function(b){for(var b=i.castListToJSArray(b),a={},h=b.length;h--;)a[i.castStringToJSString(b[h][1])]=b[h][2];return["JSON",a]},JsonString:function(b){return["JsonString",b]},JsonNumber:function(b){return["JsonNumber",b]},JsonBool:function(b){return["JsonBool",b]},JsonNull:["JsonNull"],JsonArray:function(b){return["JsonArray",b]},JsonObject:function(b){return["JsonObject",b]}}}();
10−var Value=function(){function d(b){if(0==b.length)return b;for(var b=b.replace(/"/g,"&#34;").replace(/'/g,"&#39;").replace(/</g,"&#60;").replace(/>/g,"&#62;").replace(/\n/g,"<br/>"),b=b.split("<br/>"),a=b.length;a--;){var h=b,e=a,c;c=b[a];if(0!=c.length){c=c.split("");" "==c[0]&&(c[0]="&nbsp;");for(var f=c.length;--f;)" "==c[f][0]&&" "==c[f-1]&&(c[f-1]+=c[f],c[f]="");for(f=c.length;f--;)if(1<c[f].length&&" "==c[f][0]){for(var n=c[f].split(""),g=n.length-2;0<=g;g-=2)n[g]="&nbsp;";c[f]=n.join("")}c=
11−c.join("");c=" "===c[c.length-1]?c.slice(0,-1)+"&nbsp;":c}h[e]=c}return b.join("<br/>")}var a=function(b,g){if("object"===typeof b){if(b===g)return!0;if(b.length!==g.length)return!1;for(var h=b.length;h--;)if(!a(b[h],g[h]))return!1;return!0}return b===g},g=function(b){if("boolean"===typeof b)return b?"True":"False";if("number"!==typeof b){if("string"===typeof b&&2>b.length)return"'"+b+"'";if(b[0]){if("Tuple"===b[0].substring(0,5)){for(var a="",h=b.length;--h;)a=","+g(b[h])+a;","===a[0]&&(a=a.substring(1));
12−return"("+a+")"}if("Cons"===b[0])for(var h="string"===typeof b[1]?'"':"]",e="string"===typeof b[1]?"":",",c="string"===typeof b[1]?function(c){return c}:g,a=("string"===typeof b[1]?'"':"[")+c(b[1]),b=b[2];;)if("Cons"===b[0])a+=e+c(b[1]),b=b[2];else return a+h;else{if("Nil"===b[0])return"[]";if("JSON"===b[0])return"(JSON.fromList "+g(Elm.JSON.toList(b))+")";if("RBNode"===b[0]||"RBEmpty"===b[0])return"(Map.fromList "+g(Elm.Dict.fold(function(c){return function(b){return function(a){return["Cons",["Tuple2",
13−c,b],a]}}})(["Nil"])(b))+")";a="";for(h=b.length;--h;)a=" "+g(b[h])+a;a=b[0]+a;return 1<b.length?"("+a+")":a}}}return b+""},i=function(b){for(var a=["Nil"],h=b.length;h--;)a=["Cons",b[h],a];return a},j;j=document.addEventListener?function(b,a,h){b.addEventListener(a,h,!1)}:function(b,a,h){b.attachEvent("on"+a,h)};return{eq:a,str:i,show:function(b){return i(g(b))},Tuple:function(){var b=arguments.length,a=Array(b+1);for(a[0]="Tuple"+arguments.length;b--;)a[b+1]=arguments[b];return a},append:function(b,
14−a){if("string"===typeof b&&"string"===typeof a)return b.concat(a);if("Nil"===b[0])return a;for(var h=["Cons",b[1],["Nil"]],e=h,b=b[2];"Cons"===b[0];)e[2]=["Cons",b[1],["Nil"]],b=b[2],e=e[2];e[2]=a;return h},listToArray:function(b){for(var a=[];"Cons"===b[0];)a.push(b[1]),b=b[2];return a},toText:function(b){if("string"===typeof b)return d(b);for(var a=[];"Cons"===b[0];)a.push(b[1]),b=b[2];return d(a.join(""))},properEscape:d,getTextSize:function(b,a,h){var e=document.createElement("div");e.innerHTML=
15−h;e.style.textAlign="left";0<b&&(e.style.width=b+"px");e.style.visibility="hidden";e.style.styleFloat="left";e.style.cssFloat="left";document.body.appendChild(e);h=window.getComputedStyle(e);b=h.getPropertyValue("width").slice(0,-2)-0;h=h.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(e);delete e;return[Math.ceil(b),Math.ceil(Math.max(a,h))]},getSize:function(b){b=b.cloneNode(!0);b.style.visibility="hidden";b.style.styleFloat="left";b.style.cssFloat="left";document.body.appendChild(b);
16−var a=b.offsetWidth,h=b.offsetHeight;document.body.removeChild(b);delete b;return[a,h]},getExcess:function(b){b=b.cloneNode(!0);b.style.visibility="hidden";b.style.styleFloat="left";b.style.cssFloat="left";document.body.appendChild(b);var a=b.offsetWidth,h=b.offsetHeight,e=window.getComputedStyle(b),c=e.getPropertyValue("width").slice(0,-2)-0,e=e.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(b);delete b;return[a-c,h-e]},groupForms:function(b){for(var b=Elm.JavaScript.castListToJSArray(b),
17−a=[],h=[],e=b.length;e--;){var c=b[e];switch(c[4][0]){case "FElement":0<h.length&&(a.push(h),h=[]);a.push(c);break;default:h.push(c)}}0<h.length&&a.push(h);return a},wrap:function(a){var g=Value.getSize(a);return["Element",Guid.guid(),["EHtml",a],g[0],g[1],1,Nothing,Nothing]},addListener:j}}(),Elm=Elm||{};
18−Elm.List=function(){function d(a){return function(b){if("Nil"===b[0])return b;"Cons"!==b[0]&&c("map");for(var f=["Cons",a(b[1]),["Nil"]],e=f,b=b[2];"Cons"===b[0];)e[2]=["Cons",a(b[1]),["Nil"]],b=b[2],e=e[2];return f}}function a(a){return function(b){return function(f){var e=b;if("Nil"===f[0])return e;for("Cons"!==f[0]&&c("foldl");"Cons"===f[0];)e=a(f[1])(e),f=f[2];return e}}}function g(a){return function(b){return function(f){var e=b;if("Nil"===f[0])return e;"Cons"!==f[0]&&c("foldr");for(var n=[];"Cons"===
19−f[0];)n.push(f[1]),f=f[2];for(f=n.length;f--;)e=a(n[f])(e);return e}}}function i(c){return function(b){var f;"Cons"!==b[0]?f=void 0:(f=b[1],b=b[2],f=a(c)(f)(b));return f}}function j(b){return function(a){return function(f){if("Nil"===f[0])return["Cons",a,["Nil"]];"Cons"!==f[0]&&c("scanl");for(var e=[a];"Cons"===f[0];)a=b(f[1])(a),e.push(a),f=f[2];for(var f=["Nil"],n=e.length;n--;)f=["Cons",e[n],f];return f}}}function b(c){return function(a){a:{for(var f=[function(c){return"Nil"!==c[0]?void 0:["Tuple2",
20−["Nil"],["Nil"]]},function(a){if("Cons"===a[0]){var f=a[1],a=a[2];var e=b(c)(a);"Tuple2"!==e[0]?f=void 0:(a=e[1],e=e[2],f=c(f)?["Tuple2",["Cons",f,a],e]:["Tuple2",a,["Cons",f,e]]);return f}}],e=f.length;e--;){var n=f[e](a);if(void 0!==n){a=n;break a}}a=void 0}return a}}function l(c){a:{for(var a=[function(c){return"Nil"!==c[0]?void 0:["Tuple2",["Nil"],["Nil"]]},function(c){if("Cons"!==c[0])c=void 0;else if(c=["Tuple2",c[1],l(c[2])],"Tuple2"!==c[0]||"Tuple2"!==c[1][0])c=void 0;else var a=c[1][1],b=
21−c[1][2],c="Tuple2"!==c[2][0]?void 0:["Tuple2",["Cons",a,c[2][1]],["Cons",b,c[2][2]]];return c}],b=a.length;b--;){var f=a[b](c);if(void 0!==f){c=f;break a}}c=void 0}return c}function h(c){return function(a){a:{for(var b=[function(c){return"Nil"!==c[0]?void 0:["Nil"]},function(c){if("Cons"===c[0]){var a=c[1];return"Nil"!==c[2][0]?void 0:["Cons",a,["Nil"]]}},function(a){if("Cons"===a[0]){var b=a[1];if("Cons"===a[2][0]){var f=a[2][1],a=a[2][2];return["Cons",b,["Cons",c,h(c)(["Cons",f,a])]]}}}],f=b.length;f--;){var e=
22−b[f](a);if(void 0!==e){a=e;break a}}a=void 0}return a}}function e(c){return function(a){a:{for(var b=[function(c){return"Nil"!==c[0]?void 0:["Nil"]},function(c){if("Cons"===c[0]){var a=c[1];return"Nil"!==c[2][0]?void 0:a}},function(a){if("Cons"===a[0]){var b=a[1];if("Cons"===a[2][0]){var f=a[2][1],a=a[2][2];return Value.append(b,Value.append(c,e(c)(["Cons",f,a])))}}}],f=b.length;f--;){var n=b[f](a);if(void 0!==n){a=n;break a}}a=void 0}return a}}var c=function(c){throw"Function '"+c+"' expecting a list!";
23−},f=a(function(c){return function(a){return["Cons",c,a]}})(["Nil"]),n=g(function(c){return function(a){return Value.append(c,a)}})(["Nil"]),m=a(function(c){return function(a){return c&&a}})(!0),s=a(function(c){return function(a){return c||a}})(!1),p=a(function(c){return function(a){return c+a}})(0),k=a(function(c){return function(a){return c*a}})(1),u=i(function(c){return function(a){return Math.max(c,a)}}),x=i(function(c){return function(a){return Math.min(c,a)}});return{head:function(c){if("Cons"!==
24−c[0])throw"Error: 'head' only accepts lists of length greater than one.";return c[1]},tail:function(c){if("Cons"!==c[0])throw"Error: 'tail' only accepts lists of length greater than one.";return c[2]},last:function(c){if("Cons"!==c[0])throw"Error: 'last' only accepts lists of length greater than one.";for(var a=c[1];"Cons"===c[0];)a=c[1],c=c[2];return a},map:d,foldl:a,foldr:g,foldl1:i,foldr1:function(a){return function(b){if("Nil"===b[0])throw"'foldr1' requires an non-empty list.";"Cons"!==b[0]&&
25−c("foldr1");for(var f=[];"Cons"===b[0];)f.push(b[1]),b=b[2];for(var b=f.pop(),e=f.length;e--;)b=a(f[e])(b);return b}},scanl:j,scanl1:function(c){return function(a){if("Cons"!==a[0])throw"Error: 'scanl1' requires a list of at least length 1.";return j(c)(a[1])(a[2])}},filter:function(a){return function(b){if("Nil"===b[0])return b;"Cons"!==b[0]&&c("filter");for(var f=[];"Cons"===b[0];)a(b[1])&&f.push(b[1]),b=b[2];for(var b=["Nil"],e=f.length;e--;)b=["Cons",f[e],b];return b}},length:function(c){for(var a=
26−0;"Cons"===c[0];)a+=1,c=c[2];return a},reverse:f,concat:n,concatMap:function(c){return function(a){return n(d(c)(a))}},and:m,or:s,all:function(c){return a(function(a){return function(b){return b&&c(a)}})(!0)},any:function(c){return a(function(a){return function(b){return b||c(a)}})(!1)},sum:p,product:k,maximum:u,minimum:x,partition:b,zipWith:function(a){return function(b){return function(f){if("Nil"===b[0]||"Nil"===f[0])return["Nil"];("Cons"!==b[0]||"Cons"!==f[0])&&c("zipWith");for(var e=[];"Cons"===
27−b[0]&&"Cons"===f[0];)e.push(a(b[1])(f[1])),b=b[2],f=f[2];for(var f=["Nil"],n=e.length;n--;)f=["Cons",e[n],f];return f}}},zip:function(a){return function(b){if("Nil"===a[0]||"Nil"===b[0])return["Nil"];("Cons"!==a[0]||"Cons"!==b[0])&&c("zip");for(var f=[];"Cons"===a[0]&&"Cons"===b[0];)f.push(["Tuple2",a[1],b[1]]),a=a[2],b=b[2];for(var b=["Nil"],e=f.length;e--;)b=["Cons",f[e],b];return b}},unzip:l,intersperse:h,intercalate:e,sort:function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&c("sort");for(var b=
28−[];"Cons"===a[0];)b.push(a[1]),a=a[2];b.sort(function(c,a){return c-a});for(var a=["Nil"],f=b.length;f--;)a=["Cons",b[f],a];return a},take:function(a){return function(b){if(0>=a)return["Nil"];if("Nil"===b[0])return b;"Cons"!==b[0]&&c("take");var f=["Cons",b[1],["Nil"]],e=f,b=b[2];for(--a;"Cons"===b[0]&&0<a;)e[2]=["Cons",b[1],["Nil"]],e=e[2],b=b[2],--a;return f}},drop:function(a){return function(b){if("Nil"===b[0])return b;for("Cons"!==b[0]&&c("drop");"Cons"===b[0]&&0<a;)b=b[2],--a;return b}}}}();
29−Elm=Elm||{};
30−Elm.Maybe=function(){function d(a){return function(d){return"Just"===a[0]?["Cons",a[1],d]:d}}function a(a){return function(d){return function(j){var b=a(d);return"Just"===b[0]?["Cons",b[1],j]:j}}}return{Just:function(a){return["Just",a]},Nothing:["Nothing"],catMaybes:Elm.List.foldr(d)(["Nil"]),isJust:function(a){return"Just"===a[0]},isNothing:function(a){return"Nothing"===a[0]},fromMaybe:function(a){return function(d){return"Just"===d[0]?d[1]:a}},consMaybe:d,mapMaybe:function(g){return Elm.List.foldr(a(g))(["Nil"])},maybe:function(a){return function(d){return function(j){return"Just"===
31−j[0]?d(j[1]):a}}}}}();
32−(function(){for(var d in Elm)this[d]=Elm[d];if(Elm.Dict)throw"Module name collision, 'Dict' is already defined.";Elm.Dict=function(){function a(a){return function(c){return function(b){return function(f){return function(e){return["RBNode",a,c,b,f,e]}}}}}function g(a){return function(){switch(a[0]){case "RBEmpty":return z(Value.str("(min RBEmpty) is not defined"));case "RBNode":switch(a[4][0]){case "RBEmpty":return["Tuple2",a[2],a[3]]}return g(a[4])}throw"Non-exhaustive pattern match in case";}()}
33−function d(a){return function(c){var b;a:{switch(c[0]){case "RBEmpty":b=Nothing;break a;case "RBNode":b=function(){switch(compare(a)(c[2])[0]){case "EQ":return Just(c[3]);case "GT":return d(a)(c[5]);case "LT":return d(a)(c[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";}return b}}function j(a){return function(c){return function(b){var f;a:{switch(b[0]){case "RBEmpty":f=a;break a;case "RBNode":f=function(){switch(compare(c)(b[2])[0]){case "EQ":return b[3];
34−case "GT":return j(a)(c)(b[5]);case "LT":return j(a)(c)(b[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";}return f}}}function b(a){return function(c){return A(d(a)(c))}}function l(c){a:{switch(c[0]){case "RBNode":switch(c[5][0]){case "RBNode":c=a(c[1])(c[5][2])(c[5][3])(a(w)(c[2])(c[3])(c[4])(c[5][4]))(c[5][5]);break a}}c=z(Value.str("rotateLeft of a node without enough children"))}return c}function h(c){a:{switch(c[0]){case "RBNode":switch(c[4][0]){case "RBNode":c=
35−a(c[1])(c[4][2])(c[4][3])(c[4][4])(a(w)(c[2])(c[3])(c[4][5])(c[5]));break a}}c=z(Value.str("rotateRight of a node without enough children"))}return c}function e(c){a:{switch(c[0]){case "Black":c=w;break a;case "Red":c=C;break a}throw"Non-exhaustive pattern match in case";}return c}function c(c){a:{switch(c[0]){case "RBNode":switch(c[4][0]){case "RBNode":switch(c[5][0]){case "RBNode":c=a(e(c[1]))(c[2])(c[3])(a(e(c[4][1]))(c[4][2])(c[4][3])(c[4][4])(c[4][5]))(a(e(c[5][1]))(c[5][2])(c[5][3])(c[5][4])(c[5][5]));
36−break a}}}c=z(Value.str("color_flip called on a RBEmpty or RBNode with a RBEmpty child"))}return c}function f(a){a:switch(a[0]){case "RBNode":switch(a[5][0]){case "RBNode":switch(a[5][1][0]){case "Red":a=l(a);break a}}}a:switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":switch(a[4][4][0]){case "RBNode":switch(a[4][4][1][0]){case "Red":a=h(a);break a}}}}}a:switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":switch(a[5][0]){case "RBNode":switch(a[5][1][0]){case "Red":a=
37−c(a);break a}}}}}return a}function n(c){a:switch(c[0]){case "RBNode":switch(c[1][0]){case "Red":c=a(C)(c[2])(c[3])(c[4])(c[5]);break a}}return c}function m(c){return function(b){return function(e){var h=function(e){var n;a:{switch(e[0]){case "RBEmpty":n=a(w)(c)(b)(y)(y);break a;case "RBNode":n=function(){switch(compare(c)(e[2])[0]){case "EQ":return a(e[1])(e[2])(b)(e[4])(e[5]);case "GT":return a(e[1])(e[2])(e[3])(e[4])(h(e[5]));case "LT":return a(e[1])(e[2])(e[3])(h(e[4]))(e[5])}throw"Non-exhaustive pattern match in case";
38−}();n=f(n);break a}throw"Non-exhaustive pattern match in case";}return n};return n(h(e))}}}function s(c){a:{switch(c[0]){case "RBNode":switch(c[4][0]){case "RBNode":switch(c[4][1][0]){case "Red":c=!0;break a}}}c=!1}return c}function p(c){a:{switch(c[0]){case "RBNode":switch(c[4][0]){case "RBNode":switch(c[4][4][0]){case "RBNode":switch(c[4][4][1][0]){case "Red":c=!0;break a}}}}c=!1}return c}function k(b){if(not(s(b))&&not(p(b))){b=c(b);a:switch(b[0]){case "RBNode":b:switch(b[5][0]){case "RBNode":switch(b[5][4][0]){case "RBNode":switch(b[5][4][1][0]){case "Red":b=
39−c(l(a(b[1])(b[2])(b[3])(b[4])(h(b[5]))));break b}}}break a}}return b}function u(b){return function(e){var d;a:{switch(e[0]){case "RBEmpty":d=y;break a;case "RBNode":if("LT"===compare(b)(e[2])[0]){d=k(e);b:{switch(d[0]){case "RBEmpty":d=z(Value.str("delLT on RBEmpty"));break b;case "RBNode":d=f(a(d[1])(d[2])(d[3])(del(d[4]))(d[5]));break b}break}}else{e=s(e)?h(e):e;b:{switch(e[0]){case "RBNode":switch(e[5][0]){case "RBEmpty":e=eq(b,e[2]);break b}}e=!1}if(e)d=y;else{var e=not,i;b:{switch(d[0]){case "RBNode":switch(d[5][0]){case "RBNode":switch(d[5][1][0]){case "Red":i=
40−!0;break b}}}i=!1}if(e=e(i)){e=not;b:{switch(d[0]){case "RBNode":switch(d[5][0]){case "RBNode":switch(d[5][4][0]){case "RBNode":switch(d[5][4][1][0]){case "Red":i=!0;break b}}}}i=!1}e=e(i)}e&&(d=c(d),d=p(d)?c(h(d)):d);b:{switch(d[0]){case "RBNode":e=eq(b,d[2]);break b}e=!1}if(e)b:{switch(d[0]){case "RBEmpty":d=z(Value.str("delEQ called on a RBEmpty"));break b;case "RBNode":i=g(d[5]);c:{switch(i[0]){case "Tuple2":e=i[1];break c}break}c:{switch(i[0]){case "Tuple2":i=i[2];break c}break}var e=a(d[1])(e)(i)(d[4]),
41−j=function(c){a:{switch(c[0]){case "RBNode":switch(c[4][0]){case "RBEmpty":c=y;break a}}c=k(c);b:{switch(c[0]){case "RBEmpty":c=y;break b;case "RBNode":c=f(a(c[1])(c[2])(c[3])(j(c[4]))(c[5]));break b}throw"Non-exhaustive pattern match in case";}}return c};d=n(j(d[5]));d=f(e(d));break b}break}else b:{switch(d[0]){case "RBEmpty":d=z(Value.str("delGT called on a RBEmpty"));break b;case "RBNode":d=f(a(d[1])(d[2])(d[3])(d[4])(del(d[5])));break b}break}}}break a}throw"Non-exhaustive pattern match in case";
42−}return n(d)}}function x(c){return function(b){a:{switch(b[0]){case "RBEmpty":b=y;break a;case "RBNode":b=a(b[1])(b[2])(c(b[3]))(x(c)(b[4]))(x(c)(b[5]));break a}throw"Non-exhaustive pattern match in case";}return b}}function q(c){return function(a){return function(b){a:{switch(b[0]){case "RBEmpty":b=a;break a;case "RBNode":b=q(c)(c(b[2])(b[3])(q(c)(a)(b[4])))(b[5]);break a}throw"Non-exhaustive pattern match in case";}return b}}}function r(c){return function(a){return function(b){a:{switch(b[0]){case "RBEmpty":b=
43−a;break a;case "RBNode":b=r(c)(c(b[2])(b[3])(r(c)(a)(b[5])))(b[4]);break a}throw"Non-exhaustive pattern match in case";}return b}}}var t=[],v;for(v in Elm.Prelude)0<=t.indexOf(v)||(this[v]=Elm.Prelude[v]);var A=Elm.Maybe.isJust,w=["Red"],C=["Black"],y=["RBEmpty"],B=y,z=console.log;return{empty:B,lookup:d,findWithDefault:j,member:b,insert:m,singleton:function(c){return function(a){return m(c)(a)(y)}},remove:u,map:x,foldl:q,foldr:r,union:function(c){return function(a){return q(m)(a)(c)}},intersect:function(c){return function(a){return q(function(c){return function(f){return function(e){return b(c)(a)?
44−m(c)(f)(e):e}}})(B)(c)}},diff:function(c){return function(a){return q(function(c){return function(){return function(a){return u(c)(a)}}})(c)(a)}},keys:function(c){return q(function(c){return function(){return function(a){return["Cons",c,a]}}})(["Nil"])(c)},values:function(c){return q(function(){return function(c){return function(a){return["Cons",c,a]}}})(["Nil"])(c)},toList:function(c){return q(function(c){return function(a){return function(b){return["Cons",["Tuple2",c,a],b]}}})(["Nil"])(c)},fromList:function(c){return List.foldl(uncurry(m))(B)(c)}}}()})();
45−(function(){for(var d in Elm)this[d]=Elm[d];Elm.Set=function(){var a=[],d;for(d in Elm.Prelude)0<=a.indexOf(d)||(this[d]=Elm.Prelude[d]);a=Dict.empty;d=Dict.remove;var i=Dict.member,j=Dict.union,b=Dict.intersect,l=Dict.diff,h=Dict.keys,e=List.foldl(function(c){return function(a){return Dict.insert(c)(["Tuple0"])(a)}})(a);return{empty:a,singleton:function(c){return Dict.singleton(c)(["Tuple0"])},insert:function(c){return Dict.insert(c)(["Tuple0"])},remove:d,member:i,union:j,intersect:b,diff:l,toList:h,
46−fromList:e,foldl:function(c){return Dict.foldl(function(a){return function(){return function(b){return c(a)(b)}}})},foldr:function(c){return Dict.foldr(function(a){return function(){return function(b){return c(a)(b)}}})},map:function(c){return function(a){a=h(a);return e(List.map(c)(a))}}}}()})();Elm=Elm||{};
47−Elm.Char=function(){function d(a,b){return function(d){d=d.charCodeAt(0);return a<=d&&d<=b}}var a=d(48,57),g=d(97,102),i=d(65,70);return{fromCode:function(a){return String.fromCharCode(a)},toCode:function(a){return a.charCodeAt(0)},toUpper:function(a){return a.toUpperCase()},toLower:function(a){return a.toLowerCase()},toLocaleUpper:function(a){return a.toLocaleUpperCase()},toLocaleLower:function(a){return a.toLocaleLowerCase()},isLower:d(97,122),isUpper:d(65,90),isDigit:a,isOctDigit:d(48,55),isHexDigit:function(d){return a(d)||
48−g(d)||i(d)}}}();Elm=Elm||{};
49−Elm.Color=function(){return{rgba:function(d){return function(a){return function(g){return function(i){return["Color",d,a,g,i]}}}},rgb:function(d){return function(a){return function(g){return["Color",d,a,g,1]}}},red:["Color",255,0,0,1],green:["Color",0,255,0,1],blue:["Color",0,0,255,1],yellow:["Color",255,255,0,1],cyan:["Color",0,255,255,1],magenta:["Color",255,0,255,1],black:["Color",0,0,0,1],white:["Color",255,255,255,1],gray:["Color",128,128,128,1],grey:["Color",128,128,128,1],complement:function(d){var a,
50−g=d[1]/255;a=d[2]/255;var i=d[3]/255,d=Math.max(g,a,i),j=Math.min(g,a,i),j=d-j,b=0;0===j?b=0:d===g?b=(a-i)/j%6:d===a?b=(i-g)/j+2:d===i&&(b=(g-a)/j+4);a=60*b;var g=d*(0===d?0:j/d),b=(a+180)%360/60,l=g*(1-Math.abs(b%2-1)),j=i=a=0;0<=b&&1>b?(a=g,i=l,j=0):1<=b&&2>b?(a=l,i=g,j=0):2<=b&&3>b?(a=0,i=g,j=l):3<=b&&4>b?(a=0,i=l,j=g):4<=b&&5>b?(a=l,i=0,j=g):5<=b&&6>b&&(a=g,i=0,j=l);d-=g;return["Color",Math.round(255*(a+d)),Math.round(255*(i+d)),Math.round(255*(j+d)),1]},extract:function(d){return 1===d[4]?"rgb("+
51−d[1]+","+d[2]+","+d[3]+")":"rgba("+d[1]+","+d[2]+","+d[3]+","+d[4]+")"}}}();
52−var Collage=function(){function d(a,c){var b=c.length-1;if(!(0>=b))for(a.moveTo(c[b][1],c[b][2]);b--;)a.lineTo(c[b][1],c[b][2])}function a(a,c,b,d){0===a.length&&(a=[8,4]);var h=d.length-1;if(!(0>=h)){var g=d[h][1],i=d[h][2],k=0,j=0,l=0,q=0,r=0,t=0,v=a.length,A=!0,w=a[0];for(c.moveTo(g,i);h--;){k=d[h][1];j=d[h][2];l=k-g;q=j-i;for(r=Math.sqrt(l*l+q*q);w<=r;)g+=l*w/r,i+=q*w/r,c[A?"lineTo":"moveTo"](g,i),l=k-g,q=j-i,r=Math.sqrt(l*l+q*q),A=!A,t=(t+1)%v,w=a[t];0<r&&(c[A?"lineTo":"moveTo"](k,j),w-=r);g=
53−k;i=j}}c.strokeStyle=Elm.Color.extract(b);c.stroke()}function g(b,c,f,n,g){c.clearRect(0,0,f,n);for(f=g.length;f--;){var i=g[f],p=b,n=c,k=i[1],j=i[2],l=i[3][1],q=i[3][2],i=i[4];n.save();(0!==l||0!==q)&&n.translate(l,q);k!==~~k&&n.rotate(2*Math.PI*k);1!==j&&n.scale(j,j);n.beginPath();switch(i[0]){case "FLine":a:switch(p=n,k=i,i=k[3][1],k[1][0]){case "Solid":k=k[2];d(p,i);p.strokeStyle=Elm.Color.extract(k);p.stroke();break;case "Dotted":a([3,3],p,k[2],i);break a;case "Dashed":a([8,4],p,k[2],i);break a;
54−case "Custom":a(k[1][1],p,k[2],i)}break;case "FShape":a:switch(l=p,j=n,p=i[1],k=i[2],i=i[3][1],p[0]){case "Filled":p=j;d(p,i);p.fillStyle=Elm.Color.extract(k);p.fill();break a;case "Outlined":p=j;d(p,i);p.strokeStyle=Elm.Color.extract(k);p.stroke();break a;case "Textured":k=l;p=p[1];l=new Image;l.src=h.castStringToJSString(p);l.onload=k;d(j,i);j.fillStyle=j.createPattern(l,"repeat");j.fill();break a;case "CustomOutline":a(p[1],j,k,i)}break;case "FImage":k=n,j=i[1],l=i[2],i=i[3],q=new Image,q.onload=
55−p,q.src=h.castStringToJSString(i),k.drawImage(q,-j/2,-l/2,j,l)}n.restore()}}function i(a,c,b){var d=Render.newElement("canvas");d.style.width=~~a+"px";d.style.height=~~c+"px";d.style.display="block";d.width=~~a;d.height=~~c;if(d.getContext){var h=d.getContext("2d"),a=d.width,c=d.height;g(function(){g(this,h,a,c,b)},h,a,c,b);return d}d.innerHTML="Your browser does not support the canvas element.";return d}function j(a,c,b,d,h,i,g){var k=Render.render(g),b="translate("+(h-g[3]/2)+"px,"+(i-g[4]/2)+"px) "+
56−(1===d?"":"scale("+d+","+d+")")+" "+(b===~~b?"":"rotate("+360*b+"deg)");k.style.transform=b;k.style.msTransform=b;k.style.MozTransform=b;k.style.webkitTransform=b;k.style.OTransform=b;b=Render.newElement("div");Render.addTo(b,k);b.style.width=~~a+"px";b.style.height=~~c+"px";b.style.overflow="hidden";return b}function b(a,c,b){if(!Value.eq(b,c)){var d=a.style.width.slice(0,-2)-0,h=a.style.height.slice(0,-2)-0;if("object"===typeof b[0]){if("object"===typeof c[0]&&a.getContext){var l=a.getContext("2d");
57−return g(function(){g(this,l,d,h,b)},l,d,h,b)}c=i(d,h,b);c.style.position="absolute";return a.parentNode.replaceChild(c,a)}c=j(d,h,b[1],b[2],b[3][1],b[3][2],b[4][1]);c.style.position="absolute";return a.parentNode.replaceChild(c,a)}}function l(a,c,b,d,h){var i=0,g,k=(a[1]-d[1])/b,a=(a[2]-d[2])/b;0!==c&&(c*=-2*Math.PI,b=k*Math.cos(c)-a*Math.sin(c),a=k*Math.sin(c)+a*Math.cos(c),k=b);if(0===h.length)return!1;g=h[0];for(b=h.length-1;b--;){c=h[b];d=g[1];g=g[2];var j=c[1],l=c[2];if(g<l)var q=g,r=l;else q=
58−l,r=g;if(d<j)var t=d,v=j;else t=j,v=d;q<a&&a<=r&&k<=v&&(k<=t||k<=(a-g)*(j-d)/(l-g)+d)&&++i;g=c}return 1===i%2}var h=Elm.JavaScript;return{collage:function(a,c,b){if(0===b.length)return i(a,c,[]);for(var d=Array(b.length),h=b.length;h--;){var g=b[h];d[h]="string"===typeof g[0]?j(a,c,g[1],g[2],g[3][1],g[3][2],g[4][1]):i(a,c,g)}return 1===b.length?d[0]:Render.flowWith(Render.goIn,function(c){return c},d)},updateCollage:function(a,c,f){if(1===f.length)return b(a,c[0],f[0]);for(var a=a.childNodes,d=a.length,
59−h=d;h--;)b(a[d-h-1],c[h],f[h])},insideForm:function(a){return function(c){var b=a[1],d=a[2];if(6>c.length){var h=c[3][1],g=c[3][2],i=0,j=c[2];switch(c[4][0]){case "FShape":for(var u=c[4][3][1],x=u.length;--x;)var q=u[x],i=Math.max(i,q[1]*q[1]+q[2]*q[2]);i*=j*j;break;case "FImage":u=j*c[4][1]/2;j=j*c[4][2]/2;i=u*u+j*j;break;case "FElement":u=j*c[4][1][3]/2,j=j*c[4][1][4]/2,i=u*u+j*j}c.push(function(c,a){var b=c-h,f=a-g;return b*b+f*f<i+1})}if(!c[5](b,d))return!1;var r,t;switch(c[4][0]){case "FShape":return l(a,
60−c[1],c[2],c[3],c[4][3][1]);case "FLine":return!1;case "FImage":r=c[4][1]/2;t=c[4][2]/2;break;case "FElement":r=c[4][1][3]/2,t=c[4][1][4]/2}return l(a,c[1],c[2],c[3],[[null,r,t],[null,-r,t],[null,-r,-t],[null,r,-t],[null,r,t]])}}}}(),Elm=Elm||{};
61−Elm.Graphics=function(){function d(c){return function(a){return["Position",c,a]}}function a(c){return function(a){return["EText",c,a]}}function g(c){return function(a){return["EFlow",c,k.castListToJSArray(a)]}}function i(c){return["Line",k.castListToJSArray(c)]}function j(c){return function(a){var b=k.castListToJSArray(c);0<b.length&&b.push(b[0]);return["Shape",b,a]}}function b(c){return function(a){return function(b){return function(f){return["Form",c,a,b,f]}}}}function l(c){return function(a){return function(b){return["FLine",
62−c,a,b]}}}function h(c){return function(a){return function(b){return["FShape",c,a,b]}}}function e(c,a,b,f,d,e){return["Element",Guid.guid(),c,a,b,f,d,e]}function c(c,a,b){return["Element",Guid.guid(),c,a,b,1,Nothing,Nothing]}function f(c){return~~c[3]}function n(c){return~~c[4]}function m(a){return function(b){return function(f){return c(["EImage",k.castStringToJSString(f)],a,b)}}}function s(a){return function(b){return c(A,a,b)}}function p(c){return function(a){return function(b){var f=map(function(b){return["Tuple2",
63−c/2*cos(2*(pi/50)*b),a/2*sin(2*(pi/50)*b)]}),d=49,e=["Nil"];if(0<=d){do e=["Cons",d,e];while(0<d--)}return j(f(e))(b)}}}var k=Elm.JavaScript,u=["DRight"],x=["DDown"],q=["DOut"],r=["Near"],t=["Mid"],v=["Far"],A=["EEmpty"],w=["Solid"],C=["Dotted"],y=["Dashed"],B=["Filled"],z=["Outlined"],D=d(r)(r),E=d(v)(r),F=d(r)(v),G=d(v)(v),H=d(r)(t),I=d(v)(t),r=d(t)(r),v=d(t)(v),t=d(t)(t);return{left:["DLeft"],right:u,down:x,up:["DUp"],inward:["DIn"],outward:q,topLeft:D,topRight:E,bottomLeft:F,bottomRight:G,midLeft:H,
64−midRight:I,midTop:r,midBottom:v,middle:t,middleAt:function(c){return function(a){return["PositionAt",c,a]}},topLeftAt:function(c){return function(a){return["PositionTL",c,a]}},topRightAt:function(c){return function(a){return["PositionTR",c,a]}},bottomLeftAt:function(c){return function(a){return["PositionBL",c,a]}},bottomRightAt:function(c){return function(a){return["PositionBR",c,a]}},absolute:function(c){return["Absolute",c]},relative:function(c){return["Relative",c]},width:function(c){return function(a){var b=
65−a[2];switch(b[0]){case "EImage":case "EVideo":return e(a[2],c,a[4]*c/a[3],a[5],a[6],a[7]);case "EText":return b=Value.getTextSize(c,a[4],b[2]),e(a[2],c,b[1],a[5],a[6],a[7])}return e(a[2],c,a[4],a[5],a[6],a[7])}},height:function(a){return function(c){switch(c[2][0]){case "EImage":case "EVideo":return e(c[2],c[3]*a/c[4],a,c[5],c[6],c[7])}return e(c[2],c[3],a,c[5],c[6],c[7])}},size:function(c){return function(a){return function(b){return e(b[2],c,a,b[5],b[6],b[7])}}},opacity:function(c){return function(a){return e(a[2],
66−a[3],a[4],c,a[6],a[7])}},color:function(c){return function(a){return e(a[2],a[3],a[4],a[5],Just(c),a[7])}},link:function(a){return function(c){return e(c[2],c[3],c[4],c[5],c[6],Just(k.castStringToJSString(a)))}},widthOf:f,heightOf:n,sizeOf:function(c){return["Tuple2",~~c[3],~~c[4]]},text:function(b){var f=Value.getTextSize(0,0,b);return c(a("left")(b),f[0],f[1])},asText:function(b){var b=monospace(Value.toText(Value.show(b))),f=Value.getTextSize(0,0,b);return c(a("left")(b),f[0],f[1])},plainText:function(b){var b=
67−Value.toText(b),f=Value.getTextSize(0,0,b);return c(a("left")(b),f[0],f[1])},centeredText:function(b){var f=Value.getTextSize(0,0,b);return c(a("center")(b),f[0],f[1])},justifiedText:function(b){var f=Value.getTextSize(0,0,b);return c(a("justify")(b),f[0],f[1])},rightedText:function(b){var f=Value.getTextSize(0,0,b);return c(a("right")(b),f[0],f[1])},image:m,images:function(c){var a=Elm.Signal.constant(s(0)(0)),c=Elm.Signal.lift(function(c){var c=k.castStringToJSString(c),b=new Image;b.onload=function(){Dispatcher.notify(a.id,
68−m(this.width)(this.height)(c))};b.src=c})(c);return Elm.Signal.lift2(function(c){return function(){return c}})(a)(c)},video:function(a){return function(b){return function(f){return c(["EVideo",k.castStringToJSString(f)],a,b)}}},fittedImage:function(a){return function(b){return function(f){return c(["EFittedImage",k.castStringToJSString(f)],a,b)}}},flow:function(a){return function(b){var d;d=map(f)(b);a:{switch(a[0]){case "DLeft":d=sum(d);break a;case "DRight":d=sum(d);break a}d=maximum(d)}var e;e=
69−map(n)(b);a:{switch(a[0]){case "DDown":e=sum(e);break a;case "DUp":e=sum(e);break a}e=maximum(e)}return c(g(a)(b),d,e)}},above:function(a){return function(b){return c(g(x)(["Cons",a,["Cons",b,["Nil"]]]),max(~~a[3])(~~b[3]),~~a[4]+~~b[4])}},below:function(a){return function(b){return c(g(x)(["Cons",b,["Cons",a,["Nil"]]]),max(~~a[3])(~~b[3]),~~a[4]+~~b[4])}},beside:function(a){return function(b){return c(g(u)(["Cons",a,["Cons",b,["Nil"]]]),~~a[3]+~~b[3],max(~~a[4])(~~b[4]))}},layers:function(a){return c(g(q)(a),
70−maximum(map(f)(a)),maximum(map(n)(a)))},collage:function(a){return function(b){return function(f){return c(["ECollage",a,b,Value.groupForms(f)],a,b)}}},spacer:s,container:function(a){return function(b){return function(f){return function(d){return c(["EContainer",f,d],a,b)}}}},line:i,segment:function(a){return function(c){return i(["Cons",a,["Cons",c,["Nil"]]])}},polygon:j,rect:function(a){return function(c){return function(b){return j(["Cons",["Tuple2",0-a/2,0-c/2],["Cons",["Tuple2",0-a/2,c/2],["Cons",
71−["Tuple2",a/2,c/2],["Cons",["Tuple2",a/2,0-c/2],["Nil"]]]]])(b)}}},oval:p,circle:function(a){return p(2*a)(2*a)},ngon:function(a){return function(c){return function(b){var f=toFloat(a),d=map(function(a){return["Tuple2",c*cos(2*(pi/f)*a),c*sin(2*(pi/f)*a)]}),e=a-1,h=["Nil"];if(0<=e){do h=["Cons",e,h];while(0<e--)}return j(d(h))(b)}}},solid:function(a){return function(c){return b(0)(1)(["Tuple2",0,0])(l(w)(a)(c))}},dotted:function(a){return function(c){return b(0)(1)(["Tuple2",0,0])(l(C)(a)(c))}},dashed:function(a){return function(c){return b(0)(1)(["Tuple2",
72−0,0])(l(y)(a)(c))}},customLine:function(a){return function(c){return function(f){return b(0)(1)(["Tuple2",0,0])(l(["Custom",k.castListToJSArray(a)])(c)(f))}}},filled:function(a){return function(c){return b(0)(1)(c[2])(h(B)(a)(c))}},outlined:function(a){return function(c){return b(0)(1)(c[2])(h(z)(a)(c))}},customOutline:function(a){return function(c){return function(f){return b(0)(1)(f[2])(h(["CustomOutline",k.castListToJSArray(a)])(c)(f))}}},textured:function(a){return function(c){return b(0)(1)(c[2])(h(["Textured",
73−a])(null)(c))}},sprite:function(a){return function(c){return function(f){return function(d){return b(0)(1)(d)(["FImage",c,f,k.castStringToJSString(a)])}}}},toForm:function(a){return function(c){return b(0)(1)(a)(["FElement",c])}},rotate:function(a){return function(c){a:{switch(c[0]){case "Form":var f=c[2],d=c[3],e=c[4],c=b(a+c[1])(f)(d)(e);break a}throw"Non-exhaustive pattern match in case";}return c}},scale:function(a){return function(c){return b(c[1])(a*c[2])(c[3])(c[4])}},move:function(a){return function(c){return function(f){var d;
74−a:{switch(f[0]){case "Form":d=f[1];var e=f[2],h=f[3],f=f[4];switch(h[0]){case "Tuple2":var g=h[1],h=h[2];d=b(d)(e)(["Tuple2",a+g,c+h])(f);break a}}throw"Non-exhaustive pattern match in case";}return d}}},isWithin:Collage.insideForm}}();Elm=Elm||{};
75−Elm.Text=function(){function d(a){return Value.toText(a)}var a=function(a){return function(b){return"<"+a+' style="padding:0;margin:0">'+b+"</"+a+">"}},g=function(a,b){return function(d){return"<span style='"+a+":"+b+"'>"+d+"</span>"}},i=function(a){a=Elm.JavaScript.castStringToJSString(a);return g("font-family",a)},j=a("h1"),b=g("font-style","italic"),a=a("b"),l=g("text-decoration","underline"),h=g("text-decoration","overline"),e=g("text-decoration","line-through");return{fromString:d,toText:d,header:j,
76−height:function(a){return g("font-size",a+"em")},italic:b,bold:a,underline:l,overline:h,strikeThrough:e,monospace:i("monospace"),typeface:i,color:function(a){return g("color",Elm.Color.extract(a))},link:function(a){return function(b){return"<a href='"+d(a)+"'>"+b+"</a>"}}}}();
77−var Render=function(){function d(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a}function a(a){return a}function g(a){a.style.styleFloat="left";a.style.cssFloat="left";return a}function i(a){a.style.position="absolute";return a}function j(a,b,e){for(var h=d("div"),g=e.length;g--;){var i=a(b(e[g]));h.appendChild(i)}return h}function b(a){switch(a[0]){case "Absolute":return a[1]+"px";case "Relative":return 100*a[1]+"%"}}function l(a,f){f.style.position="absolute";f.style.margin=
78−"auto";switch(a[0]){case "Position":"Far"!==a[1][0]&&(f.style.left=0);"Near"!==a[1][0]&&(f.style.right=0);"Far"!==a[2][0]&&(f.style.top=0);"Near"!==a[2][0]&&(f.style.bottom=0);break;case "PositionAt":f.style.top=b(a[2]);f.style.left=b(a[1]);var d="translate("+-elem[3]/2+"px,"+-elem[4]/2+"px)";f.style.transform=d;f.style.msTransform=d;f.style.MozTransform=d;f.style.webkitTransform=d;f.style.OTransform=d;break;default:d=a[0].slice(-2),f.style["T"===d[0]?"top":"bottom"]=b(a[2]),f.style["L"===d[1]?"left":
79−"right"]=b(a[1])}}function h(c){var b={};switch(c[2][0]){case "EText":var b=c[2][1],e=c[2][2],m=d("div");m.innerHTML=e;m.style.textAlign=b;b=m;break;case "EImage":b=c[2][1];e=d("img");e.src=b;e.name=b;e.style.display="block";b=e;break;case "EVideo":m=c[2][1];b=d("video");b.controls="controls";e=d("source");e.src=m;m=m.split(".");e.type="video/"+m[m.length-1];b.appendChild(e);b.style.display="block";break;case "EFittedImage":var s=c[3],p=c[4],b=c[2][1],e=d("div");e.style.width=s+"px";e.style.height=
80−p+"px";e.style.position="relative";e.style.overflow="hidden";var k=d("img");k.onload=function(){k.style.position="absolute";k.style.margin="auto";var a=s,b=p;s/p>this.width/this.height?b=Math.round(this.height*s/this.width):a=Math.round(this.width*p/this.height);k.style.width=a+"px";k.style.height=b+"px";k.style.left=(s-a)/2+"px";k.style.top=(p-b)/2+"px"};k.src=b;k.name=b;e.appendChild(k);b=e;break;case "EFlow":a:{b=c[2][2];switch(c[2][1][0]){case "DDown":b=b.slice(0).reverse();case "DUp":b=j(a,h,
81−b);break a;case "DRight":b=b.slice(0).reverse();case "DLeft":b=j(g,h,b);break a;case "DOut":b=b.slice(0).reverse();case "DIn":b=j(i,h,b);break a}b=void 0}break;case "ECollage":b=Collage.collage(c[2][1],c[2][2],c[2][3]);break;case "EEmpty":b=d("div");break;case "EContainer":e=c[2][1];b=h(c[2][2]);l(e,b);e=d("div");e.style.position="relative";e.style.overflow="hidden";e.appendChild(b);b=e;break;case "EHtml":b=c[2][1];"button"!==b.type&&(e=Value.getExcess(b),c[3]-=e[0],c[4]-=e[1]);break;case "EExternalHtml":b=
82−d("div"),b.appendChild(c[2][1])}b.id=c[1];b.style.width=~~c[3]+"px";b.style.height=~~c[4]+"px";1!==c[5]&&(b.style.opacity=c[5]);"Just"===c[6][0]&&(b.style.backgroundColor=Elm.Color.extract(c[6][1]));return"Just"===c[7][0]?(e=d("a"),e.href=c[7][1],e.appendChild(b),e):b}function e(b,d,j){"A"===b.tagName&&(b=b.firstChild);if(d[1]!==j[1]){if(d[2][0]!==j[2][0])return b.parentNode.replaceChild(h(j),b);var m=j[2],s=d[2];switch(m[0]){case "EText":m[1]!==s[1]&&(b.style.textAlign=m[1]);m[2]!==s[2]&&(b.innerHTML=
83−m[2]);break;case "EImage":m[1]!==s[1]&&(b.src=m[1]);break;case "EVideo":case "EFittedImage":if(!Value.eq(m,s)||j[3]!==d[3]||j[4]!==d[4])return b.parentNode.replaceChild(h(j),b);break;case "ECollage":if(m[1]!==s[1]||m[2]!==s[2]||m[3].length!==s[3].length)return b.parentNode.replaceChild(h(j),b);Collage.updateCollage(b,s[3],m[3]);break;case "EFlow":if(m[1]!==s[1])return b.parentNode.replaceChild(h(j),b);var p=m[2],k=b.childNodes;if(p.length!==k.length)return b.parentNode.replaceChild(h(j),b);var s=
84−s[2],u={};switch(m[1][0]){case "DDown":case "DUp":u=a;break;case "DRight":case "DLeft":u=g;break;case "DOut":case "DIn":u=i}for(m=k.length;m--;)e(k[m],s[m],p[m]),u(k[m]);break;case "EContainer":e(b.childNodes[0],s[2],m[2]);l(m[1],b.childNodes[0]);break;case "EHtml":j[1]!==d[1]&&(p=h(j),b.parentNode.replaceChild(p,b),b=p);"button"!==p.type&&(m=Value.getExcess(b),j[3]-=m[0],j[4]-=m[1]);break;case "EExternalHtml":j[1]!==d[1]&&b.parentNode.replaceChild(h(j),b)}j[3]!==d[3]&&(b.style.width=~~j[3]+"px");
85−j[4]!==d[4]&&(b.style.height=~~j[4]+"px");j[5]!==d[5]&&(b.style.opacity=j[5]);2===j[6].length&&(m=Elm.Color.extract(j[6][1]),m!==b.style.backgroundColor&&(b.style.backgroundColor=m));if(2===j[7].length&&(1===d[7].length||j[7][1]!==d[7][1]))b.parentNode.href=j[7][1];j[1]=d[1]}}return{render:h,update:e,addTo:function(a,b){a.appendChild(b)},newElement:d,flowWith:j,goIn:i}}(),Elm=Elm||{};
86−Elm.Signal=function(){var d=function(a,b,d){for(var h=a.kids,g=h.length;g--;)h[g].recv(b,d,a.id)},a=function(a){this.id=Guid.guid();this.value=a;this.kids=[];this.defaultNumberOfKids=0;this.recv=function(a,b,e){if(b=b===this.id)this.value=e;d(this,a,b);return b};Dispatcher.inputs.push(this)},g=function(a,b){this.id=Guid.guid();this.value=null;this.kids=[];this.count=0;this.changed=!1;b.reverse();this.recalc=function(){for(var d=a,f=b.length;f--;)d=d(b[f].value);this.value=d};this.recalc();this.recv=
87−function(a,e){this.count+=1;e&&(this.changed=!0);this.count==b.length&&(this.changed&&this.recalc(),d(this,a,this.changed),this.changed=!1,this.count=0)};for(var f=b.length;f--;)b[f].kids.push(this)},i=function(a,b,f,h){this.id=Guid.guid();this.value=f?b(h.value):b;this.kids=[];this.recv=function(b,c){c&&(this.value=a(h.value)(this.value));d(this,b,c)};h.kids.push(this)},j=function(a,b,f){this.id=Guid.guid();this.value=a(f.value)?b:f.value;this.kids=[];this.recv=function(b,c){var h=c&&!a(f.value);
88−h&&(this.value=f.value);d(this,b,h)};f.kids.push(this)},b=function(a){this.id=Guid.guid();this.value=a.value;this.kids=[];this.recv=function(b,f){var h=f&&!eq(this.value,a.value);h&&(this.value=a.value);d(this,b,h)};a.kids.push(this)},l=function(a){return function(b){return function(d){d=new g(function(a){return function(b){return[a,b]}},[a,d]);d=new j(function(a){return a[0]},[!0,b],d);return new g(function(a){return a[1]},[d])}}},h=function(a,b){this.id=Guid.guid();this.value=b.value;this.kids=
89−[];this.count=0;this.changed=!1;this.recv=function(f,h,g){g===a.id&&(this.changed=h);this.count+=1;2==this.count&&(this.changed&&(this.value=b.value),d(this,f,this.changed),this.count=0,this.changed=!1)};a.kids.push(this);b.kids.push(this)};return{constant:function(b){return new a(b)},lift:function(a){return function(b){return new g(a,[b])}},lift2:function(a){return function(b){return function(d){return new g(a,[b,d])}}},lift3:function(a){return function(b){return function(d){return function(h){return new g(a,
90−[b,d,h])}}}},lift4:function(a){return function(b){return function(d){return function(h){return function(i){return new g(a,[b,d,h,i])}}}}},foldp:function(a){return function(b){return function(d){return new i(a,b,!1,d)}}},foldp_:function(a){return function(b){return function(d){return new i(a,b,!0,d)}}},foldp1:function(a){return function(b){return new i(a,function(a){return a},!0,b)}},count:function(a){return new i(function(){return function(a){return a+1}},0,!1,a)},keepIf:function(a){return function(b){return function(d){return new j(function(b){return!a(b)},
91−b,d)}}},dropIf:function(a){return function(b){return function(d){return new j(a,b,d)}}},keepWhen:function(a){return l(new g(function(a){return!a},[a]))},dropWhen:l,dropRepeats:function(a){return new b(a)},sampleOn:function(a){return function(b){return new h(a,b)}}}}();
92−var Dispatcher=function(){function d(a){if(!a.hasOwnProperty("defaultNumberOfKids"))return!0;var g=a.kids.length;if(0==g)return!1;if(g>a.defaultNumberOfKids)return!0;for(var h=!1;g--;)h=h||d(a.kids[g]);return h}var a=null,g=0,i=[],j=null;return{initialize:function(){a=Elm.main();a.hasOwnProperty("recv")||(a=Elm.Signal.constant(a));j=a.value;for(var b=[],g=i.length;g--;)d(i[g])&&b.push(i[g]);i=b;document.getElementById("content").appendChild(Render.render(j));b=document.getElementById("widthChecker").offsetWidth;
93−b!==window.innerWidth&&Dispatcher.notify(Window.dimensions.id,Value.Tuple(b,window.innerHeight));a=Elm.Signal.lift(function(a){var b=document.getElementById("content");Render.update(b.firstChild,j,a);return j=a})(a)},notify:function(a,d){g+=1;for(var h=!1,e=i.length;e--;)h=i[e].recv(g,a,d)||h;return h},inputs:i}}();
94−Elm.HTTP=function(){function d(a){return function(d){return function(c){return function(f){return{"0":"Request",length:1,verb:b.castStringToJSString(a),url:b.castStringToJSString(d),data:null===c?null:b.castStringToJSString(c),headers:f}}}}}function a(a){return d("GET")(a)(null)(["Nil"])}function g(a,d){return function(c){if(""!==c.url){var f={value:["Waiting"]};a.push(f);var g=null;window.ActiveXObject&&(g=new ActiveXObject("Microsoft.XMLHTTP"));window.XMLHttpRequest&&(g=new XMLHttpRequest);g.onreadystatechange=
95−function(){4===g.readyState&&(f.value=200===g.status?["Success",l(g.responseText)]:["Failure",g.status,l(g.statusText)],setTimeout(function(){i(a,d)},0))};g.open(c.verb,c.url,!0);Elm.List.map(function(a){g.setRequestHeader(b.castStringToJSString(a[1]),b.castStringToJSString(a[2]))})(c.headers);g.send(c.data)}}}function i(a,b){0<a.length&&(Dispatcher.notify(b.id,a[0].value),"Waiting"!==a[0].value[0]&&(a.shift(),setTimeout(function(){i(a,b)},0)))}function j(a){var b=Elm.Signal.constant(["Waiting"]),
96−a=Elm.Signal.lift(g([],b))(a);return Elm.Signal.lift2(function(a){return function(){return a}})(b)(a)}var b=Elm.JavaScript,l=Elm.JavaScript.castJSStringToString;return{get:a,post:function(a){return function(b){return d("POST")(a)(b)(["Nil"])}},request:d,send:j,sendGet:function(b){return j(Elm.Signal.lift(a)(b))}}}();
97−Elm.Input=function(){var d=Elm.JavaScript,a=Elm.JavaScript.castJSStringToString,g=function(b,g){b.placeholder=d.castStringToJSString(g);var h=Elm.Signal.constant(["Nil"]);Value.addListener(b,"keyup",function(){Dispatcher.notify(h.id,a(b.value));b.focus()});b.style.padding="1px";return Value.Tuple(Value.wrap(b),h)},i=function(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a},j=function(a){for(var d=i("select"),g=[];"Cons"===a[0];){var e=i("option"),c=Value.toText(a[1][1]);
98−e.value=c;e.innerHTML=c;d.appendChild(e);g.push(a[1][2]);a=a[2]}var f=Elm.Signal.constant(g[0]);Value.addListener(d,"change",function(){Dispatcher.notify(f.id,g[d.selectedIndex])});return Value.Tuple(Value.wrap(d),f)};return{textArea:function(a){return function(d){var h=i("textarea");h.rows=d;h.cols=a;return g(h,"")}},textField:function(a){var d=i("input");d.type="text";return g(d,a)},password:function(a){var d=i("input");d.type="password";return g(d,a)},checkbox:function(a){var d=i("input");d.type=
99−"checkbox";d.checked=a;var g=Elm.Signal.constant(a);Value.addListener(d,"change",function(){Dispatcher.notify(g.id,d.checked)});return Value.Tuple(Value.wrap(d),g)},dropDown:j,stringDropDown:function(a){return j(Elm.List.map(function(a){return Value.Tuple(a,a)})(a))},button:function(a){var g=i("input");g.type="button";g.value=d.castStringToJSString(a);var h=Elm.Signal.constant(!1);Value.addListener(g,"click",function(){Dispatcher.notify(h.id,!0);Dispatcher.notify(h.id,!1)});return Value.Tuple(Value.wrap(g),
100−h)}}}();
101−Elm.Keyboard={Raw:function(){function d(a,g){return"Nil"===g[0]?g:g[1]===a?g[2]:["Cons",g[1],d(a,g[2])]}var a=Elm.Signal.constant(["Nil"]),g=Elm.Signal.constant(["Nothing"]);Value.addListener(document,"keydown",function(d){var g;a:{for(g=a.value;"Nil"!==g[0];){if(g[1]===d.keyCode){g=!0;break a}g=g[2]}g=!1}g||Dispatcher.notify(a.id,["Cons",d.keyCode,a.value])||this.removeEventListener("keydown",arguments.callee,!1)});Value.addListener(document,"keyup",function(g){var j=d(g.keyCode,a.value);Dispatcher.notify(a.id,
102−j)||this.removeEventListener("keyup",arguments.callee,!1)});Value.addListener(window,"blur",function(d){Dispatcher.notify(a.id,["Nil"])||this.removeEventListener("blur",arguments.callee,!1)});Value.addListener(document,"keypress",function(a){var d=Dispatcher.notify(g.id,["Just",a.charCode||a.keyCode]);Dispatcher.notify(g.id,["Nothing"]);d||this.removeEventListener("keypress",arguments.callee,!1)});return{keysDown:a,charPressed:g}}()};
103−Elm.Mouse=function(){function d(a){var b=0,c=0;a||(a=window.event);if(a.pageX||a.pageY)b=a.pageX,c=a.pageY;else if(a.clientX||a.clientY)b=a.clientX+document.body.scrollLeft+document.documentElement.scrollLeft,c=a.clientY+document.body.scrollTop+document.documentElement.scrollTop;return Value.Tuple(b,c)}var a=Elm.Signal.constant(Value.Tuple(0,0));a.defaultNumberOfKids=2;var g=Elm.Signal.lift(function(a){return a[1]})(a);g.defaultNumberOfKids=0;var i=Elm.Signal.lift(function(a){return a[2]})(a);i.defaultNumberOfKids=
104−0;var j=Elm.Signal.constant(!1),b=Elm.Signal.constant(!1),l=Elm.Signal.constant(Value.Tuple());Value.addListener(document,"click",function(a){var d=Dispatcher.notify(b.id,!0),c=Dispatcher.notify(l.id,Value.Tuple());Dispatcher.notify(b.id,!1);!d&&!c&&this.removeEventListener("click",arguments.callee,!1)});Value.addListener(document,"mousedown",function(a){Dispatcher.notify(j.id,!0)||this.removeEventListener("mousedown",arguments.callee,!1)});Value.addListener(document,"mouseup",function(a){Dispatcher.notify(j.id,
105−!1)||this.removeEventListener("mouseup",arguments.callee,!1)});Value.addListener(document,"mousemove",function(b){Dispatcher.notify(a.id,d(b))||this.removeEventListener("mousemove",arguments.callee,!1)});return{position:a,x:g,y:i,isClicked:b,isDown:j,clicks:l,isClickedOn:function(a){var a=Render.render(a),b=Elm.Signal.constant(!1);Value.addListener(a,"click",function(){Dispatcher.notify(b.id,!0);Dispatcher.notify(b.id,!1)});return Value.Tuple(Value.wrap(a),b)}}}();
106−Elm.Random=function(){return{inRange:function(d){return function(a){return Elm.Signal.constant(Math.floor(Math.random()*(a-d+1))+d)}},randomize:function(d){return function(a){return function(g){return Elm.Signal.lift(function(){return Math.floor(Math.random()*(a-d+1))+d})(g)}}}}}();
107−Elm.Time=function(){return{every:function(d){var d=1E3*d,a=Elm.Signal.constant(0),g=0;setInterval(function(){g+=d;Dispatcher.notify(a.id,g/1E3)},d);return a},after:function(d){var d=1E3*d,a=Elm.Signal.constant(!1);setTimeout(function(){Dispatcher.notify(a.id,!0)},d);return a},before:function(d){var d=1E3*d,a=Elm.Signal.constant(!0);setTimeout(function(){Dispatcher.notify(a.id,!1)},d);return a}}}();
108−Elm.Window=function(){var d=Elm.Signal.constant(Value.Tuple(window.innerWidth,window.innerHeight));d.defaultNumberOfKids=2;var a=Elm.Signal.lift(function(a){return a[1]})(d);a.defaultNumberOfKids=0;var g=Elm.Signal.lift(function(a){return a[2]})(d);g.defaultNumberOfKids=0;Value.addListener(window,"resize",function(a){var g=document.getElementById("widthChecker").offsetWidth;Dispatcher.notify(d.id,Value.Tuple(g,window.innerHeight))||this.removeEventListener("resize",arguments.callee,!1)});return{dimensions:d,
109−width:a,height:g}}();Value.addListener(document,"elm_log",function(d){console.log(d.value)});Value.addListener(document,"elm_title",function(d){document.title=d.value});Value.addListener(document,"elm_redirect",function(d){0<d.value.length&&(window.location=d.value)});Elm=Elm||{};
110−Elm.Prelude=function(){var d=function(a){return function(g){var i=a%g,i=0==a?0:0<g?0<=a?i:i+g:-d(-a)(-g);return i==g?0:i}};return{eq:Value.eq,id:function(a){return a},not:function(a){return!a},fst:function(a){return a[1]},snd:function(a){return a[2]},rem:function(a){return function(d){return a%d}},div:function(a){return function(d){return~~(a/d)}},compare:function(a){return function(d){a="object"===typeof a?toText(a):a;d="object"===typeof d?toText(d):d;return[a===d?"EQ":a<d?"LT":"GT"]}},toFloat:function(a){return a},
111−round:function(a){return Math.round(a)},floor:function(a){return Math.floor(a)},ceiling:function(a){return Math.ceil(a)},truncate:function(a){return~~a},readInt:function(a){var a=JavaScript.castStringToJSString(a),d=a.length;if(0===d)return Nothing;var i=0;if("-"==a[0]){if(1===d)return Nothing;i=1}for(;i<d;++i)if(!Char.isDigit(a[i]))return Nothing;return Just(parseInt(a))},readFloat:function(a){var a=JavaScript.castStringToJSString(a),d=a.length;if(0===d)return Nothing;var i=0;if("-"==a[0]){if(1===
112−d)return Nothing;i=1}for(var j=0;i<d;++i)if(!Char.isDigit(a[i])){if("."===a[i]&&(j+=1,1>=j))continue;return Nothing}return Just(parseFloat(a))},sqrt:Math.sqrt,abs:Math.abs,pi:Math.PI,e:Math.E,sin:Math.sin,cos:Math.cos,tan:Math.tan,asin:Math.asin,acos:Math.acos,atan:Math.atan,atan2:function(a){return function(d){return Math.atan2(a,d)}},mod:d,min:function(a){return function(d){return Math.min(a,d)}},max:function(a){return function(d){return Math.max(a,d)}},flip:function(a){return function(d){return function(i){return a(i)(d)}}},
113−clamp:function(a){return function(d){return function(i){return Math.min(d,Math.max(a,i))}}},curry:function(a){return function(d){return function(i){return a(["Tuple2",d,i])}}},uncurry:function(a){return function(d){if("Tuple2"!==d[0])throw"Function was uncurry'd but was not given a pair.";return a(d[1])(d[2])}},logBase:function(a){return function(d){return Math.log(d)/Math.log(a)}},Just:Elm.Maybe.Just,Nothing:Elm.Maybe.Nothing,maybe:Elm.Maybe.maybe,map:Elm.List.map,filter:Elm.List.filter,head:Elm.List.head,
114−tail:Elm.List.tail,last:Elm.List.last,length:Elm.List.length,reverse:Elm.List.reverse,foldr:Elm.List.foldr,foldr1:Elm.List.foldr1,foldl:Elm.List.foldl,foldl1:Elm.List.foldl1,and:Elm.List.and,or:Elm.List.or,all:Elm.List.all,any:Elm.List.any,sum:Elm.List.sum,product:Elm.List.product,concat:Elm.List.concat,concatMap:Elm.List.concatMap,maximum:Elm.List.maximum,minimum:Elm.List.minimum,scanl:Elm.List.scanl,scanl1:Elm.List.scanl1,take:Elm.List.take,drop:Elm.List.drop,zip:Elm.List.zip,unzip:Elm.List.unzip,
115−lift:Elm.Signal.lift,lift2:Elm.Signal.lift2,lift3:Elm.Signal.lift3,lift4:Elm.Signal.lift4,foldp:Elm.Signal.foldp,foldp1:Elm.Signal.foldp1,foldp_:Elm.Signal.foldp_,constant:Elm.Signal.constant,count:Elm.Signal.count,keepIf:Elm.Signal.keepIf,dropIf:Elm.Signal.dropIf,keepWhen:Elm.Signal.keepWhen,dropWhen:Elm.Signal.dropWhen,dropRepeats:Elm.Signal.dropRepeats,sampleOn:Elm.Signal.sampleOn}}();
116−(function(){var d=function(a){for(var d in a)Elm.Prelude[d]=a[d]};d(Elm.Color);d(Elm.Text);d(Elm.Graphics);show=Value.show})();
117−(function(){for(var d in Elm)this[d]=Elm[d];Elm.Automaton=function(){function a(a){return["Automaton",a]}function d(a){return["DragFrom",a]}function i(b){return function(c){var d;a:{switch(b[0]){case "Automaton":d=b[1];break a}throw"Non-exhaustive pattern match in case";}var e;a:{switch(c[0]){case "Automaton":e=c[1];break a}throw"Non-exhaustive pattern match in case";}return a(function(a){var a=d(a),b;a:{switch(a[0]){case "Tuple2":b=a[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(a[0]){case "Tuple2":a=
118−a[2];break a}throw"Non-exhaustive pattern match in case";}var c=e(b);a:{switch(c[0]){case "Tuple2":b=c[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(c[0]){case "Tuple2":c=c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",b,i(a)(c)]})}}function j(b){return a(function(a){var c=unzip(map(function(b){a:{switch(b[0]){case "Automaton":b=b[1](a);break a}throw"Non-exhaustive pattern match in case";}return b})(b)),d;a:{switch(c[0]){case "Tuple2":d=c[1];break a}throw"Non-exhaustive pattern match in case";
119−}a:{switch(c[0]){case "Tuple2":c=c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",d,j(c)]})}function b(c){return a(function(a){return["Tuple2",c(a),b(c)]})}function l(b){return function(c){return a(function(a){a=c(a)(b);return["Tuple2",a,l(a)(c)]})}}function h(b){return function(c){return a(function(a){var d=c(a)(b);a:{switch(d[0]){case "Tuple2":a=d[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(d[0]){case "Tuple2":d=d[2];break a}throw"Non-exhaustive pattern match in case";
120−}return["Tuple2",a,h(d)(c)]})}}function e(a){return function(b){a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":b=["Tuple2",a[1]-b[1],a[2]-b[2]];break b}break}break a}throw"Non-exhaustive pattern match in case";}return b}}function c(a){return function(b){var c;a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":var f=function(a){return["Tuple2",b[2],["Tuple2",a,b[2]]]};c=function(){switch(b[1][0]){case "DragFrom":var c;a[1]?c=["Tuple2",uncurry(move)(e(a[2])(b[1][1]))(b[2]),["Tuple2",
121−d(b[1][1]),b[2]]]:(c=uncurry(move)(e(a[2])(b[1][1]))(b[2]),c=["Tuple2",c,["Tuple2",m,c]]);return c;case "Ignore":return f(a[1]?s:m);case "Listen":return f(not(a[1])?m:isWithin(a[2])(b[2])?d(a[2]):s)}throw"Non-exhaustive pattern match in case";}();break b}break}break a}throw"Non-exhaustive pattern match in case";}return c}}var f=[],n;for(n in Elm.Prelude)0<=f.indexOf(n)||(this[n]=Elm.Prelude[n]);var m=["Listen"],s=["Ignore"],f=l(0)(function(){return function(a){return 1+a}});return{Automaton:a,run:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=
122−lift(fst)(foldp_(function(a){return function(b){a:{switch(b[0]){case "Tuple2":switch(b[2][0]){case "Automaton":b=b[2][1](a);break a}}throw"Non-exhaustive pattern match in case";}return b}})(a[1])(b));break a}throw"Non-exhaustive pattern match in case";}return b}},step:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=a[1](b);break a}throw"Non-exhaustive pattern match in case";}return b}},composeAuto:i,combine:j,pure:b,init:l,init_:h,count:f,Listen:m,Ignore:s,DragFrom:d,vecSub:e,stepDrag:c,
123−draggable:function(a){return h(["Tuple2",m,a])(c)}}}()})();
elm/elm-runtime-0.6.0.3.jsdeleted−134
@@ -1,134 +0,0 @@
1−Elm={};var Guid=function(){var e=0;return{guid:function(){return e+=1}}}();
2−Elm.JavaScript=function(){function e(a){for(var b=["Nil"],l=a.length;l--;)b=["Cons",a[l],b];return b}function j(a){for(var b=[];"Cons"===a[0];)b.push(a[1]),a=a[2];return b}function a(a){return a.slice(1)}function d(a){return["Tuple"+a.length].concat(a)}return{castJSBoolToBool:function(a){return a},castBoolToJSBool:function(a){return a},castJSNumberToFloat:function(a){return a},castFloatToJSNumber:function(a){return a},castJSNumberToInt:function(a){return~~a},castIntToJSNumber:function(a){return a},
3−Experimental:{castJSElementToElement:function(a){return function(b){return function(l){return["Element",Guid.guid(),["EExternalHtml",l],a,b,1,Nothing,Nothing]}}},castElementToJSElement:function(a){return Render.render(a)}},castJSArrayToList:e,castListToJSArray:j,castJSStringToString:e,castStringToJSString:function(a){return"string"===typeof a?a:j(a).join("")},castTupleToJSTuple2:a,castTupleToJSTuple3:a,castTupleToJSTuple4:a,castTupleToJSTuple5:a,castJSTupleToTuple2:d,castJSTupleToTuple3:d,castJSTupleToTuple4:d,
4−castJSTupleToTuple5:d}}();var JSjson=window.JSON;
5−Elm.JSON=function(){function e(b,a){return function(h){return function(k){var f=d.castStringToJSString(h);return k[1].hasOwnProperty(f)&&(k=k[1][f],k[0]===b)?k[1]:a}}}function j(b){return function(a){function h(b){switch(b[0]){case "JsonNull":return null;case "JsonString":return d.castStringToJSString(b[1]);case "JsonObject":var f={},b=b[1][1],c;for(c in b)f[c]=h(b[c]);return f;case "JsonArray":f=d.castListToJSArray(b[1]);for(c=f.length;c--;)f[c]=h(f[c]);return f;default:return b[1]}}return JSjson.stringify(h(["JsonObject",
6−a]),null,d.castStringToJSString(b))}}function a(b){function a(b){switch(typeof b){case "string":return["JsonString",d.castJSStringToString(b)];case "number":return["JsonNumber",d.castJSNumberToFloat(b)];case "boolean":return["JsonBool",d.castJSBoolToBool(b)];case "object":if(null===b)return["JsonNull"];for(var f in b)b[f]=a(b[f]);return b instanceof Array?["JsonArray",d.castJSArrayToList(b)]:["JsonObject",["JSON",b]]}}var b=JSjson.parse(b),h;for(h in b)b[h]=a(b[h]);return["JSON",b]}var d=Elm.JavaScript,
7−i=["JSON",{}];return{empty:i,singleton:function(b){return function(a){var h={};h[d.castStringToJSString(b)]=a;return["JSON",h]}},insert:function(b){return function(a){return function(h){var h=h[1],k={},f;for(f in h)k[f]=h[f];k[d.castStringToJSString(b)]=a;return["JSON",k]}}},lookup:function(b){return function(a){var h=d.castStringToJSString(b);return a[1].hasOwnProperty(h)?["Just",a[1][h]]:["Nothing"]}},findString:e("JsonString",["Nil"]),findObject:e("JsonObject",i),findArray:e("JsonArray",["Nil"]),
8−findWithDefault:function(b){return function(a){return function(h){var k=d.castStringToJSString(a);return h[1].hasOwnProperty(k)?h[1][k]:b}}},remove:function(b){return function(a){var a=a[1],h={},k;for(k in a)h[k]=a[k];delete h[d.castStringToJSString(b)];return["JSON",h]}},toPrettyJSString:j,toJSString:j(""),fromJSString:a,toPrettyString:function(b){return function(a){return d.castJSStringToString(j(b)(a))}},toString:function(b){return d.castJSStringToString(j("")(b))},fromString:function(b){return a(d.castStringToJSString(b))},
9−toList:function(b){var b=b[1],a=[],h;for(h in b)a.push(Value.Tuple(d.castJSStringToString(h),b[h]));return d.castJSArrayToList(a)},fromList:function(b){for(var b=d.castListToJSArray(b),a={},h=b.length;h--;)a[d.castStringToJSString(b[h][1])]=b[h][2];return["JSON",a]},JsonString:function(b){return["JsonString",b]},JsonNumber:function(b){return["JsonNumber",b]},JsonBool:function(b){return["JsonBool",b]},JsonNull:["JsonNull"],JsonArray:function(b){return["JsonArray",b]},JsonObject:function(b){return["JsonObject",
10−b]}}}();
11−var Value=function(){function e(b){if(0==b.length)return b;for(var b=b.replace(/"/g,"&#34;").replace(/'/g,"&#39;").replace(/</g,"&#60;").replace(/>/g,"&#62;").replace(/\n/g,"<br/>"),b=b.split("<br/>"),a=b.length;a--;){var h=b,d=a,f;f=b[a];if(0!=f.length){f=f.split("");" "==f[0]&&(f[0]="&nbsp;");for(var c=f.length;--c;)" "==f[c][0]&&" "==f[c-1]&&(f[c-1]+=f[c],f[c]="");for(c=f.length;c--;)if(1<f[c].length&&" "==f[c][0]){for(var g=f[c].split(""),r=g.length-2;0<=r;r-=2)g[r]="&nbsp;";f[c]=g.join("")}f=f.join("");
12−f=" "===f[f.length-1]?f.slice(0,-1)+"&nbsp;":f}h[d]=f}return b.join("<br/>")}var j=function(b,a){if("object"===typeof b){if(b===a)return!0;if(b.length!==a.length)return!1;for(var h=b.length;h--;)if(!j(b[h],a[h]))return!1;return!0}return b===a},a=function(b){if("boolean"===typeof b)return b?"True":"False";if("number"!==typeof b){if("string"===typeof b&&2>b.length)return"'"+b+"'";if(b[0]){if("Tuple"===b[0].substring(0,5)){for(var d="",h=b.length;--h;)d=","+a(b[h])+d;","===d[0]&&(d=d.substring(1));return"("+
13−d+")"}if("Cons"===b[0])for(var h="string"===typeof b[1]?'"':"]",k="string"===typeof b[1]?"":",",f="string"===typeof b[1]?function(b){return b}:a,d=("string"===typeof b[1]?'"':"[")+f(b[1]),b=b[2];;)if("Cons"===b[0])d+=k+f(b[1]),b=b[2];else return d+h;else{if("Nil"===b[0])return"[]";if("JSON"===b[0])return"(JSON.fromList "+a(Elm.JSON.toList(b))+")";if("RBNode"===b[0]||"RBEmpty"===b[0])return b=Elm.Dict.foldr(function(b){return function(a){return function(f){return["Cons",["Tuple2",b,a],f]}}})(["Nil"])(b),
14−d="Dict","Cons"===b[0]&&"Tuple0"===b[1][2][0]&&(d="Set",b=Elm.List.map(function(b){return b[1]})(b)),"("+d+".fromList "+a(b)+")";d="";for(h=b.length;--h;)d=" "+a(b[h])+d;d=b[0]+d;return 1<b.length?"("+d+")":d}}}return b+""},d=function(b){for(var a=["Nil"],d=b.length;d--;)a=["Cons",b[d],a];return a},i;i=document.addEventListener?function(b,a,d){b.addEventListener(a,d,!1)}:function(b,a,d){b.attachEvent("on"+a,d)};return{eq:j,str:d,show:function(b){return d(a(b))},Tuple:function(){var b=arguments.length,
15−a=Array(b+1);for(a[0]="Tuple"+arguments.length;b--;)a[b+1]=arguments[b];return a},append:function(b,a){if("string"===typeof b&&"string"===typeof a)return b.concat(a);if("Nil"===b[0])return a;for(var d=["Cons",b[1],["Nil"]],k=d,b=b[2];"Cons"===b[0];)k[2]=["Cons",b[1],["Nil"]],b=b[2],k=k[2];k[2]=a;return d},listToArray:function(b){for(var a=[];"Cons"===b[0];)a.push(b[1]),b=b[2];return a},toText:function(a){if("string"===typeof a)return e(a);for(var d=[];"Cons"===a[0];)d.push(a[1]),a=a[2];return e(d.join(""))},
16−properEscape:e,getTextSize:function(a,d,h){var k=document.createElement("div");k.innerHTML=h;k.style.textAlign="left";0<a&&(k.style.width=a+"px");k.style.visibility="hidden";k.style.styleFloat="left";k.style.cssFloat="left";document.body.appendChild(k);h=window.getComputedStyle(k,null);a=h.getPropertyValue("width").slice(0,-2)-0;h=h.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(k);return[Math.ceil(a),Math.ceil(Math.max(d,h))]},getSize:function(a){a=a.cloneNode(!0);a.style.visibility=
17−"hidden";a.style.styleFloat="left";a.style.cssFloat="left";document.body.appendChild(a);var d=a.offsetWidth,h=a.offsetHeight;document.body.removeChild(a);return[d,h]},getExcess:function(a){a=a.cloneNode(!0);a.style.visibility="hidden";a.style.styleFloat="left";a.style.cssFloat="left";document.body.appendChild(a);var d=a.offsetWidth,h=a.offsetHeight,k=window.getComputedStyle(a,null),f=k.getPropertyValue("width").slice(0,-2)-0,k=k.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(a);
18−return[d-f,h-k]},groupForms:function(a){for(var a=Elm.JavaScript.castListToJSArray(a),d=[],h=[],k=a.length;k--;){var f=a[k];switch(f[4][0]){case "FElement":0<h.length&&(d.push(h),h=[]);d.push(f);break;default:h.push(f)}}0<h.length&&d.push(h);return d},wrap:function(a){var d=Value.getSize(a);return["Element",Guid.guid(),["EHtml",a],d[0],d[1],1,["Nothing"],["Nothing"]]},addListener:i}}();
19−Elm.List=function(){function e(a){return function(b){if("Nil"===b[0])return b;"Cons"!==b[0]&&f("map");for(var c=["Cons",a(b[1]),["Nil"]],g=c,b=b[2];"Cons"===b[0];)g[2]=["Cons",a(b[1]),["Nil"]],b=b[2],g=g[2];return c}}function j(a){return function(b){return function(c){var g=b;if("Nil"===c[0])return g;for("Cons"!==c[0]&&f("foldl");"Cons"===c[0];)g=a(c[1])(g),c=c[2];return g}}}function a(a){return function(b){return function(c){var g=b;if("Nil"===c[0])return g;"Cons"!==c[0]&&f("foldr");for(var d=[];"Cons"===
20−c[0];)d.push(c[1]),c=c[2];for(c=d.length;c--;)g=a(d[c])(g);return g}}}function d(a){return function(f){var b;"Cons"!==f[0]?b=void 0:(b=f[1],f=f[2],b=j(a)(b)(f));return b}}function i(a){return function(b){return function(c){if("Nil"===c[0])return["Cons",b,["Nil"]];"Cons"!==c[0]&&f("scanl");for(var g=[b];"Cons"===c[0];)b=a(c[1])(b),g.push(b),c=c[2];for(var c=["Nil"],d=g.length;d--;)c=["Cons",g[d],c];return c}}}function b(a){return function(f){a:{for(var c=[function(a){return"Nil"!==a[0]?void 0:["Tuple2",
21−["Nil"],["Nil"]]},function(f){if("Cons"===f[0]){var c=f[1],f=f[2];var g=b(a)(f);"Tuple2"!==g[0]?c=void 0:(f=g[1],g=g[2],c=a(c)?["Tuple2",["Cons",c,f],g]:["Tuple2",f,["Cons",c,g]]);return c}}],g=c.length;g--;){var d=c[g](f);if(void 0!==d){f=d;break a}}f=void 0}return f}}function l(a){a:{for(var f=[function(a){return"Nil"!==a[0]?void 0:["Tuple2",["Nil"],["Nil"]]},function(a){if("Cons"!==a[0])a=void 0;else if(a=["Tuple2",a[1],l(a[2])],"Tuple2"!==a[0]||"Tuple2"!==a[1][0])a=void 0;else var f=a[1][1],b=
22−a[1][2],a="Tuple2"!==a[2][0]?void 0:["Tuple2",["Cons",f,a[2][1]],["Cons",b,a[2][2]]];return a}],b=f.length;b--;){var c=f[b](a);if(void 0!==c){a=c;break a}}a=void 0}return a}function h(a){return function(f){a:{for(var b=[function(a){return"Nil"!==a[0]?void 0:["Nil"]},function(a){if("Cons"===a[0]){var f=a[1];return"Nil"!==a[2][0]?void 0:["Cons",f,["Nil"]]}},function(f){if("Cons"===f[0]){var b=f[1];if("Cons"===f[2][0]){var c=f[2][1],f=f[2][2];return["Cons",b,["Cons",a,h(a)(["Cons",c,f])]]}}}],c=b.length;c--;){var g=
23−b[c](f);if(void 0!==g){f=g;break a}}f=void 0}return f}}function k(a){return function(f){a:{for(var b=[function(a){return"Nil"!==a[0]?void 0:["Nil"]},function(a){if("Cons"===a[0]){var f=a[1];return"Nil"!==a[2][0]?void 0:f}},function(f){if("Cons"===f[0]){var b=f[1];if("Cons"===f[2][0]){var c=f[2][1],f=f[2][2];return Value.append(b,Value.append(a,k(a)(["Cons",c,f])))}}}],c=b.length;c--;){var g=b[c](f);if(void 0!==g){f=g;break a}}f=void 0}return f}}var f=function(a){throw"Function '"+a+"' expecting a list!";
24−},c=j(function(a){return function(f){return["Cons",a,f]}})(["Nil"]),g=a(function(a){return function(f){return Value.append(a,f)}})(["Nil"]),r=j(function(a){return function(f){return a&&f}})(!0),m=j(function(a){return function(f){return a||f}})(!1),n=j(function(a){return function(f){return a+f}})(0),u=j(function(a){return function(f){return a*f}})(1),x=d(function(a){return function(f){return Math.max(a,f)}}),q=d(function(a){return function(f){return Math.min(a,f)}});return{head:function(a){if("Cons"!==
25−a[0])throw"Error: 'head' only accepts lists of length greater than one.";return a[1]},tail:function(a){if("Cons"!==a[0])throw"Error: 'tail' only accepts lists of length greater than one.";return a[2]},last:function(a){if("Cons"!==a[0])throw"Error: 'last' only accepts lists of length greater than one.";for(var f=a[1];"Cons"===a[0];)f=a[1],a=a[2];return f},map:e,foldl:j,foldr:a,foldl1:d,foldr1:function(a){return function(b){if("Nil"===b[0])throw"'foldr1' requires an non-empty list.";"Cons"!==b[0]&&
26−f("foldr1");for(var c=[];"Cons"===b[0];)c.push(b[1]),b=b[2];for(var b=c.pop(),g=c.length;g--;)b=a(c[g])(b);return b}},scanl:i,scanl1:function(a){return function(f){if("Cons"!==f[0])throw"Error: 'scanl1' requires a list of at least length 1.";return i(a)(f[1])(f[2])}},filter:function(a){return function(b){if("Nil"===b[0])return b;"Cons"!==b[0]&&f("filter");for(var c=[];"Cons"===b[0];)a(b[1])&&c.push(b[1]),b=b[2];for(var b=["Nil"],g=c.length;g--;)b=["Cons",c[g],b];return b}},length:function(a){for(var f=
27−0;"Cons"===a[0];)f+=1,a=a[2];return f},reverse:c,concat:g,concatMap:function(a){return function(f){return g(e(a)(f))}},and:r,or:m,all:function(a){return j(function(f){return function(b){return b&&a(f)}})(!0)},any:function(a){return j(function(f){return function(b){return b||a(f)}})(!1)},sum:n,product:u,maximum:x,minimum:q,partition:b,zipWith:function(a){return function(b){return function(c){if("Nil"===b[0]||"Nil"===c[0])return["Nil"];("Cons"!==b[0]||"Cons"!==c[0])&&f("zipWith");for(var g=[];"Cons"===
28−b[0]&&"Cons"===c[0];)g.push(a(b[1])(c[1])),b=b[2],c=c[2];for(var c=["Nil"],d=g.length;d--;)c=["Cons",g[d],c];return c}}},zip:function(a){return function(b){if("Nil"===a[0]||"Nil"===b[0])return["Nil"];("Cons"!==a[0]||"Cons"!==b[0])&&f("zip");for(var c=[];"Cons"===a[0]&&"Cons"===b[0];)c.push(["Tuple2",a[1],b[1]]),a=a[2],b=b[2];for(var b=["Nil"],g=c.length;g--;)b=["Cons",c[g],b];return b}},unzip:l,intersperse:h,intercalate:k,sort:function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&f("sort");for(var b=
29−[];"Cons"===a[0];)b.push(a[1]),a=a[2];b.sort(function(a,f){return a-f});for(var a=["Nil"],c=b.length;c--;)a=["Cons",b[c],a];return a},take:function(a){return function(b){if(0>=a)return["Nil"];if("Nil"===b[0])return b;"Cons"!==b[0]&&f("take");var c=["Cons",b[1],["Nil"]],g=c,b=b[2];for(--a;"Cons"===b[0]&&0<a;)g[2]=["Cons",b[1],["Nil"]],g=g[2],b=b[2],--a;return c}},drop:function(a){return function(b){if("Nil"===b[0])return b;for("Cons"!==b[0]&&f("drop");"Cons"===b[0]&&0<a;)b=b[2],--a;return b}}}}();
30−Elm.Maybe=function(){function e(a){return function(d){return"Just"===a[0]?["Cons",a[1],d]:d}}function j(a){return function(d){return function(i){var b=a(d);return"Just"===b[0]?["Cons",b[1],i]:i}}}return{Just:function(a){return["Just",a]},Nothing:["Nothing"],catMaybes:Elm.List.foldr(e)(["Nil"]),isJust:function(a){return"Just"===a[0]},isNothing:function(a){return"Nothing"===a[0]},fromMaybe:function(a){return function(d){return"Just"===d[0]?d[1]:a}},consMaybe:e,mapMaybe:function(a){return Elm.List.foldr(j(a))(["Nil"])},
31−maybe:function(a){return function(d){return function(i){return"Just"===i[0]?d(i[1]):a}}}}}();
32−Elm.Char=function(){function e(a,b){return function(d){d=d.charCodeAt(0);return a<=d&&d<=b}}var j=e(48,57),a=e(97,102),d=e(65,70);return{fromCode:function(a){return String.fromCharCode(a)},toCode:function(a){return a.charCodeAt(0)},toUpper:function(a){return a.toUpperCase()},toLower:function(a){return a.toLowerCase()},toLocaleUpper:function(a){return a.toLocaleUpperCase()},toLocaleLower:function(a){return a.toLocaleLowerCase()},isLower:e(97,122),isUpper:e(65,90),isDigit:j,isOctDigit:e(48,55),isHexDigit:function(e){return j(e)||
33−a(e)||d(e)}}}();
34−Elm.Color=function(){function e(e){var a=e.value*e.saturation,d=e.hue/60,i=a*(1-Math.abs(d%2-1)),b=0,l=0,h=0;0<=d&&1>d?(b=a,l=i,h=0):1<=d&&2>d?(b=i,l=a,h=0):2<=d&&3>d?(b=0,l=a,h=i):3<=d&&4>d?(b=0,l=i,h=a):4<=d&&5>d?(b=i,l=0,h=a):5<=d&&6>d&&(b=a,l=0,h=i);e=e.value-a;return["Color",Math.round(255*(b+e)),Math.round(255*(l+e)),Math.round(255*(h+e)),1]}return{rgba:function(e){return function(a){return function(d){return function(i){return["Color",e,a,d,i]}}}},rgb:function(e){return function(a){return function(d){return["Color",e,
35−a,d,1]}}},hsva:function(j){return function(a){return function(d){return function(i){var b=e({hue:j,saturation:a,value:d});b[4]=i;return b}}}},hsv:function(j){return function(a){return function(d){return e({hue:j,saturation:a,value:d})}}},red:["Color",255,0,0,1],green:["Color",0,255,0,1],blue:["Color",0,0,255,1],yellow:["Color",255,255,0,1],cyan:["Color",0,255,255,1],magenta:["Color",255,0,255,1],black:["Color",0,0,0,1],white:["Color",255,255,255,1],gray:["Color",128,128,128,1],grey:["Color",128,128,
36−128,1],complement:function(j){var a;a=j[1]/255;var d=j[2]/255,j=j[3]/255,i=Math.max(a,d,j),b=Math.min(a,d,j),b=i-b,l=0;0===b?l=0:i===a?l=(d-j)/b%6:i===d?l=(j-a)/b+2:i===j&&(l=(a-d)/b+4);a={value:i,hue:60*l,saturation:0===i?0:b/i};a.hue=(a.hue+180)%360;return e(a)},extract:function(e){return 1===e[4]?"rgb("+e[1]+","+e[2]+","+e[3]+")":"rgba("+e[1]+","+e[2]+","+e[3]+","+e[4]+")"}}}();
37−var Collage=function(){function e(a,b){var c=b.length-1;if(!(0>=c))for(a.moveTo(b[c][1],b[c][2]);c--;)a.lineTo(b[c][1],b[c][2])}function j(a,b,c,g){0===a.length&&(a=[8,4]);var d=g.length-1;if(!(0>=d)){var m=g[d][1],h=g[d][2],e=0,i=0,j=0,l=0,p=0,s=0,v=a.length,z=!0,w=a[0];for(b.moveTo(m,h);d--;){e=g[d][1];i=g[d][2];j=e-m;l=i-h;for(p=Math.sqrt(j*j+l*l);w<=p;)m+=j*w/p,h+=l*w/p,b[z?"lineTo":"moveTo"](m,h),j=e-m,l=i-h,p=Math.sqrt(j*j+l*l),z=!z,s=(s+1)%v,w=a[s];0<p&&(b[z?"lineTo":"moveTo"](e,i),w-=p);m=
38−e;h=i}}b.strokeStyle=Elm.Color.extract(c);b.stroke()}function a(a,b,c,g,d){b.clearRect(0,0,c,g);for(c=d.length;c--;){var m=d[c],n=a,g=b,i=m[1],l=m[2],q=m[3][1],t=m[3][2],m=m[4];g.save();(0!==q||0!==t)&&g.translate(q,t);i!==~~i&&g.rotate(2*Math.PI*i);1!==l&&g.scale(l,l);g.beginPath();switch(m[0]){case "FLine":a:switch(n=g,i=m,m=i[3][1],i[1][0]){case "Solid":i=i[2];e(n,m);n.strokeStyle=Elm.Color.extract(i);n.stroke();break;case "Dotted":j([3,3],n,i[2],m);break a;case "Dashed":j([8,4],n,i[2],m);break a;
39−case "Custom":j(i[1][1],n,i[2],m)}break;case "FShape":a:switch(q=n,l=g,n=m[1],i=m[2],m=m[3][1],n[0]){case "Filled":n=l;e(n,m);n.fillStyle=Elm.Color.extract(i);n.fill();break a;case "Outlined":n=l;e(n,m);n.strokeStyle=Elm.Color.extract(i);n.stroke();break a;case "Textured":i=q;n=n[1];q=new Image;q.src=h.castStringToJSString(n);q.onload=i;e(l,m);l.fillStyle=l.createPattern(q,"repeat");l.fill();break a;case "CustomOutline":j(n[1],l,i,m)}break;case "FImage":i=g,l=m[1],q=m[2],m=m[3],t=new Image,t.onload=
40−n,t.src=h.castStringToJSString(m),i.drawImage(t,-l/2,-q/2,l,q)}g.restore()}}function d(b,f,c){var g=Render.newElement("canvas"),b=~~b,f=~~f;g.style.width=b+"px";g.style.height=f+"px";g.style.display="block";g.width=b;g.height=f;if(g.getContext){var d=g.getContext("2d");a(function(){a(this,d,b,f,c)},d,b,f,c);return g}g.innerHTML="Your browser does not support the canvas element.";return g}function i(a,b,c,g,d,h,e){var i=Render.render(e),c="translate("+(d-e[3]/2)+"px,"+(h-e[4]/2)+"px) "+(1===g?"":"scale("+
41−g+","+g+")")+" "+(c===~~c?"":"rotate("+360*c+"deg)");i.style.transform=c;i.style.msTransform=c;i.style.MozTransform=c;i.style.webkitTransform=c;i.style.OTransform=c;c=Render.newElement("div");Render.addTo(c,i);c.style.width=~~a+"px";c.style.height=~~b+"px";c.style.overflow="hidden";return c}function b(b,f,c){if(!Value.eq(c,f)){var g=b.style.width.slice(0,-2)-0,h=b.style.height.slice(0,-2)-0;if("object"===typeof c[0]){if("object"===typeof f[0]&&b.getContext){var m=b.getContext("2d");return a(function(){a(this,
42−m,g,h,c)},m,g,h,c)}f=d(g,h,c);f.style.position="absolute";return b.parentNode.replaceChild(f,b)}f=i(g,h,c[1],c[2],c[3][1],c[3][2],c[4][1]);f.style.position="absolute";return b.parentNode.replaceChild(f,b)}}function l(a,b,c,g,d){var h=0,e,i=(a[1]-g[1])/c,a=(a[2]-g[2])/c;0!==b&&(b*=-2*Math.PI,c=i*Math.cos(b)-a*Math.sin(b),a=i*Math.sin(b)+a*Math.cos(b),i=c);if(0===d.length)return!1;e=d[0];for(c=d.length-1;c--;){b=d[c];g=e[1];e=e[2];var j=b[1],l=b[2];if(e<l)var t=e,p=l;else t=l,p=e;if(g<j)var s=g,v=j;
43−else s=j,v=g;t<a&&a<=p&&i<=v&&(i<=s||i<=(a-e)*(j-g)/(l-e)+g)&&++h;e=b}return 1===h%2}var h=Elm.JavaScript;return{collage:function(a,b,c){if(0===c.length)return d(a,b,[]);for(var g=Array(c.length),h=c.length;h--;){var e=c[h];g[h]="string"===typeof e[0]?i(a,b,e[1],e[2],e[3][1],e[3][2],e[4][1]):d(a,b,e)}return 1===c.length?g[0]:Render.flowWith(Render.goIn,function(a){return a},g)},updateCollage:function(a,f,c){if(1===c.length)return b(a,f[0],c[0]);for(var a=a.childNodes,g=a.length,d=g;d--;)b(a[g-d-1],
44−f[d],c[d])},insideForm:function(a){return function(b){var c=a[1],g=a[2];if(6>b.length){var d=b[3][1],e=b[3][2],h=0,i=b[2];switch(b[4][0]){case "FShape":for(var j=b[4][3][1],q=j.length;--q;)var t=j[q],h=Math.max(h,t[1]*t[1]+t[2]*t[2]);h*=i*i;break;case "FImage":j=i*b[4][1]/2;i=i*b[4][2]/2;h=j*j+i*i;break;case "FElement":j=i*b[4][1][3]/2,i=i*b[4][1][4]/2,h=j*j+i*i}b.push(function(a,b){var c=a-d,f=b-e;return c*c+f*f<h+1})}if(!b[5](c,g))return!1;var p,s;switch(b[4][0]){case "FShape":return l(a,b[1],b[2],
45−b[3],b[4][3][1]);case "FLine":return!1;case "FImage":p=b[4][1]/2;s=b[4][2]/2;break;case "FElement":p=b[4][1][3]/2,s=b[4][1][4]/2}return l(a,b[1],b[2],b[3],[[null,p,s],[null,-p,s],[null,-p,-s],[null,p,-s],[null,p,s]])}}}}();
46−Elm.Graphics=function(){function e(a){return function(b){return["Position",a,b]}}function j(a){return function(b){return["EText",a,b]}}function a(a){return function(b){return["EFlow",a,u.castListToJSArray(b)]}}function d(a){return["Line",u.castListToJSArray(a)]}function i(a){return function(b){var c=u.castListToJSArray(a);0<c.length&&c.push(c[0]);return["Shape",c,b]}}function b(a){return function(b){return function(c){return function(f){return["Form",a,b,c,f]}}}}function l(a){return function(b){return function(c){return["FLine",
47−a,b,c]}}}function h(a){return function(b){return function(c){return["FShape",a,b,c]}}}function k(a,b,c,f,g,d){return["Element",Guid.guid(),a,b,c,f,g,d]}function f(a,b,c){return["Element",Guid.guid(),a,b,c,1,["Nothing"],["Nothing"]]}function c(a){return~~a[3]}function g(a){return~~a[4]}function r(a){return function(b){return function(c){return f(["EImage",u.castStringToJSString(c)],a,b)}}}function m(a){return function(b){return f(z,a,b)}}function n(a){return function(b){return function(c){var f=map(function(c){return["Tuple2",
48−a/2*Math.cos(2*(Math.PI/50)*c),b/2*Math.sin(2*(Math.PI/50)*c)]}),g=49,d=["Nil"];if(0<=g){do d=["Cons",g,d];while(0<g--)}return i(f(d))(c)}}}for(this.i in Elm.List)eval("var "+this.i+" = Elm.List[this.i];");var u=Elm.JavaScript,x=["DRight"],q=["DDown"],t=["DOut"],p=["Near"],s=["Mid"],v=["Far"],z=["EEmpty"],w=["Solid"],C=["Dotted"],E=["Dashed"],A=["Filled"],D=["Outlined"],y=e(p)(p),B=e(v)(p),F=e(p)(v),G=e(v)(v),H=e(p)(s),I=e(v)(s),p=e(s)(p),v=e(s)(v),s=e(s)(s);return{left:["DLeft"],right:x,down:q,up:["DUp"],
49−inward:["DIn"],outward:t,topLeft:y,topRight:B,bottomLeft:F,bottomRight:G,midLeft:H,midRight:I,midTop:p,midBottom:v,middle:s,middleAt:function(a){return function(b){return["PositionAt",a,b]}},topLeftAt:function(a){return function(b){return["PositionTL",a,b]}},topRightAt:function(a){return function(b){return["PositionTR",a,b]}},bottomLeftAt:function(a){return function(b){return["PositionBL",a,b]}},bottomRightAt:function(a){return function(b){return["PositionBR",a,b]}},absolute:function(a){return["Absolute",
50−a]},relative:function(a){return["Relative",a]},width:function(a){return function(b){var c=b[2];switch(c[0]){case "EImage":case "EVideo":return k(b[2],a,b[4]*a/b[3],b[5],b[6],b[7]);case "EText":return c=Value.getTextSize(a,b[4],c[2]),k(b[2],a,c[1],b[5],b[6],b[7])}return k(b[2],a,b[4],b[5],b[6],b[7])}},height:function(a){return function(b){switch(b[2][0]){case "EImage":case "EVideo":return k(b[2],b[3]*a/b[4],a,b[5],b[6],b[7])}return k(b[2],b[3],a,b[5],b[6],b[7])}},size:function(a){return function(b){return function(c){return k(c[2],
51−a,b,c[5],c[6],c[7])}}},opacity:function(a){return function(b){return k(b[2],b[3],b[4],a,b[6],b[7])}},color:function(a){return function(b){return k(b[2],b[3],b[4],b[5],["Just",a],b[7])}},link:function(a){return function(b){return k(b[2],b[3],b[4],b[5],b[6],["Just",u.castStringToJSString(a)])}},widthOf:c,heightOf:g,sizeOf:function(a){return["Tuple2",~~a[3],~~a[4]]},text:function(a){var b=Value.getTextSize(0,0,a);return f(j("left")(a),b[0],b[1])},asText:function(a){var a=Elm.Text.monospace(Value.toText(Value.show(a))),
52−b=Value.getTextSize(0,0,a);return f(j("left")(a),b[0],b[1])},plainText:function(a){var a=Value.toText(a),b=Value.getTextSize(0,0,a);return f(j("left")(a),b[0],b[1])},centeredText:function(a){var b=Value.getTextSize(0,0,a);return f(j("center")(a),b[0],b[1])},justifiedText:function(a){var b=Value.getTextSize(0,0,a);return f(j("justify")(a),b[0],b[1])},rightedText:function(a){var b=Value.getTextSize(0,0,a);return f(j("right")(a),b[0],b[1])},image:r,images:function(a){var b=Elm.Signal.constant(m(0)(0)),
53−a=Elm.Signal.lift(function(a){var a=u.castStringToJSString(a),c=new Image;c.onload=function(){Dispatcher.notify(b.id,r(this.width)(this.height)(a))};c.src=a})(a);return Elm.Signal.lift2(function(a){return function(){return a}})(b)(a)},video:function(a){return function(b){return function(c){return f(["EVideo",u.castStringToJSString(c)],a,b)}}},fittedImage:function(a){return function(b){return function(c){return f(["EFittedImage",u.castStringToJSString(c)],a,b)}}},flow:function(b){return function(d){var h;
54−h=map(c)(d);a:{switch(b[0]){case "DLeft":h=sum(h);break a;case "DRight":h=sum(h);break a}h=maximum(h)}var e;e=map(g)(d);a:{switch(b[0]){case "DDown":e=sum(e);break a;case "DUp":e=sum(e);break a}e=maximum(e)}return f(a(b)(d),h,e)}},above:function(b){return function(c){return f(a(q)(["Cons",b,["Cons",c,["Nil"]]]),Math.max(~~b[3],~~c[3]),~~b[4]+~~c[4])}},below:function(b){return function(c){return f(a(q)(["Cons",c,["Cons",b,["Nil"]]]),Math.max(~~b[3],~~c[3]),~~b[4]+~~c[4])}},beside:function(b){return function(c){return f(a(x)(["Cons",
55−b,["Cons",c,["Nil"]]]),~~b[3]+~~c[3],Math.max(~~b[4],~~c[4]))}},layers:function(b){return f(a(t)(b),maximum(map(c)(b)),maximum(map(g)(b)))},collage:function(a){return function(b){return function(c){return f(["ECollage",a,b,Value.groupForms(c)],a,b)}}},spacer:m,container:function(a){return function(b){return function(c){return function(g){return f(["EContainer",c,g],a,b)}}}},line:d,segment:function(a){return function(b){return d(["Cons",a,["Cons",b,["Nil"]]])}},polygon:i,rect:function(a){return function(b){return function(c){return i(["Cons",
56−["Tuple2",0-a/2,0-b/2],["Cons",["Tuple2",0-a/2,b/2],["Cons",["Tuple2",a/2,b/2],["Cons",["Tuple2",a/2,0-b/2],["Nil"]]]]])(c)}}},oval:n,circle:function(a){return n(2*a)(2*a)},ngon:function(a){return function(b){return function(c){var f=map(function(c){return["Tuple2",b*Math.cos(2*(Math.PI/a)*c),b*Math.sin(2*(Math.PI/a)*c)]}),g=a-1,d=["Nil"];if(0<=g){do d=["Cons",g,d];while(0<g--)}return i(f(d))(c)}}},solid:function(a){return function(c){return b(0)(1)(["Tuple2",0,0])(l(w)(a)(c))}},dotted:function(a){return function(c){return b(0)(1)(["Tuple2",
57−0,0])(l(C)(a)(c))}},dashed:function(a){return function(c){return b(0)(1)(["Tuple2",0,0])(l(E)(a)(c))}},customLine:function(a){return function(c){return function(f){return b(0)(1)(["Tuple2",0,0])(l(["Custom",u.castListToJSArray(a)])(c)(f))}}},filled:function(a){return function(c){return b(0)(1)(c[2])(h(A)(a)(c))}},outlined:function(a){return function(c){return b(0)(1)(c[2])(h(D)(a)(c))}},customOutline:function(a){return function(c){return function(f){return b(0)(1)(f[2])(h(["CustomOutline",u.castListToJSArray(a)])(c)(f))}}},
58−textured:function(a){return function(c){return b(0)(1)(c[2])(h(["Textured",a])(null)(c))}},sprite:function(a){return function(c){return function(f){return function(g){return b(0)(1)(g)(["FImage",c,f,u.castStringToJSString(a)])}}}},toForm:function(a){return function(c){return b(0)(1)(a)(["FElement",c])}},rotate:function(a){return function(c){a:{switch(c[0]){case "Form":var f=c[2],g=c[3],d=c[4],c=b(a+c[1])(f)(g)(d);break a}throw"Non-exhaustive pattern match in case";}return c}},scale:function(a){return function(c){return b(c[1])(a*
59−c[2])(c[3])(c[4])}},move:function(a){return function(c){return function(f){var g;a:{switch(f[0]){case "Form":g=f[1];var d=f[2],h=f[3],f=f[4];switch(h[0]){case "Tuple2":var e=h[1],h=h[2];g=b(g)(d)(["Tuple2",a+e,c+h])(f);break a}}throw"Non-exhaustive pattern match in case";}return g}}},isWithin:Collage.insideForm}}();
60−Elm.Text=function(){function e(a){return Value.toText(a)}var j=function(a){return function(b){return"<"+a+' style="padding:0;margin:0">'+b+"</"+a+">"}},a=function(a,b){return function(g){return"<span style='"+a+":"+b+"'>"+g+"</span>"}},d=function(b){b=Elm.JavaScript.castStringToJSString(b);return a("font-family",b)},i=j("h1"),b=a("font-style","italic"),j=j("b"),l=a("text-decoration","underline"),h=a("text-decoration","overline"),k=a("text-decoration","line-through");return{fromString:e,toText:e,header:i,
61−height:function(b){return a("font-size",b+"em")},italic:b,bold:j,underline:l,overline:h,strikeThrough:k,monospace:d("monospace"),typeface:d,color:function(b){return a("color",Elm.Color.extract(b))},link:function(a){return function(b){return"<a href='"+e(a)+"'>"+b+"</a>"}}}}();
62−var Render=function(){function e(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a}function j(a){return a}function a(a){a.style.styleFloat="left";a.style.cssFloat="left";return a}function d(a){a.style.position="absolute";return a}function i(a,b,g){for(var d=e("div"),h=g.length;h--;){var i=a(b(g[h]));d.appendChild(i)}return d}function b(a){switch(a[0]){case "Absolute":return a[1]+"px";case "Relative":return 100*a[1]+"%"}}function l(a,c){c.style.position="absolute";c.style.margin=
63−"auto";switch(a[0]){case "Position":"Far"!==a[1][0]&&(c.style.left=0);"Near"!==a[1][0]&&(c.style.right=0);"Far"!==a[2][0]&&(c.style.top=0);"Near"!==a[2][0]&&(c.style.bottom=0);break;case "PositionAt":c.style.top=b(a[2]);c.style.left=b(a[1]);var g="translate("+~~(-c.style.width.slice(0,-2)/2)+"px,"+~~(-c.style.height.slice(0,-2)/2)+"px)";c.style.transform=g;c.style.msTransform=g;c.style.MozTransform=g;c.style.webkitTransform=g;c.style.OTransform=g;break;default:g=a[0].slice(-2),c.style["T"===g[0]?
64−"top":"bottom"]=b(a[2]),c.style["L"===g[1]?"left":"right"]=b(a[1])}}function h(b){var c={};switch(b[2][0]){case "EText":var c=b[2][1],g=b[2][2],r=e("div");r.innerHTML=g;r.style.textAlign=c;c=r;break;case "EImage":c=b[2][1];g=e("img");g.src=c;g.name=c;g.style.display="block";c=g;break;case "EVideo":r=b[2][1];c=e("video");c.controls="controls";g=e("source");g.src=r;r=r.split(".");g.type="video/"+r[r.length-1];c.appendChild(g);c.style.display="block";break;case "EFittedImage":var m=b[3],n=b[4],c=b[2][1],
65−g=e("div");g.style.width=m+"px";g.style.height=n+"px";g.style.position="relative";g.style.overflow="hidden";var k=e("img");k.onload=function(){k.style.position="absolute";k.style.margin="auto";var a=m,b=n;m/n>this.width/this.height?b=Math.round(this.height*m/this.width):a=Math.round(this.width*n/this.height);k.style.width=a+"px";k.style.height=b+"px";k.style.left=(m-a)/2+"px";k.style.top=(n-b)/2+"px"};k.src=c;k.name=c;g.appendChild(k);c=g;break;case "EFlow":a:{c=b[2][2];switch(b[2][1][0]){case "DDown":c=
66−c.slice(0).reverse();case "DUp":c=i(j,h,c);break a;case "DRight":c=c.slice(0).reverse();case "DLeft":c=i(a,h,c);break a;case "DOut":c=c.slice(0).reverse();case "DIn":c=i(d,h,c);break a}c=void 0}break;case "ECollage":c=Collage.collage(b[2][1],b[2][2],b[2][3]);break;case "EEmpty":c=e("div");break;case "EContainer":g=b[2][1];c=h(b[2][2]);l(g,c);g=e("div");g.style.position="relative";g.style.overflow="hidden";g.appendChild(c);c=g;break;case "EHtml":c=b[2][1];"button"!==c.type&&(g=Value.getExcess(c),b[3]-=
67−g[0],b[4]-=g[1]);break;case "EExternalHtml":c=e("div"),c.appendChild(b[2][1])}c.id=b[1];c.style.width=~~b[3]+"px";c.style.height=~~b[4]+"px";1!==b[5]&&(c.style.opacity=b[5]);"Just"===b[6][0]&&(c.style.backgroundColor=Elm.Color.extract(b[6][1]));return"Just"===b[7][0]?(g=e("a"),g.href=b[7][1],g.appendChild(c),g):c}function k(b,c,g){"A"===b.tagName&&(b=b.firstChild);if(c[1]!==g[1]){if(c[2][0]!==g[2][0])return b.parentNode.replaceChild(h(g),b);var e=g[2],i=c[2];switch(e[0]){case "EText":e[1]!==i[1]&&
68−(b.style.textAlign=e[1]);e[2]!==i[2]&&(b.innerHTML=e[2]);break;case "EImage":e[1]!==i[1]&&(b.src=e[1]);break;case "EVideo":case "EFittedImage":if(!Value.eq(e,i)||g[3]!==c[3]||g[4]!==c[4])return b.parentNode.replaceChild(h(g),b);break;case "ECollage":if(e[1]!==i[1]||e[2]!==i[2]||e[3].length!==i[3].length)return b.parentNode.replaceChild(h(g),b);Collage.updateCollage(b,i[3],e[3]);break;case "EFlow":if(e[1]!==i[1])return b.parentNode.replaceChild(h(g),b);var n=e[2],u=b.childNodes;if(n.length!==u.length)return b.parentNode.replaceChild(h(g),
69−b);var i=i[2],x=function(a){return a};switch(e[1][0]){case "DDown":case "DUp":x=j;break;case "DRight":case "DLeft":x=a;break;case "DOut":case "DIn":x=d}for(e=u.length;e--;)k(u[e],i[e],n[e]),x(u[e]);break;case "EContainer":k(b.childNodes[0],i[2],e[2]);l(e[1],b.childNodes[0]);break;case "EHtml":g[1]!==c[1]&&(n=h(g),b.parentNode.replaceChild(n,b),b=n);"button"!==n.type&&(e=Value.getExcess(b),g[3]-=e[0],g[4]-=e[1]);break;case "EExternalHtml":g[1]!==c[1]&&b.parentNode.replaceChild(h(g),b)}g[3]!==c[3]&&
70−(b.style.width=~~g[3]+"px");g[4]!==c[4]&&(b.style.height=~~g[4]+"px");g[5]!==c[5]&&(b.style.opacity=g[5]);2===g[6].length&&(e=Elm.Color.extract(g[6][1]),e!==b.style.backgroundColor&&(b.style.backgroundColor=e));if(2===g[7].length&&(1===c[7].length||g[7][1]!==c[7][1]))b.parentNode.href=g[7][1];g[1]=c[1]}}return{render:h,update:k,addTo:function(a,b){a.appendChild(b)},newElement:e,flowWith:i,goIn:d}}();
71−Elm.Signal=function(){function e(a){this.id=Guid.guid();this.value=a;this.kids=[];this.defaultNumberOfKids=0;this.recv=function(a,b,c){if(b=b===this.id)this.value=c;k(this,a,b);return b};Dispatcher.inputs.push(this)}function j(a,b){this.id=Guid.guid();this.value=null;this.kids=[];this.count=0;this.changed=!1;b.reverse();this.recalc=function(){for(var d=a,f=b.length;f--;)d=d(b[f].value);this.value=d};this.recalc();this.recv=function(a,c){this.count+=1;c&&(this.changed=!0);this.count==b.length&&(this.changed&&
72−this.recalc(),k(this,a,this.changed),this.changed=!1,this.count=0)};for(var d=b.length;d--;)b[d].kids.push(this)}function a(a,b,d,f){this.id=Guid.guid();this.value=d?b(f.value):b;this.kids=[];this.recv=function(b,d){d&&(this.value=a(f.value)(this.value));k(this,b,d)};f.kids.push(this)}function d(a,b,d){this.id=Guid.guid();this.value=a(d.value)?b:d.value;this.kids=[];this.recv=function(b,g){var f=g&&!a(d.value);f&&(this.value=d.value);k(this,b,f)};d.kids.push(this)}function i(a){this.id=Guid.guid();
73−this.value=a.value;this.kids=[];this.recv=function(b,d){var f=d&&!Value.eq(this.value,a.value);f&&(this.value=a.value);k(this,b,f)};a.kids.push(this)}function b(a,b){this.id=Guid.guid();var d=(new window.Date).getTime();this.value=a?Value.Tuple(d,b.value):d;this.kids=[];this.recv=function(d,f){f&&(this.value=a?Value.Tuple(d,b.value):d);k(this,d,f)};b.kids.push(this)}function l(a,b){this.id=Guid.guid();this.value=b.value;this.kids=[];this.count=0;this.changed=!1;this.recv=function(d,f,e){e===a.id&&
74−(this.changed=f);this.count+=1;2==this.count&&(this.changed&&(this.value=b.value),k(this,d,this.changed),this.count=0,this.changed=!1)};a.kids.push(this);b.kids.push(this)}function h(a,b){this.id=Guid.guid();this.value=a.value;this.kids=[];this.next=null;this.count=0;this.changed=!1;this.recv=function(d,f,e){this.count+=1;f&&(this.changed=!0,e==b.id&&null===this.next&&(this.next=b.value),e==a.id&&(this.next=a.value));2==this.count&&(this.changed&&(this.value=this.next,this.next=null),k(this,d,this.changed),
75−this.changed=!1,this.count=0)};a.kids.push(this);b.kids.push(this)}var k=function(a,b,d){for(var f=a.kids,e=f.length;e--;)f[e].recv(b,d,a.id)},f=function(a){return function(b){return function(f){f=new j(function(a){return function(b){return[a,b]}},[a,f]);f=new d(function(a){return a[0]},[!0,b],f);return new j(function(a){return a[1]},[f])}}};return{constant:function(a){return new e(a)},lift:function(a){return function(b){return new j(a,[b])}},lift2:function(a){return function(b){return function(d){return new j(a,
76−[b,d])}}},lift3:function(a){return function(b){return function(d){return function(f){return new j(a,[b,d,f])}}}},lift4:function(a){return function(b){return function(d){return function(f){return function(e){return new j(a,[b,d,f,e])}}}}},lift5:function(a){return function(b){return function(d){return function(f){return function(e){return function(h){return new j(a,[b,d,f,e,h])}}}}}},lift6:function(a){return function(b){return function(d){return function(f){return function(e){return function(h){return function(i){return new j(a,
77−[b,d,f,e,h,i])}}}}}}},lift7:function(a){return function(b){return function(d){return function(f){return function(e){return function(h){return function(i){return function(k){return new j(a,[b,d,f,e,h,i,k])}}}}}}}},lift8:function(a){return function(b){return function(d){return function(f){return function(e){return function(h){return function(i){return function(k){return function(l){return new j(a,[b,d,f,e,h,i,k,l])}}}}}}}}},foldp:function(b){return function(d){return function(f){return new a(b,d,!1,
78−f)}}},foldp_:function(b){return function(d){return function(f){return new a(b,d,!0,f)}}},foldp1:function(b){return function(d){return new a(b,function(a){return a},!0,d)}},delay:function(a){return function(b){var d=new e(b.value),f=!0,b=new l(d,new j(function(a){return function(){return a}},[d,new j(function(b){f||setTimeout(function(){Dispatcher.notify(d.id,b)},a)},[b])])),f=!1;return b}},merge:function(a){return function(b){return new h(a,b)}},merges:function(a){return Elm.List.foldl1(function(a){return function(b){return new h(a,
79−b)}})(a)},average:function(a){return function(b){for(var d=Array(a),f=a;f--;)d[f]=0;var f=0,e=!1,h=0;return new j(function(b){h+=b-d[f];d[f]=b;b=h/Math.max(1,e?a:f);++f==a&&(e=!0,f=0);return b},[b])}},count:function(b){return new a(function(){return function(a){return a+1}},0,!1,b)},countIf:function(b){return function(d){return new a(function(a){return function(d){return b(a)?d+1:d}},0,!1,d)}},keepIf:function(a){return function(b){return function(f){return new d(function(b){return!a(b)},b,f)}}},dropIf:function(a){return function(b){return function(f){return new d(a,
80−b,f)}}},keepWhen:function(a){return f(new j(function(a){return!a},[a]))},dropWhen:f,dropRepeats:function(a){return new i(a)},sampleOn:function(a){return function(b){return new l(a,b)}},timestamp:function(a){return new b(!0,a)},timeOf:function(a){return new b(!1,a)}}}();
81−var Dispatcher=function(){function e(a){if(!a.hasOwnProperty("defaultNumberOfKids"))return!0;var b=a.kids.length;if(0==b)return!1;if(b>a.defaultNumberOfKids)return!0;for(var d=!1;b--;)d=d||e(a.kids[b]);return d}var j=null,a=[],d=null;return{initialize:function(){j=Elm.main();j.hasOwnProperty("recv")||(j=Elm.Signal.constant(j));d=j.value;for(var i=[],b=a.length;b--;)e(a[b])&&i.push(a[b]);a=i;document.getElementById("content").appendChild(Render.render(d));i=document.getElementById("widthChecker").offsetWidth;
82−i!==window.innerWidth&&Dispatcher.notify(Elm.Window.dimensions.id,Value.Tuple(i,window.innerHeight));j=Elm.Signal.lift(function(a){var b=document.getElementById("content");Render.update(b.firstChild,d,a);return d=a})(j)},notify:function(d,b){for(var e=(new window.Date).getTime(),h=!1,j=a.length;j--;)h=a[j].recv(e,d,b)||h;return h},inputs:a}}();
83−Elm.HTTP=function(){function e(a){return function(d){return function(f){return function(c){return{"0":"Request",length:1,verb:b.castStringToJSString(a),url:b.castStringToJSString(d),data:null===f?null:b.castStringToJSString(f),headers:c}}}}}function j(a){return e("GET")(a)(null)(["Nil"])}function a(a,e){return function(f){if(""!==f.url){var c={value:["Waiting"]};a.push(c);var g=null;window.ActiveXObject&&(g=new ActiveXObject("Microsoft.XMLHTTP"));window.XMLHttpRequest&&(g=new XMLHttpRequest);g.onreadystatechange=
84−function(){4===g.readyState&&(c.value=200===g.status?["Success",l(g.responseText)]:["Failure",g.status,l(g.statusText)],setTimeout(function(){d(a,e)},0))};g.open(f.verb,f.url,!0);Elm.List.map(function(a){g.setRequestHeader(b.castStringToJSString(a[1]),b.castStringToJSString(a[2]))})(f.headers);g.send(f.data)}}}function d(a,b){0<a.length&&(Dispatcher.notify(b.id,a[0].value),"Waiting"!==a[0].value[0]&&(a.shift(),setTimeout(function(){d(a,b)},0)))}function i(b){var d=Elm.Signal.constant(["Waiting"]),
85−b=Elm.Signal.lift(a([],d))(b);return Elm.Signal.lift2(function(a){return function(){return a}})(d)(b)}var b=Elm.JavaScript,l=Elm.JavaScript.castJSStringToString;return{get:j,post:function(a){return function(b){return e("POST")(a)(b)(["Nil"])}},request:e,send:i,sendGet:function(a){return i(Elm.Signal.lift(j)(a))}}}();
86−Elm.Input=function(){var e=Elm.JavaScript,j=Elm.JavaScript.castJSStringToString,a=function(a,d){a.placeholder=e.castStringToJSString(d);var h=Elm.Signal.constant(["Nil"]);Value.addListener(a,"keyup",function(){Dispatcher.notify(h.id,j(a.value));a.focus()});a.style.padding="1px";return Value.Tuple(Value.wrap(a),h)},d=function(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a},i=function(a){for(var e=d("select"),h=[];"Cons"===a[0];){var i=d("option"),f=Value.toText(a[1][1]);
87−i.value=f;i.innerHTML=f;e.appendChild(i);h.push(a[1][2]);a=a[2]}var c=Elm.Signal.constant(h[0]);Value.addListener(e,"change",function(){Dispatcher.notify(c.id,h[e.selectedIndex])});return Value.Tuple(Value.wrap(e),c)};return{textArea:function(b){return function(e){var h=d("textarea");h.rows=e;h.cols=b;return a(h,"")}},textField:function(b){var e=d("input");e.type="text";return a(e,b)},password:function(b){var e=d("input");e.type="password";return a(e,b)},checkbox:function(a){var e=d("input");e.type=
88−"checkbox";e.checked=a;var h=Elm.Signal.constant(a);Value.addListener(e,"change",function(){Dispatcher.notify(h.id,e.checked)});return Value.Tuple(Value.wrap(e),h)},dropDown:i,stringDropDown:function(a){return i(Elm.List.map(function(a){return Value.Tuple(a,a)})(a))},button:function(a){var i=d("input");i.type="button";i.value=e.castStringToJSString(a);var h=Elm.Signal.constant(!1);Value.addListener(i,"click",function(){Dispatcher.notify(h.id,!0);Dispatcher.notify(h.id,!1)});return Value.Tuple(Value.wrap(i),
89−h)}}}();
90−Elm.Keyboard={Raw:function(){function e(a,i){return"Nil"===i[0]?i:i[1]===a?i[2]:["Cons",i[1],e(a,i[2])]}var j=Elm.Signal.constant(["Nil"]),a=Elm.Signal.constant(["Nothing"]);Value.addListener(document,"keydown",function(a){var e;a:{for(e=j.value;"Nil"!==e[0];){if(e[1]===a.keyCode){e=!0;break a}e=e[2]}e=!1}e||Dispatcher.notify(j.id,["Cons",a.keyCode,j.value])||this.removeEventListener("keydown",arguments.callee,!1)});Value.addListener(document,"keyup",function(a){var i=e(a.keyCode,j.value);Dispatcher.notify(j.id,
91−i)||this.removeEventListener("keyup",arguments.callee,!1)});Value.addListener(window,"blur",function(a){Dispatcher.notify(j.id,["Nil"])||this.removeEventListener("blur",arguments.callee,!1)});Value.addListener(document,"keypress",function(d){var e=Dispatcher.notify(a.id,["Just",d.charCode||d.keyCode]);Dispatcher.notify(a.id,["Nothing"]);e||this.removeEventListener("keypress",arguments.callee,!1)});return{keysDown:j,charPressed:a}}()};
92−Elm.Mouse=function(){function e(a){var b=0,d=0;a||(a=window.event);if(a.pageX||a.pageY)b=a.pageX,d=a.pageY;else if(a.clientX||a.clientY)b=a.clientX+document.body.scrollLeft+document.documentElement.scrollLeft,d=a.clientY+document.body.scrollTop+document.documentElement.scrollTop;return Value.Tuple(b,d)}var j=Elm.Signal.constant(Value.Tuple(0,0));j.defaultNumberOfKids=2;var a=Elm.Signal.lift(function(a){return a[1]})(j);a.defaultNumberOfKids=0;var d=Elm.Signal.lift(function(a){return a[2]})(j);d.defaultNumberOfKids=
93−0;var i=Elm.Signal.constant(!1),b=Elm.Signal.constant(!1),l=Elm.Signal.constant(Value.Tuple());Value.addListener(document,"click",function(a){var d=Dispatcher.notify(b.id,!0),f=Dispatcher.notify(l.id,Value.Tuple());Dispatcher.notify(b.id,!1);!d&&!f&&this.removeEventListener("click",arguments.callee,!1)});Value.addListener(document,"mousedown",function(a){Dispatcher.notify(i.id,!0)||this.removeEventListener("mousedown",arguments.callee,!1)});Value.addListener(document,"mouseup",function(a){Dispatcher.notify(i.id,
94−!1)||this.removeEventListener("mouseup",arguments.callee,!1)});Value.addListener(document,"mousemove",function(a){Dispatcher.notify(j.id,e(a))||this.removeEventListener("mousemove",arguments.callee,!1)});return{position:j,x:a,y:d,isClicked:b,isDown:i,clicks:l,isClickedOn:function(a){var a=Render.render(a),b=Elm.Signal.constant(!1);Value.addListener(a,"click",function(){Dispatcher.notify(b.id,!0);Dispatcher.notify(b.id,!1)});return Value.Tuple(Value.wrap(a),b)}}}();
95−Elm.Random=function(){return{inRange:function(e){return function(j){return Elm.Signal.constant(Math.floor(Math.random()*(j-e+1))+e)}},randomize:function(e){return function(j){return function(a){return Elm.Signal.lift(function(){return Math.floor(Math.random()*(j-e+1))+e})(a)}}}}}();
96−Elm.Time=function(){function e(){return(new window.Date).getTime()}function j(a){return function(d){var i=1E3/a,b=e(),j=b,h=0,k=!0,f=Elm.Signal.constant(h),c=0;return Elm.Signal.lift2(function(a){return function(d){if(a){var m=!k&&a;c=setTimeout(function(){j=e();h=m?0:j-b;b=j;Dispatcher.notify(f.id,h)},i)}else k&&clearTimeout(c);k=a;return d}})(d)(f)}}Elm.Signal.constant(!0);return{fpsWhen:j,fps:function(a){return j(a)(Elm.Signal.constant(!0))},every:function(a){var d=Elm.Signal.constant(e());setInterval(function(){Dispatcher.notify(d.id,
97−e())},a);return d},delay:Elm.Signal.delay,since:function(a){return function(d){var e=Elm.Signal.count(Elm.Signal.delay(a)(d));return Elm.Signal.lift2(function(a){return function(d){return!Value.eq(a,d)}})(Elm.Signal.count(d))(e)}},after:function(a){var a=1E3*a,d=Elm.Signal.constant(!1);setTimeout(function(){Dispatcher.notify(d.id,!0)},a);return d},before:function(a){var a=1E3*a,d=Elm.Signal.constant(!0);setTimeout(function(){Dispatcher.notify(d.id,!1)},a);return d},hour:36E5,minute:6E4,second:1E3,
98−ms:1,inHours:function(a){return a/36E5},inMinutes:function(a){return a/6E4},inSeconds:function(a){return a/1E3},inMss:function(a){return a},toDate:function(a){return new window.Date(a)},read:function(a){a=window.Date.parse(a);return isNaN(a)?["Nothing"]:["Just",a]}}}();
99−Elm.Window=function(){var e=Elm.Signal.constant(Value.Tuple(window.innerWidth,window.innerHeight));e.defaultNumberOfKids=2;var j=Elm.Signal.lift(function(a){return a[1]})(e);j.defaultNumberOfKids=0;var a=Elm.Signal.lift(function(a){return a[2]})(e);a.defaultNumberOfKids=0;Value.addListener(window,"resize",function(a){var i=document.getElementById("widthChecker").offsetWidth;Dispatcher.notify(e.id,Value.Tuple(i,window.innerHeight))||this.removeEventListener("resize",arguments.callee,!1)});return{dimensions:e,
100−width:j,height:a}}();
101−Elm.Date=function(){var e="Sun Mon Tue Wed Thu Fri Sat".split(" "),j="Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec".split(" ");return{read:function(a){a=new window.Date(Elm.JavaScript.castStringToJSString(a));return isNaN(a.getTime())?["Nothing"]:["Just",a]},year:function(a){return a.getFullYear()},month:function(a){return[j[a.getMonth()]]},day:function(a){return a.getDate()},hour:function(a){return a.getHours()},minute:function(a){return a.getMinutes()},second:function(a){return a.getSeconds()},dayOfWeek:function(a){return[e[a.getDay()]]},
102−toTime:function(a){return a.getTime()},Mon:["Mon"],Tue:["Tue"],Wed:["Wed"],Thu:["Thu"],Fri:["Fri"],Sat:["Sat"],Sun:["Sun"],Jan:["Jan"],Feb:["Feb"],Mar:["Mar"],Apr:["Apr"],May:["May"],Jun:["Jun"],Jul:["Jul"],Aug:["Aug"],Sep:["Sep"],Oct:["Oct"],Nov:["Nov"],Dec:["Dec"]}}();Value.addListener(document,"elm_log",function(e){console.log(e.value)});Value.addListener(document,"elm_title",function(e){document.title=e.value});
103−Value.addListener(document,"elm_redirect",function(e){0<e.value.length&&(window.location=e.value)});
104−Elm.Prelude=function(){function e(a){return function(d){if(a instanceof Array&&d instanceof Array){var i=a.length;if(i==d.length){for(var b=1;b<i;++b){var j=e(a[b])(d[b]);if("EQ"!==j[0])return j}return["EQ"]}return[1==d.length?"GT":"LT"]}return[a===d?"EQ":a<d?"LT":"GT"]}}var j=function(a){return function(d){var e=a%d,e=0==a?0:0<d?0<=a?e:e+d:-j(-a)(-d);return e==d?0:e}};return{eq:Value.eq,id:function(a){return a},not:function(a){return!a},fst:function(a){return a[1]},snd:function(a){return a[2]},rem:function(a){return function(d){return a%
105−d}},div:function(a){return function(d){return~~(a/d)}},otherwise:!0,compare:e,toFloat:function(a){return a},round:function(a){return Math.round(a)},floor:function(a){return Math.floor(a)},ceiling:function(a){return Math.ceil(a)},truncate:function(a){return~~a},readInt:function(a){var a=Elm.JavaScript.castStringToJSString(a),d=a.length;if(0===d)return["Nothing"];var e=0;if("-"==a[0]){if(1===d)return["Nothing"];e=1}for(;e<d;++e)if(!Elm.Char.isDigit(a[e]))return["Nothing"];return["Just",parseInt(a)]},
106−readFloat:function(a){var a=Elm.JavaScript.castStringToJSString(a),d=a.length;if(0===d)return["Nothing"];var e=0;if("-"==a[0]){if(1===d)return["Nothing"];e=1}for(var b=0;e<d;++e)if(!Elm.Char.isDigit(a[e])){if("."===a[e]&&(b+=1,1>=b))continue;return["Nothing"]}return["Just",parseFloat(a)]},sqrt:Math.sqrt,abs:Math.abs,pi:Math.PI,e:Math.E,sin:Math.sin,cos:Math.cos,tan:Math.tan,asin:Math.asin,acos:Math.acos,atan:Math.atan,atan2:function(a){return function(d){return Math.atan2(a,d)}},mod:j,min:function(a){return function(d){return Math.min(a,
107−d)}},max:function(a){return function(d){return Math.max(a,d)}},flip:function(a){return function(d){return function(e){return a(e)(d)}}},clamp:function(a){return function(d){return function(e){return Math.min(d,Math.max(a,e))}}},curry:function(a){return function(d){return function(e){return a(["Tuple2",d,e])}}},uncurry:function(a){return function(d){if("Tuple2"!==d[0])throw"Function was uncurry'd but was not given a pair.";return a(d[1])(d[2])}},logBase:function(a){return function(d){return Math.log(d)/
108−Math.log(a)}},Just:Elm.Maybe.Just,Nothing:Elm.Maybe.Nothing,maybe:Elm.Maybe.maybe,map:Elm.List.map,zip:Elm.List.zip,zipWith:Elm.List.zipWith,filter:Elm.List.filter,head:Elm.List.head,tail:Elm.List.tail,last:Elm.List.last,length:Elm.List.length,reverse:Elm.List.reverse,foldr:Elm.List.foldr,foldr1:Elm.List.foldr1,foldl:Elm.List.foldl,foldl1:Elm.List.foldl1,and:Elm.List.and,or:Elm.List.or,all:Elm.List.all,any:Elm.List.any,sum:Elm.List.sum,product:Elm.List.product,concat:Elm.List.concat,concatMap:Elm.List.concatMap,
109−maximum:Elm.List.maximum,minimum:Elm.List.minimum,scanl:Elm.List.scanl,scanl1:Elm.List.scanl1,take:Elm.List.take,drop:Elm.List.drop,zip:Elm.List.zip,unzip:Elm.List.unzip,lift:Elm.Signal.lift,lift2:Elm.Signal.lift2,lift3:Elm.Signal.lift3,lift4:Elm.Signal.lift4,lift5:Elm.Signal.lift5,lift6:Elm.Signal.lift6,lift7:Elm.Signal.lift7,lift8:Elm.Signal.lift8,foldp:Elm.Signal.foldp,foldp1:Elm.Signal.foldp1,foldp_:Elm.Signal.foldp_,constant:Elm.Signal.constant,merge:Elm.Signal.merge,count:Elm.Signal.count,countIf:Elm.Signal.countIf,
110−average:Elm.Signal.average,keepIf:Elm.Signal.keepIf,dropIf:Elm.Signal.dropIf,keepWhen:Elm.Signal.keepWhen,dropWhen:Elm.Signal.dropWhen,dropRepeats:Elm.Signal.dropRepeats,sampleOn:Elm.Signal.sampleOn,timestamp:Elm.Signal.timestamp,timeOf:Elm.Signal.timeOf}}();(function(){var e=function(e){for(var a in e)Elm.Prelude[a]=e[a]};e(Elm.Color);e(Elm.Text);e(Elm.Graphics);e(Elm.Time);show=Value.show})();
111−Elm.Dict=function(){function e(a){return function(b){return function(c){return function(d){return function(e){return["RBNode",a,b,c,d,e]}}}}}function j(a){a:{switch(a[0]){case "RBEmpty":throw"(min RBEmpty) is not defined";case "RBNode":switch(a[4][0]){case "RBEmpty":a=["Tuple2",a[2],a[3]];break a}a=j(a[4]);break a}throw"Non-exhaustive pattern match in case";}return a}function a(b){return function(c){var d;a:{switch(c[0]){case "RBEmpty":d=v;break a;case "RBNode":d=function(){switch(p(b)(c[2])[0]){case "EQ":return z(c[3]);
112−case "GT":return a(b)(c[5]);case "LT":return a(b)(c[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";}return d}}function d(a){return function(b){return function(c){var e;a:{switch(c[0]){case "RBEmpty":e=a;break a;case "RBNode":e=function(){switch(p(b)(c[2])[0]){case "EQ":return c[3];case "GT":return d(a)(b)(c[5]);case "LT":return d(a)(b)(c[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";
113−}return e}}}function i(b){return function(c){return E(a(b)(c))}}function b(a){a:{switch(a[0]){case "RBNode":switch(a[5][0]){case "RBNode":a=e(a[1])(a[5][2])(a[5][3])(e(A)(a[2])(a[3])(a[4])(a[5][4]))(a[5][5]);break a}}throw"rotateLeft of a node without enough children";}return a}function l(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":a=e(a[1])(a[4][2])(a[4][3])(a[4][4])(e(A)(a[2])(a[3])(a[4][5])(a[5]));break a}}throw"rotateRight of a node without enough children";}return a}function h(a){a:{switch(a[0]){case "Black":a=
114−A;break a;case "Red":a=D;break a}throw"Non-exhaustive pattern match in case";}return a}function k(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[5][0]){case "RBNode":a=e(h(a[1]))(a[2])(a[3])(e(h(a[4][1]))(a[4][2])(a[4][3])(a[4][4])(a[4][5]))(e(h(a[5][1]))(a[5][2])(a[5][3])(a[5][4])(a[5][5]));break a}}}throw"color_flip called on a RBEmpty or RBNode with a RBEmpty child";}return a}function f(a){a:switch(a[0]){case "RBNode":switch(a[5][0]){case "RBNode":switch(a[5][1][0]){case "Red":a=
115−b(a);break a}}}a:switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":switch(a[4][4][0]){case "RBNode":switch(a[4][4][1][0]){case "Red":a=l(a);break a}}}}}a:switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":switch(a[5][0]){case "RBNode":switch(a[5][1][0]){case "Red":a=k(a);break a}}}}}return a}function c(a){a:switch(a[0]){case "RBNode":switch(a[1][0]){case "Red":a=e(D)(a[2])(a[3])(a[4])(a[5]);break a}}return a}function g(a){return function(b){return function(d){var g=
116−function(c){var d;a:{switch(c[0]){case "RBEmpty":d=e(A)(a)(b)(y)(y);break a;case "RBNode":d=function(){switch(p(a)(c[2])[0]){case "EQ":return e(c[1])(c[2])(b)(c[4])(c[5]);case "GT":return e(c[1])(c[2])(c[3])(c[4])(g(c[5]));case "LT":return e(c[1])(c[2])(c[3])(g(c[4]))(c[5])}throw"Non-exhaustive pattern match in case";}();d=f(d);break a}throw"Non-exhaustive pattern match in case";}return d};return c(g(d))}}}function r(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":a=
117−!0;break a}}}a=!1}return a}function m(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][4][0]){case "RBNode":switch(a[4][4][1][0]){case "Red":a=!0;break a}}}}a=!1}return a}function n(a){if(w(r(a))&&w(m(a))){a=k(a);a:switch(a[0]){case "RBNode":b:switch(a[5][0]){case "RBNode":switch(a[5][4][0]){case "RBNode":switch(a[5][4][1][0]){case "Red":a=k(b(e(a[1])(a[2])(a[3])(a[4])(l(a[5]))));break b}}}break a}}return a}function u(a){return function(b){var d=function(b){a:{switch(b[0]){case "RBEmpty":b=
118−y;break a;case "RBNode":if("LT"===p(a)(b[2])[0])b:{b=n(b);switch(b[0]){case "RBEmpty":throw"delLT on RBEmpty";case "RBNode":b=f(e(b[1])(b[2])(b[3])(d(b[4]))(b[5]));break b}break}else{var g=r(b)?l(b):b,h;b:{switch(g[0]){case "RBNode":switch(g[5][0]){case "RBEmpty":h=C(a,g[2]);break b}}h=!1}if(h)b=g[4];else{g=w;b:{switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":h=!0;break b}}}h=!1}if(g=g(h)){g=w;b:{switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][4][0]){case "RBNode":switch(b[5][4][1][0]){case "Red":h=
119−!0;break b}}}}h=!1}g=g(h)}g&&(b=k(b),b=m(b)?k(l(b)):b);b:{switch(b[0]){case "RBNode":g=C(a,b[2]);break b}g=!1}if(g)b:{switch(b[0]){case "RBEmpty":throw"delEQ called on a RBEmpty";case "RBNode":h=j(b[5]);c:{switch(h[0]){case "Tuple2":g=h[1];break c}break}c:{switch(h[0]){case "Tuple2":h=h[2];break c}break}var g=e(b[1])(g)(h)(b[4]),i=function(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBEmpty":a=y;break a}}b:{a=n(a);switch(a[0]){case "RBEmpty":a=y;break b;case "RBNode":a=f(e(a[1])(a[2])(a[3])(i(a[4]))(a[5]));
120−break b}throw"Non-exhaustive pattern match in case";}}return a},b=c(i(b[5])),b=f(g(b));break b}break}else b:{switch(b[0]){case "RBEmpty":throw"delGT called on a RBEmpty";case "RBNode":b=f(e(b[1])(b[2])(b[3])(b[4])(d(b[5])));break b}break}}}break a}throw"Non-exhaustive pattern match in case";}return b};return i(a)(b)?c(d(b)):b}}function x(a){return function(b){a:{switch(b[0]){case "RBEmpty":b=y;break a;case "RBNode":b=e(b[1])(b[2])(a(b[3]))(x(a)(b[4]))(x(a)(b[5]));break a}throw"Non-exhaustive pattern match in case";
121−}return b}}function q(a){return function(b){return function(c){a:{switch(c[0]){case "RBEmpty":c=b;break a;case "RBNode":c=q(a)(a(c[2])(c[3])(q(a)(b)(c[4])))(c[5]);break a}throw"Non-exhaustive pattern match in case";}return c}}}function t(a){return function(b){return function(c){a:{switch(c[0]){case "RBEmpty":c=b;break a;case "RBNode":c=t(a)(a(c[2])(c[3])(t(a)(b)(c[5])))(c[4]);break a}throw"Non-exhaustive pattern match in case";}return c}}}var p=Elm.Prelude.compare,s=Elm.Prelude.uncurry,v=Elm.Prelude.Nothing,
122−z=Elm.Prelude.Just,w=Elm.Prelude.not,C=Elm.Prelude.eq,E=Elm.Maybe.isJust,A=["Red"],D=["Black"],y=["RBEmpty"],B=y;return{$op:{},empty:B,lookup:a,findWithDefault:d,member:i,insert:g,singleton:function(a){return function(b){return g(a)(b)(y)}},remove:u,map:x,foldl:q,foldr:t,union:function(a){return function(b){return q(g)(b)(a)}},intersect:function(a){return function(b){return q(function(a){return function(c){return function(d){return i(a)(b)?g(a)(c)(d):d}}})(B)(a)}},diff:function(a){return function(b){return q(function(a){return function(){return function(b){return u(a)(b)}}})(a)(b)}},
123−keys:function(a){return t(function(a){return function(){return function(b){return["Cons",a,b]}}})(["Nil"])(a)},values:function(a){return t(function(){return function(a){return function(b){return["Cons",a,b]}}})(["Nil"])(a)},toList:function(a){return t(function(a){return function(b){return function(c){return["Cons",["Tuple2",a,b],c]}}})(["Nil"])(a)},fromList:function(a){return Elm.List.foldl(s(g))(B)(a)}}}();
124−Elm.Set=function(){var e=Elm.Dict.empty,j=Elm.Dict.remove,a=Elm.Dict.member,d=Elm.Dict.union,i=Elm.Dict.intersect,b=Elm.Dict.diff,l=Elm.Dict.keys,h=Elm.List.foldl(function(a){return function(b){return Elm.Dict.insert(a)(["Tuple0"])(b)}})(e);return{empty:e,singleton:function(a){return Elm.Dict.singleton(a)(["Tuple0"])},insert:function(a){return Elm.Dict.insert(a)(["Tuple0"])},remove:j,member:a,union:d,intersect:i,diff:b,toList:l,fromList:h,foldl:function(a){return Elm.Dict.foldl(function(b){return function(){return function(c){return a(b)(c)}}})},
125−foldr:function(a){return Elm.Dict.foldr(function(b){return function(){return function(c){return a(b)(c)}}})},map:function(a){return function(b){b=l(b);return h(Elm.List.map(a)(b))}}}}();
126−(function(){try{var e={};for(this.i in Elm)eval("var "+this.i+"=Elm[this.i];");if(Elm.Automaton)throw"Module name collision, 'Automaton' is already defined.";Elm.Automaton=function(){function a(a){return["Automaton",a]}function d(b){return a(function(a){var c=unzip(map(function(b){a:{switch(b[0]){case "Automaton":b=b[1](a);break a}throw"Non-exhaustive pattern match in case";}return b})(b)),e;a:{switch(c[0]){case "Tuple2":e=c[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(c[0]){case "Tuple2":c=
127−c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",e,d(c)]})}function i(b){return a(function(a){return["Tuple2",b(a),i(b)]})}function b(c){return function(d){return a(function(a){a=d(a)(c);return["Tuple2",a,b(a)(d)]})}}function j(b){return function(c){return a(function(a){var d=c(a)(b);a:{switch(d[0]){case "Tuple2":a=d[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(d[0]){case "Tuple2":d=d[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",
128−a,j(d)(c)]})}}function h(a){return function(b){a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":b=["Tuple2",a[1]-b[1],a[2]-b[2]];break b}break}break a}throw"Non-exhaustive pattern match in case";}return b}}function k(a){return function(b){var c;a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":var d=function(a){return["Tuple2",b[2],["Tuple2",a,b[2]]]};c=function(){switch(b[1][0]){case "DragFrom":var c;a[1]?c=["Tuple2",uncurry(move)(h(a[2])(b[1][1]))(b[2]),["Tuple2",["DragFrom",
129−b[1][1]],b[2]]]:(c=uncurry(move)(h(a[2])(b[1][1]))(b[2]),c=["Tuple2",c,["Tuple2",g,c]]);return c;case "Ignore":return d(a[1]?r:g);case "Listen":return d(not(a[1])?g:isWithin(a[2])(b[2])?["DragFrom",a[2]]:r)}throw"Non-exhaustive pattern match in case";}();break b}break}break a}throw"Non-exhaustive pattern match in case";}return c}}try{if(!(Elm.Prelude instanceof Object))throw"module not found";}catch(f){throw"Module 'Prelude' is missing. Compile with --make flag or load missing module in a separate JavaScript file.";
130−}var c={};for(this.i in Elm.Prelude)c[this.i]||eval("var "+this.i+" = Elm.Prelude[this.i];");var g=["Listen"],r=["Ignore"];e[">>>"]=function(b){return function(c){var d;a:{switch(b[0]){case "Automaton":d=b[1];break a}throw"Non-exhaustive pattern match in case";}var f;a:{switch(c[0]){case "Automaton":f=c[1];break a}throw"Non-exhaustive pattern match in case";}return a(function(a){var a=d(a),b;a:{switch(a[0]){case "Tuple2":b=a[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(a[0]){case "Tuple2":a=
131−a[2];break a}throw"Non-exhaustive pattern match in case";}var c=f(b);a:{switch(c[0]){case "Tuple2":b=c[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(c[0]){case "Tuple2":c=c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",b,e[">>>"](a)(c)]})}};e["<<<"]=function(a){return function(b){return e[">>>"](b)(a)}};e["^>>"]=function(a){return function(b){return e[">>>"](i(a))(b)}};e[">>^"]=function(a){return function(b){return e[">>>"](a)(i(b))}};e["^<<"]=function(a){return function(b){return e[">>>"](b)(i(a))}};
132−e["<<^"]=function(a){return function(b){return e[">>>"](i(b))(a)}};c=b(0)(function(){return function(a){return 1+a}});return{$op:{">>>":e[">>>"],"<<<":e["<<<"],"^>>":e["^>>"],">>^":e[">>^"],"^<<":e["^<<"],"<<^":e["<<^"]},run:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=lift(fst)(foldp_(function(a){return function(b){a:{switch(b[0]){case "Tuple2":switch(b[2][0]){case "Automaton":b=b[2][1](a);break a}}throw"Non-exhaustive pattern match in case";}return b}})(a[1])(b));break a}throw"Non-exhaustive pattern match in case";
133−}return b}},step:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=a[1](b);break a}throw"Non-exhaustive pattern match in case";}return b}},combine:d,pure:i,init:b,init_:j,count:c,draggable:function(a){return j(["Tuple2",g,a])(k)}}}();Elm.main=function(){return Elm.Automaton.main}}catch(j){Elm.main=function(){document.body.innerHTML=Elm.Text.monospace('<br/><h2>Your browser may not be supported. Are you using a modern browser?</h2><br/><span style="color:grey">Runtime Error in Automaton module:<br/>'+
134−j+"</span>");throw j;}}})();
elm/elm-runtime-0.7.1.1.jsdeleted−142
@@ -1,142 +0,0 @@
1−Elm={};var Guid=function(){var d=0;return{guid:function(){return d+=1}}}();
2−Elm.JavaScript=function(){function d(b){for(var a=["Nil"],c=b.length;c--;)a=["Cons",b[c],a];return a}function f(b){for(var a=[];"Cons"===b[0];)a.push(b[1]),b=b[2];return a}function b(b){return b.slice(1)}function c(b){return["Tuple"+b.length].concat(b)}return{castJSBoolToBool:function(b){return b},castBoolToJSBool:function(b){return b},castJSNumberToFloat:function(b){return b},castFloatToJSNumber:function(b){return b},castJSNumberToInt:function(b){return~~b},castIntToJSNumber:function(b){return b},
3−Experimental:{castJSElementToElement:function(b){return function(a){return function(c){return["Element",Guid.guid(),["EExternalHtml",c],b,a,1,["Nothing"],["Nothing"]]}}},castElementToJSElement:function(b){return Render.render(b)}},castJSArrayToList:d,castListToJSArray:f,castJSStringToString:d,castStringToJSString:function(b){return"string"===typeof b?b:f(b).join("")},castTupleToJSTuple2:b,castTupleToJSTuple3:b,castTupleToJSTuple4:b,castTupleToJSTuple5:b,castJSTupleToTuple2:c,castJSTupleToTuple3:c,
4−castJSTupleToTuple4:c,castJSTupleToTuple5:c}}();var JSjson=window.JSON;
5−Elm.JSON=function(){function d(a,b){return function(j){return function(l){var g=c.castStringToJSString(j);return l[1].hasOwnProperty(g)&&(l=l[1][g],l[0]===a)?l[1]:b}}}function f(a){return function(b){function j(a){switch(a[0]){case "JsonNull":return null;case "JsonString":return c.castStringToJSString(a[1]);case "JsonObject":var g={};a=a[1][1];for(var e in a)g[e]=j(a[e]);return g;case "JsonArray":g=c.castListToJSArray(a[1]);for(e=g.length;e--;)g[e]=j(g[e]);return g;default:return a[1]}}return JSjson.stringify(j(["JsonObject",
6−b]),null,c.castStringToJSString(a))}}function b(a){function b(a){switch(typeof a){case "string":return["JsonString",c.castJSStringToString(a)];case "number":return["JsonNumber",c.castJSNumberToFloat(a)];case "boolean":return["JsonBool",c.castJSBoolToBool(a)];case "object":if(null===a)return["JsonNull"];for(var g in a)a[g]=b(a[g]);return a instanceof Array?["JsonArray",c.castJSArrayToList(a)]:["JsonObject",["JSON",a]]}}a=JSjson.parse(a);for(var j in a)a[j]=b(a[j]);return["JSON",a]}var c=Elm.JavaScript,
7−h=["JSON",{}];return{empty:h,singleton:function(a){return function(b){var j={};j[c.castStringToJSString(a)]=b;return["JSON",j]}},insert:function(a){return function(b){return function(j){j=j[1];var l={},g;for(g in j)l[g]=j[g];l[c.castStringToJSString(a)]=b;return["JSON",l]}}},lookup:function(a){return function(b){var j=c.castStringToJSString(a);return b[1].hasOwnProperty(j)?["Just",b[1][j]]:["Nothing"]}},findString:d("JsonString",["Nil"]),findObject:d("JsonObject",h),findArray:d("JsonArray",["Nil"]),
8−findWithDefault:function(a){return function(b){return function(j){var l=c.castStringToJSString(b);return j[1].hasOwnProperty(l)?j[1][l]:a}}},remove:function(a){return function(b){b=b[1];var j={},l;for(l in b)j[l]=b[l];delete j[c.castStringToJSString(a)];return["JSON",j]}},toPrettyJSString:f,toJSString:f(""),fromJSString:b,toPrettyString:function(a){return function(b){return c.castJSStringToString(f(a)(b))}},toString:function(a){return c.castJSStringToString(f("")(a))},fromString:function(a){return b(c.castStringToJSString(a))},
9−toList:function(a){a=a[1];var b=[],j;for(j in a)b.push(Value.Tuple(c.castJSStringToString(j),a[j]));return c.castJSArrayToList(b)},fromList:function(a){a=c.castListToJSArray(a);for(var b={},j=a.length;j--;)b[c.castStringToJSString(a[j][1])]=a[j][2];return["JSON",b]},JsonString:function(a){return["JsonString",a]},JsonNumber:function(a){return["JsonNumber",a]},JsonBool:function(a){return["JsonBool",a]},JsonNull:["JsonNull"],JsonArray:function(a){return["JsonArray",a]},JsonObject:function(a){return["JsonObject",
10−a]}}}();
11−var Value=function(){function d(a){if(0==a.length)return a;a=a.replace(/"/g,"&#34;").replace(/'/g,"&#39;").replace(/</g,"&#60;").replace(/>/g,"&#62;").replace(/\n/g,"<br/>");a=a.split("<br/>");for(var b=a.length;b--;){var c=a,l=b,g;g=a[b];if(0!=g.length){g=g.split("");" "==g[0]&&(g[0]="&nbsp;");for(var e=g.length;--e;)" "==g[e][0]&&" "==g[e-1]&&(g[e-1]+=g[e],g[e]="");for(e=g.length;e--;)if(1<g[e].length&&" "==g[e][0]){for(var k=g[e].split(""),f=k.length-2;0<=f;f-=2)k[f]="&nbsp;";g[e]=k.join("")}g=g.join("");
12−g=" "===g[g.length-1]?g.slice(0,-1)+"&nbsp;":g}c[l]=g}return a.join("<br/>")}var f=function(a,b){if("object"===typeof a){if(a.hasOwnProperty("_")){for(var c in a)if(a[c]!=b[c])return!1;for(c in b)if(a[c]!=b[c])return!1;return!0}if(a===b)return!0;if(a.length!==b.length)return!1;for(c=a.length;c--;)if(!f(a[c],b[c]))return!1;return!0}return a===b},b=function(a){if("function"===typeof a)return"<function>";if("boolean"===typeof a)return a?"True":"False";if("number"!==typeof a){if("string"===typeof a&&
13−2>a.length)return"'"+a+"'";if("object"===typeof a&&a.hasOwnProperty("_")){var c=[],j;for(j in a)if("_"!=j)for(var l=a[j].length;l--;)c.push(j+" = "+b(a[j][l]));return 0===c.length?"{}":"{ "+c.join(", ")+" }"}if(a[0]){if("Tuple"===a[0].substring(0,5)){c=Array(a.length-1);for(l=a.length;--l;)c[l-1]=b(a[l]);return"("+c.join(",")+")"}if("Cons"===a[0]){j="string"===typeof a[1]?'"':"]";var l="string"===typeof a[1]?"":",",g="string"===typeof a[1]?function(a){return a}:b,c=("string"===typeof a[1]?'"':"[")+
14−g(a[1]);for(a=a[2];;)if("Cons"===a[0])c+=l+g(a[1]),a=a[2];else return c+j}else{if("Nil"===a[0])return"[]";if("JSON"===a[0])return"(JSON.fromList "+b(Elm.JSON.toList(a))+")";if("RBNode"===a[0]||"RBEmpty"===a[0])return a=Elm.Dict.foldr(function(a){return function(g){return function(b){return["Cons",["Tuple2",a,g],b]}}})(["Nil"])(a),c="Dict","Cons"===a[0]&&"Tuple0"===a[1][2][0]&&(c="Set",a=Elm.List.map(function(a){return a[1]})(a)),"("+c+".fromList "+b(a)+")";c="";for(l=a.length;--l;)c=" "+b(a[l])+c;
15−c=a[0]+c;return 1<a.length?"("+c+")":c}}}return a+""},c=function(a){for(var b=["Nil"],c=a.length;c--;)b=["Cons",a[c],b];return b},h;h=document.addEventListener?function(a,b,c){a.addEventListener(b,c,!1)}:function(a,b,c){a.attachEvent("on"+b,c)};return{eq:f,str:c,show:function(a){return c(b(a))},Tuple:function(){var a=arguments.length,b=Array(a+1);for(b[0]="Tuple"+arguments.length;a--;)b[a+1]=arguments[a];return b},append:function(a,b){if("string"===typeof a&&"string"===typeof b)return a.concat(b);
16−if("Nil"===a[0])return b;var c=["Cons",a[1],["Nil"]],l=c;for(a=a[2];"Cons"===a[0];)l[2]=["Cons",a[1],["Nil"]],a=a[2],l=l[2];l[2]=b;return c},listToArray:function(a){for(var b=[];"Cons"===a[0];)b.push(a[1]),a=a[2];return b},toText:function(a){if("string"===typeof a)return d(a);for(var b=[];"Cons"===a[0];)b.push(a[1]),a=a[2];return d(b.join(""))},properEscape:d,getTextSize:function(a,b,c){var l=document.createElement("div");l.innerHTML=c;l.style.textAlign="left";0<a&&(l.style.width=a+"px");l.style.visibility=
17−"hidden";l.style.styleFloat="left";l.style.cssFloat="left";document.body.appendChild(l);c=window.getComputedStyle(l,null);a=c.getPropertyValue("width").slice(0,-2)-0;c=c.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(l);return[Math.ceil(a),Math.ceil(Math.max(b,c))]},getSize:function(a){a=a.cloneNode(!0);a.style.visibility="hidden";a.style.styleFloat="left";a.style.cssFloat="left";document.body.appendChild(a);var b=a.offsetWidth,c=a.offsetHeight;document.body.removeChild(a);return[b,
18−c]},getExcess:function(a){a=a.cloneNode(!0);a.style.visibility="hidden";a.style.styleFloat="left";a.style.cssFloat="left";document.body.appendChild(a);var b=a.offsetWidth,c=a.offsetHeight,l=window.getComputedStyle(a,null),g=l.getPropertyValue("width").slice(0,-2)-0,l=l.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(a);return[b-g,c-l]},groupForms:function(a){a=Elm.JavaScript.castListToJSArray(a);for(var b=[],c=[],l=a.length;l--;){var g=a[l];switch(g[4][0]){case "FElement":0<c.length&&
19−(b.push(c),c=[]);b.push(g);break;default:c.push(g)}}0<c.length&&b.push(c);return b},wrap:function(b){var c=Value.getSize(b);return["Element",Guid.guid(),["EHtml",b],c[0],c[1],1,["Nothing"],["Nothing"]]},addListener:h}}();
20−Elm.List=function(){function d(b){return function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&g("map");var e=["Cons",b(a[1]),["Nil"]],c=e;for(a=a[2];"Cons"===a[0];)c[2]=["Cons",b(a[1]),["Nil"]],a=a[2],c=c[2];return e}}function f(a){return function(b){return function(e){var c=b;if("Nil"===e[0])return c;for("Cons"!==e[0]&&g("foldl");"Cons"===e[0];)c=a(e[1])(c),e=e[2];return c}}}function b(a){return function(b){return function(e){var c=b;if("Nil"===e[0])return c;"Cons"!==e[0]&&g("foldr");for(var k=[];"Cons"===
21−e[0];)k.push(e[1]),e=e[2];for(e=k.length;e--;)c=a(k[e])(c);return c}}}function c(a){return function(b){var g;"Cons"!==b[0]?g=void 0:(g=b[1],b=b[2],g=f(a)(g)(b));return g}}function h(b){return function(a){return function(e){if("Nil"===e[0])return["Cons",a,["Nil"]];"Cons"!==e[0]&&g("scanl");for(var c=[a];"Cons"===e[0];)a=b(e[1])(a),c.push(a),e=e[2];e=["Nil"];for(var k=c.length;k--;)e=["Cons",c[k],e];return e}}}function a(b){return function(e){a:{for(var g=[function(b){return"Nil"!==b[0]?void 0:["Tuple2",
22−["Nil"],["Nil"]]},function(e){if("Cons"===e[0]){var g=e[1];e=e[2];var c=a(b)(e);"Tuple2"!==c[0]?g=void 0:(e=c[1],c=c[2],g=b(g)?["Tuple2",["Cons",g,e],c]:["Tuple2",e,["Cons",g,c]]);return g}}],c=g.length;c--;){var k=g[c](e);if(void 0!==k){e=k;break a}}e=void 0}return e}}function m(b){a:{for(var a=[function(b){return"Nil"!==b[0]?void 0:["Tuple2",["Nil"],["Nil"]]},function(b){if("Cons"!==b[0])b=void 0;else if(b=["Tuple2",b[1],m(b[2])],"Tuple2"!==b[0]||"Tuple2"!==b[1][0])b=void 0;else{var a=b[1][1],e=
23−b[1][2];b="Tuple2"!==b[2][0]?void 0:["Tuple2",["Cons",a,b[2][1]],["Cons",e,b[2][2]]]}return b}],e=a.length;e--;){var g=a[e](b);if(void 0!==g){b=g;break a}}b=void 0}return b}function j(b){return function(a){a:{for(var e=[function(b){return"Nil"!==b[0]?void 0:["Nil"]},function(b){if("Cons"===b[0]){var a=b[1];return"Nil"!==b[2][0]?void 0:["Cons",a,["Nil"]]}},function(a){if("Cons"===a[0]){var e=a[1];if("Cons"===a[2][0]){var g=a[2][1];a=a[2][2];return["Cons",e,["Cons",b,j(b)(["Cons",g,a])]]}}}],g=e.length;g--;){var c=
24−e[g](a);if(void 0!==c){a=c;break a}}a=void 0}return a}}function l(b){return function(a){a:{for(var e=[function(b){return"Nil"!==b[0]?void 0:["Nil"]},function(b){if("Cons"===b[0]){var a=b[1];return"Nil"!==b[2][0]?void 0:a}},function(a){if("Cons"===a[0]){var e=a[1];if("Cons"===a[2][0]){var g=a[2][1];a=a[2][2];return Value.append(e,Value.append(b,l(b)(["Cons",g,a])))}}}],g=e.length;g--;){var c=e[g](a);if(void 0!==c){a=c;break a}}a=void 0}return a}}var g=function(b){throw"Function '"+b+"' expecting a list!";
25−},e=f(function(b){return function(a){return["Cons",b,a]}})(["Nil"]),k=b(function(b){return function(a){return Value.append(b,a)}})(["Nil"]),x=f(function(b){return function(a){return b&&a}})(!0),n=f(function(b){return function(a){return b||a}})(!1),p=f(function(b){return function(a){return b+a}})(0),s=f(function(b){return function(a){return b*a}})(1),v=c(function(b){return function(a){return Math.max(b,a)}}),t=c(function(b){return function(a){return Math.min(b,a)}});return{head:function(b){if("Cons"!==
26−b[0])throw"Error: 'head' only accepts lists of length greater than one.";return b[1]},tail:function(b){if("Cons"!==b[0])throw"Error: 'tail' only accepts lists of length greater than one.";return b[2]},last:function(b){if("Cons"!==b[0])throw"Error: 'last' only accepts lists of length greater than one.";for(var a=b[1];"Cons"===b[0];)a=b[1],b=b[2];return a},map:d,foldl:f,foldr:b,foldl1:c,foldr1:function(b){return function(a){if("Nil"===a[0])throw"'foldr1' requires an non-empty list.";"Cons"!==a[0]&&
27−g("foldr1");for(var e=[];"Cons"===a[0];)e.push(a[1]),a=a[2];a=e.pop();for(var c=e.length;c--;)a=b(e[c])(a);return a}},scanl:h,scanl1:function(b){return function(a){if("Cons"!==a[0])throw"Error: 'scanl1' requires a list of at least length 1.";return h(b)(a[1])(a[2])}},filter:function(b){return function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&g("filter");for(var e=[];"Cons"===a[0];)b(a[1])&&e.push(a[1]),a=a[2];a=["Nil"];for(var c=e.length;c--;)a=["Cons",e[c],a];return a}},length:function(b){for(var a=
28−0;"Cons"===b[0];)a+=1,b=b[2];return a},reverse:e,concat:k,concatMap:function(b){return function(a){return k(d(b)(a))}},and:x,or:n,all:function(b){return f(function(a){return function(e){return e&&b(a)}})(!0)},any:function(b){return f(function(a){return function(e){return e||b(a)}})(!1)},sum:p,product:s,maximum:v,minimum:t,partition:a,zipWith:function(b){return function(a){return function(e){if("Nil"===a[0]||"Nil"===e[0])return["Nil"];("Cons"!==a[0]||"Cons"!==e[0])&&g("zipWith");for(var c=[];"Cons"===
29−a[0]&&"Cons"===e[0];)c.push(b(a[1])(e[1])),a=a[2],e=e[2];e=["Nil"];for(var k=c.length;k--;)e=["Cons",c[k],e];return e}}},zip:function(a){return function(b){if("Nil"===a[0]||"Nil"===b[0])return["Nil"];("Cons"!==a[0]||"Cons"!==b[0])&&g("zip");for(var e=[];"Cons"===a[0]&&"Cons"===b[0];)e.push(["Tuple2",a[1],b[1]]),a=a[2],b=b[2];b=["Nil"];for(var c=e.length;c--;)b=["Cons",e[c],b];return b}},unzip:m,intersperse:j,intercalate:l,sort:function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&g("sort");for(var b=
30−[];"Cons"===a[0];)b.push(a[1]),a=a[2];b.sort(function(a,b){return a-b});a=["Nil"];for(var e=b.length;e--;)a=["Cons",b[e],a];return a},take:function(a){return function(b){if(0>=a)return["Nil"];if("Nil"===b[0])return b;"Cons"!==b[0]&&g("take");var e=["Cons",b[1],["Nil"]],c=e;b=b[2];for(--a;"Cons"===b[0]&&0<a;)c[2]=["Cons",b[1],["Nil"]],c=c[2],b=b[2],--a;return e}},drop:function(a){return function(b){if("Nil"===b[0])return b;for("Cons"!==b[0]&&g("drop");"Cons"===b[0]&&0<a;)b=b[2],--a;return b}}}}();
31−Elm.Maybe=function(){function d(f){return function(b){return"Just"===f[0]?["Cons",f[1],b]:b}}return{Just:function(f){return["Just",f]},Nothing:["Nothing"],justs:Elm.List.foldr(d)(["Nil"]),isJust:function(f){return"Just"===f[0]},isNothing:function(f){return"Nothing"===f[0]},cons:d,maybe:function(f){return function(b){return function(c){return"Just"===c[0]?b(c[1]):f}}}}}();
32−Elm.Either=function(){function d(b){return"Left"==b[0]}function f(b){return"Right"==b[0]}function b(b){return Elm.List.map(function(b){return b[1]})(b)}return{Left:function(b){return["Left",b]},Right:function(b){return["Right",b]},either:function(b){return function(f){return function(a){switch(a[0]){case "Left":return b(a[1]);case "Right":return f(a[1])}}}},isLeft:d,isRight:f,lefts:function(c){return b(Elm.List.filter(d)(c))},rights:function(c){return b(Elm.List.filter(f)(c))},partition:function(c){c=
33−Elm.List.partition(d)(c);c[1]=b(c[1]);c[2]=b(c[2]);return c}}}();
34−Elm.Char=function(){function d(b,a){return function(c){c=c.charCodeAt(0);return b<=c&&c<=a}}var f=d(48,57),b=d(97,102),c=d(65,70);return{fromCode:function(b){return String.fromCharCode(b)},toCode:function(b){return b.charCodeAt(0)},toUpper:function(b){return b.toUpperCase()},toLower:function(b){return b.toLowerCase()},toLocaleUpper:function(b){return b.toLocaleUpperCase()},toLocaleLower:function(b){return b.toLocaleLowerCase()},isLower:d(97,122),isUpper:d(65,90),isDigit:f,isOctDigit:d(48,55),isHexDigit:function(d){return f(d)||
35−b(d)||c(d)}}}();
36−Elm.Color=function(){function d(f){var b=f.value*f.saturation,c=f.hue/60,d=b*(1-Math.abs(c%2-1)),a=0,m=0,j=0;0<=c&&1>c?(a=b,m=d,j=0):1<=c&&2>c?(a=d,m=b,j=0):2<=c&&3>c?(a=0,m=b,j=d):3<=c&&4>c?(a=0,m=d,j=b):4<=c&&5>c?(a=d,m=0,j=b):5<=c&&6>c&&(a=b,m=0,j=d);f=f.value-b;return["Color",Math.round(255*(a+f)),Math.round(255*(m+f)),Math.round(255*(j+f)),1]}return{rgba:function(f){return function(b){return function(c){return function(d){return["Color",f,b,c,d]}}}},rgb:function(f){return function(b){return function(c){return["Color",f,
37−b,c,1]}}},hsva:function(f){return function(b){return function(c){return function(h){var a=d({hue:f,saturation:b,value:c});a[4]=h;return a}}}},hsv:function(f){return function(b){return function(c){return d({hue:f,saturation:b,value:c})}}},red:["Color",255,0,0,1],green:["Color",0,255,0,1],blue:["Color",0,0,255,1],yellow:["Color",255,255,0,1],cyan:["Color",0,255,255,1],magenta:["Color",255,0,255,1],black:["Color",0,0,0,1],white:["Color",255,255,255,1],gray:["Color",128,128,128,1],grey:["Color",128,128,
38−128,1],complement:function(f){var b;b=f[1]/255;var c=f[2]/255;f=f[3]/255;var h=Math.max(b,c,f),a=Math.min(b,c,f),a=h-a,m=0;0===a?m=0:h===b?m=(c-f)/a%6:h===c?m=(f-b)/a+2:h===f&&(m=(b-c)/a+4);b={value:h,hue:60*m,saturation:0===h?0:a/h};b.hue=(b.hue+180)%360;return d(b)},extract:function(f){return 1===f[4]?"rgb("+f[1]+","+f[2]+","+f[3]+")":"rgba("+f[1]+","+f[2]+","+f[3]+","+f[4]+")"}}}();
39−var Collage=function(){function d(b,a){var e=a.length-1;if(!(0>=e))for(b.moveTo(a[e][1],a[e][2]);e--;)b.lineTo(a[e][1],a[e][2])}function f(b,a,e,c){0===b.length&&(b=[8,4]);var f=c.length-1;if(!(0>=f)){var n=c[f][1],p=c[f][2],d=0,j=0,h=0,m=0,q=0,u=0,w=b.length,z=!0,y=b[0];for(a.moveTo(n,p);f--;){d=c[f][1];j=c[f][2];h=d-n;m=j-p;for(q=Math.sqrt(h*h+m*m);y<=q;)n+=h*y/q,p+=m*y/q,a[z?"lineTo":"moveTo"](n,p),h=d-n,m=j-p,q=Math.sqrt(h*h+m*m),z=!z,u=(u+1)%w,y=b[u];0<q&&(a[z?"lineTo":"moveTo"](d,j),y-=q);n=
40−d;p=j}}a.strokeStyle=Elm.Color.extract(e);a.stroke()}function b(b,a,e,c,x){a.clearRect(0,0,e,c);for(e=x.length;e--;){var n=x[e],p=b;c=a;var h=n[1],m=n[2],t=n[3][1],r=n[3][2],n=n[4];c.save();(0!==t||0!==r)&&c.translate(t,r);h!==~~h&&c.rotate(2*Math.PI*h);1!==m&&c.scale(m,m);c.beginPath();switch(n[0]){case "FLine":a:switch(p=c,h=n,n=h[3][1],h[1][0]){case "Solid":h=h[2];d(p,n);p.strokeStyle=Elm.Color.extract(h);p.stroke();break;case "Dotted":f([3,3],p,h[2],n);break a;case "Dashed":f([8,4],p,h[2],n);
41−break a;case "Custom":f(h[1][1],p,h[2],n)}break;case "FShape":a:switch(t=p,m=c,p=n[1],h=n[2],n=n[3][1],p[0]){case "Filled":p=m;d(p,n);p.fillStyle=Elm.Color.extract(h);p.fill();break a;case "Outlined":p=m;d(p,n);p.strokeStyle=Elm.Color.extract(h);p.stroke();break a;case "Textured":h=t;p=p[1];t=new Image;t.src=j.castStringToJSString(p);t.onload=h;d(m,n);m.fillStyle=m.createPattern(t,"repeat");m.fill();break a;case "CustomOutline":f(p[1],m,h,n)}break;case "FImage":h=c,m=n[1],t=n[2],n=n[3],r=new Image,
42−r.onload=p,r.src=j.castStringToJSString(n),h.drawImage(r,-m/2,-t/2,m,t)}c.restore()}}function c(a,c,e){var k=Render.newElement("canvas");a=~~a;c=~~c;k.style.width=a+"px";k.style.height=c+"px";k.style.display="block";k.width=a;k.height=c;if(k.getContext){var f=k.getContext("2d");b(function(){b(this,f,a,c,e)},f,a,c,e);return k}k.innerHTML="Your browser does not support the canvas element.";return k}function h(b,a,e,c,f,n,d){b="translate("+(e-f/2)+"px,"+(c-n/2)+"px) "+(1===a?"":"scale("+a+","+a+")")+
43−" "+(b===~~b?"":"rotate("+360*b+"deg)");d.style.transform=b;d.style.msTransform=b;d.style.MozTransform=b;d.style.webkitTransform=b;d.style.OTransform=b}function a(a,g,e){if(!Value.eq(e,g)){var k=a.style.width.slice(0,-2)-0,f=a.style.height.slice(0,-2)-0;if("object"===typeof e[0]){if("object"===typeof g[0]&&a.getContext){var n=a.getContext("2d");return b(function(){b(this,n,k,f,e)},n,k,f,e)}g=c(k,f,e);g.style.position="absolute";return a.parentNode.replaceChild(g,a)}a.style.width=~~k+"px";a.style.height=
44−~~f+"px";var d=e[4][1];Render.update(a.firstChild,g[4][1],d);h(e[1],e[2],e[3][1],e[3][2],d[3],d[4],a.firstChild)}}function m(b,a,e,c,f){var n=0,d,j=(b[1]-c[1])/e;b=(b[2]-c[2])/e;0!==a&&(a*=-2*Math.PI,e=j*Math.cos(a)-b*Math.sin(a),b=j*Math.sin(a)+b*Math.cos(a),j=e);if(0===f.length)return!1;d=f[0];for(e=f.length-1;e--;){a=f[e];c=d[1];d=d[2];var h=a[1],m=a[2];if(d<m)var r=d,q=m;else r=m,q=d;if(c<h)var u=c,w=h;else u=h,w=c;r<b&&b<=q&&j<=w&&(j<=u||j<=(b-d)*(h-c)/(m-d)+c)&&++n;d=a}return 1===n%2}var j=
45−Elm.JavaScript;return{collage:function(b,a,e){if(0===e.length)return c(b,a,[]);for(var k=Array(e.length),d=e.length;d--;){var f=e[d];if("string"===typeof f[0]){var j=k,m=d,v=b,t=a,r=f[1],q=f[2],u=f[3][1],w=f[3][2],z=f[4][1],f=Render.render(z);h(r,q,u,w,z[3],z[4],f);r=Render.newElement("div");Render.addTo(r,f);r.style.width=~~v+"px";r.style.height=~~t+"px";r.style.overflow="hidden";j[m]=r}else k[d]=c(b,a,f)}return 1===e.length?k[0]:Render.flowWith(Render.goIn,function(b){return b},k)},updateCollage:function(b,
46−c,e){if(1===e.length)return a(b,c[0],e[0]);b=b.childNodes;for(var k=b.length,f=k;f--;)a(b[k-f-1],c[f],e[f])},insideForm:function(b){return function(a){var e=b[1],c=b[2];if(6>a.length){var f=a[3][1],d=a[3][2],j=0,h=a[2];switch(a[4][0]){case "FShape":for(var v=a[4][3][1],t=v.length;--t;)var r=v[t],j=Math.max(j,r[1]*r[1]+r[2]*r[2]);j*=h*h;break;case "FImage":v=h*a[4][1]/2;h=h*a[4][2]/2;j=v*v+h*h;break;case "FElement":v=h*a[4][1][3]/2,h=h*a[4][1][4]/2,j=v*v+h*h}a.push(function(b,a){var e=b-f,c=a-d;return e*
47−e+c*c<j+1})}if(!a[5](e,c))return!1;var q,u;switch(a[4][0]){case "FShape":return m(b,a[1],a[2],a[3],a[4][3][1]);case "FLine":return!1;case "FImage":q=a[4][1]/2;u=a[4][2]/2;break;case "FElement":q=a[4][1][3]/2,u=a[4][1][4]/2}return m(b,a[1],a[2],a[3],[[null,q,u],[null,-q,u],[null,-q,-u],[null,q,-u],[null,q,u]])}}}}();
48−Elm.Graphics=function(){function d(b){return function(a){return["Position",b,a]}}function f(b){return function(a){return["EText",b,a]}}function b(b){return function(a){return["EFlow",b,s.castListToJSArray(a)]}}function c(b){return["Line",s.castListToJSArray(b)]}function h(b){return function(a){var e=s.castListToJSArray(b);0<e.length&&e.push(e[0]);return["Shape",e,a]}}function a(b){return function(a){return function(e){return function(c){return["Form",b,a,e,c]}}}}function m(b){return function(a){return function(e){return["FLine",
49−b,a,e]}}}function j(b){return function(a){return function(e){return["FShape",b,a,e]}}}function l(b,a,e,c,g,k){return["Element",Guid.guid(),b,a,e,c,g,k]}function g(b,a,e){return["Element",Guid.guid(),b,a,e,1,["Nothing"],["Nothing"]]}function e(b){return~~b[3]}function k(b){return~~b[4]}function x(b){return function(a){return function(e){return g(["EImage",s.castStringToJSString(e)],b,a)}}}function n(b){return function(a){return g(z,b,a)}}function p(b){return function(a){return function(e){var c=map(function(e){return["Tuple2",
50−b/2*Math.cos(2*(Math.PI/50)*e),a/2*Math.sin(2*(Math.PI/50)*e)]}),g=49,k=["Nil"];if(0<=g){do k=["Cons",g,k];while(0<g--)}return h(c(k))(e)}}}for(this.i in Elm.List)eval("var "+this.i+" = Elm.List[this.i];");var s=Elm.JavaScript,v=["DRight"],t=["DDown"],r=["DOut"],q=["Near"],u=["Mid"],w=["Far"],z=["EEmpty"],y=["Solid"],D=["Dotted"],F=["Dashed"],B=["Filled"],E=["Outlined"],A=d(q)(q),C=d(w)(q),G=d(q)(w),H=d(w)(w),I=d(q)(u),J=d(w)(u),q=d(u)(q),w=d(u)(w),u=d(u)(u);return{left:["DLeft"],right:v,down:t,up:["DUp"],
51−inward:["DIn"],outward:r,topLeft:A,topRight:C,bottomLeft:G,bottomRight:H,midLeft:I,midRight:J,midTop:q,midBottom:w,middle:u,middleAt:function(b){return function(a){return["PositionAt",b,a]}},topLeftAt:function(b){return function(a){return["PositionTL",b,a]}},topRightAt:function(b){return function(a){return["PositionTR",b,a]}},bottomLeftAt:function(b){return function(a){return["PositionBL",b,a]}},bottomRightAt:function(b){return function(a){return["PositionBR",b,a]}},absolute:function(b){return["Absolute",
52−b]},relative:function(b){return["Relative",b]},width:function(b){return function(a){var e=a[2];switch(e[0]){case "EImage":case "EVideo":return l(a[2],b,a[4]*b/a[3],a[5],a[6],a[7]);case "EText":return e=Value.getTextSize(b,a[4],e[2]),l(a[2],b,e[1],a[5],a[6],a[7])}return l(a[2],b,a[4],a[5],a[6],a[7])}},height:function(a){return function(b){switch(b[2][0]){case "EImage":case "EVideo":return l(b[2],b[3]*a/b[4],a,b[5],b[6],b[7])}return l(b[2],b[3],a,b[5],b[6],b[7])}},size:function(b){return function(a){return function(e){return l(e[2],
53−b,a,e[5],e[6],e[7])}}},opacity:function(b){return function(a){return l(a[2],a[3],a[4],b,a[6],a[7])}},color:function(b){return function(a){return l(a[2],a[3],a[4],a[5],["Just",b],a[7])}},link:function(b){return function(a){return l(a[2],a[3],a[4],a[5],a[6],["Just",s.castStringToJSString(b)])}},widthOf:e,heightOf:k,sizeOf:function(a){return["Tuple2",~~a[3],~~a[4]]},text:function(a){var b=Value.getTextSize(0,0,a);return g(f("left")(a),b[0],b[1])},asText:function(a){a=Elm.Text.monospace(Value.toText(Value.show(a)));
54−var b=Value.getTextSize(0,0,a);return g(f("left")(a),b[0],b[1])},plainText:function(a){a=Value.toText(a);var b=Value.getTextSize(0,0,a);return g(f("left")(a),b[0],b[1])},centeredText:function(a){var b=Value.getTextSize(0,0,a);return g(f("center")(a),b[0],b[1])},justifiedText:function(a){var b=Value.getTextSize(0,0,a);return g(f("justify")(a),b[0],b[1])},rightedText:function(a){var b=Value.getTextSize(0,0,a);return g(f("right")(a),b[0],b[1])},image:x,images:function(a){var b=Elm.Signal.constant(n(0)(0));
55−a=Elm.Signal.lift(function(a){a=s.castStringToJSString(a);var e=new Image;e.onload=function(){Dispatcher.notify(b.id,x(this.width)(this.height)(a))};e.src=a})(a);return Elm.Signal.lift2(function(a){return function(){return a}})(b)(a)},video:function(a){return function(b){return function(e){return g(["EVideo",s.castStringToJSString(e)],a,b)}}},fittedImage:function(a){return function(b){return function(e){return g(["EFittedImage",s.castStringToJSString(e)],a,b)}}},flow:function(a){return function(c){var f;
56−f=map(e)(c);a:{switch(a[0]){case "DLeft":f=sum(f);break a;case "DRight":f=sum(f);break a}f=maximum(f)}var d;d=map(k)(c);a:{switch(a[0]){case "DDown":d=sum(d);break a;case "DUp":d=sum(d);break a}d=maximum(d)}return g(b(a)(c),f,d)}},above:function(a){return function(e){return g(b(t)(["Cons",a,["Cons",e,["Nil"]]]),Math.max(~~a[3],~~e[3]),~~a[4]+~~e[4])}},below:function(a){return function(e){return g(b(t)(["Cons",e,["Cons",a,["Nil"]]]),Math.max(~~a[3],~~e[3]),~~a[4]+~~e[4])}},beside:function(a){return function(e){return g(b(v)(["Cons",
57−a,["Cons",e,["Nil"]]]),~~a[3]+~~e[3],Math.max(~~a[4],~~e[4]))}},layers:function(a){return g(b(r)(a),maximum(map(e)(a)),maximum(map(k)(a)))},collage:function(a){return function(b){return function(e){return g(["ECollage",a,b,Value.groupForms(e)],a,b)}}},spacer:n,container:function(a){return function(b){return function(e){return function(c){return g(["EContainer",e,c],a,b)}}}},line:c,segment:function(a){return function(b){return c(["Cons",a,["Cons",b,["Nil"]]])}},polygon:h,rect:function(a){return function(b){return function(e){return h(["Cons",
58−["Tuple2",0-a/2,0-b/2],["Cons",["Tuple2",0-a/2,b/2],["Cons",["Tuple2",a/2,b/2],["Cons",["Tuple2",a/2,0-b/2],["Nil"]]]]])(e)}}},oval:p,circle:function(a){return p(2*a)(2*a)},ngon:function(a){return function(b){return function(e){var c=map(function(e){return["Tuple2",b*Math.cos(2*(Math.PI/a)*e),b*Math.sin(2*(Math.PI/a)*e)]}),g=a-1,k=["Nil"];if(0<=g){do k=["Cons",g,k];while(0<g--)}return h(c(k))(e)}}},solid:function(b){return function(e){return a(0)(1)(["Tuple2",0,0])(m(y)(b)(e))}},dotted:function(b){return function(e){return a(0)(1)(["Tuple2",
59−0,0])(m(D)(b)(e))}},dashed:function(b){return function(e){return a(0)(1)(["Tuple2",0,0])(m(F)(b)(e))}},customLine:function(b){return function(e){return function(c){return a(0)(1)(["Tuple2",0,0])(m(["Custom",s.castListToJSArray(b)])(e)(c))}}},filled:function(b){return function(e){return a(0)(1)(e[2])(j(B)(b)(e))}},outlined:function(b){return function(e){return a(0)(1)(e[2])(j(E)(b)(e))}},customOutline:function(b){return function(e){return function(c){return a(0)(1)(c[2])(j(["CustomOutline",s.castListToJSArray(b)])(e)(c))}}},
60−textured:function(b){return function(e){return a(0)(1)(e[2])(j(["Textured",b])(null)(e))}},sprite:function(b){return function(e){return function(c){return function(g){return a(0)(1)(g)(["FImage",e,c,s.castStringToJSString(b)])}}}},toForm:function(b){return function(e){return a(0)(1)(b)(["FElement",e])}},rotate:function(b){return function(e){a:{switch(e[0]){case "Form":var c=e[2],g=e[3],k=e[4];e=a(b+e[1])(c)(g)(k);break a}throw"Non-exhaustive pattern match in case";}return e}},scale:function(b){return function(e){return a(e[1])(b*
61−e[2])(e[3])(e[4])}},move:function(b){return function(e){return function(c){var g;a:{switch(c[0]){case "Form":g=c[1];var k=c[2],f=c[3];c=c[4];switch(f[0]){case "Tuple2":var d=f[1],f=f[2];g=a(g)(k)(["Tuple2",b+d,e+f])(c);break a}}throw"Non-exhaustive pattern match in case";}return g}}},isWithin:Collage.insideForm}}();
62−Elm.Text=function(){function d(a){return Value.toText(a)}var f=function(a){return function(b){return"<"+a+' style="padding:0;margin:0">'+b+"</"+a+">"}},b=function(a,b){return function(c){return"<span style='"+a+":"+b+"'>"+c+"</span>"}},c=function(a){a=Elm.JavaScript.castStringToJSString(a);return b("font-family",a)},h=f("h1"),a=b("font-style","italic"),f=f("b"),m=b("text-decoration","underline"),j=b("text-decoration","overline"),l=b("text-decoration","line-through");return{fromString:d,toText:d,header:h,
63−height:function(a){return b("font-size",a+"em")},italic:a,bold:f,underline:m,overline:j,strikeThrough:l,monospace:c("monospace"),typeface:c,color:function(a){return b("color",Elm.Color.extract(a))},link:function(a){return function(b){return"<a href='"+d(a)+"'>"+b+"</a>"}}}}();
64−var Render=function(){function d(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a}function f(a){return a}function b(a){a.style.styleFloat="left";a.style.cssFloat="left";return a}function c(a){a.style.position="absolute";return a}function h(a,b,c){for(var f=d("div"),j=c.length;j--;){var h=a(b(c[j]));f.appendChild(h)}return f}function a(a){switch(a[0]){case "Absolute":return a[1]+"px";case "Relative":return 100*a[1]+"%"}}function m(b,e){e.style.position="absolute";e.style.margin=
65−"auto";switch(b[0]){case "Position":"Far"!==b[1][0]&&(e.style.left=0);"Near"!==b[1][0]&&(e.style.right=0);"Far"!==b[2][0]&&(e.style.top=0);"Near"!==b[2][0]&&(e.style.bottom=0);break;case "PositionAt":e.style.top=a(b[2]);e.style.left=a(b[1]);var c="translate("+~~(-e.style.width.slice(0,-2)/2)+"px,"+~~(-e.style.height.slice(0,-2)/2)+"px)";e.style.transform=c;e.style.msTransform=c;e.style.MozTransform=c;e.style.webkitTransform=c;e.style.OTransform=c;break;default:c=b[0].slice(-2),e.style["T"===c[0]?
66−"top":"bottom"]=a(b[2]),e.style["L"===c[1]?"left":"right"]=a(b[1])}}function j(a){var e={};switch(a[2][0]){case "EText":var e=a[2][1],k=a[2][2],l=d("div");l.innerHTML=k;l.style.textAlign=e;e=l;break;case "EImage":e=a[2][1];k=d("img");k.src=e;k.name=e;k.style.display="block";e=k;break;case "EVideo":l=a[2][1];e=d("video");e.controls="controls";k=d("source");k.src=l;l=l.split(".");k.type="video/"+l[l.length-1];e.appendChild(k);e.style.display="block";break;case "EFittedImage":var n=a[3],p=a[4],e=a[2][1],
67−k=d("div");k.style.width=n+"px";k.style.height=p+"px";k.style.position="relative";k.style.overflow="hidden";var s=d("img");s.onload=function(){s.style.position="absolute";s.style.margin="auto";var a=n,b=p;n/p>this.width/this.height?b=Math.round(this.height*n/this.width):a=Math.round(this.width*p/this.height);s.style.width=a+"px";s.style.height=b+"px";s.style.left=(n-a)/2+"px";s.style.top=(p-b)/2+"px"};s.src=e;s.name=e;k.appendChild(s);e=k;break;case "EFlow":a:{e=a[2][2];switch(a[2][1][0]){case "DDown":e=
68−e.slice(0).reverse();case "DUp":e=h(f,j,e);break a;case "DRight":e=e.slice(0).reverse();case "DLeft":e=h(b,j,e);break a;case "DOut":e=e.slice(0).reverse();case "DIn":e=h(c,j,e);break a}e=void 0}break;case "ECollage":e=Collage.collage(a[2][1],a[2][2],a[2][3]);break;case "EEmpty":e=d("div");break;case "EContainer":k=a[2][1];e=j(a[2][2]);m(k,e);k=d("div");k.style.position="relative";k.style.overflow="hidden";k.appendChild(e);e=k;break;case "EHtml":e=a[2][1];"button"!==e.type&&(k=Value.getExcess(e),a[3]-=
69−k[0],a[4]-=k[1]);break;case "EExternalHtml":e=d("div"),e.appendChild(a[2][1])}e.id=a[1];e.style.width=~~a[3]+"px";e.style.height=~~a[4]+"px";1!==a[5]&&(e.style.opacity=a[5]);"Just"===a[6][0]&&(e.style.backgroundColor=Elm.Color.extract(a[6][1]));return"Just"===a[7][0]?(k=d("a"),k.href=a[7][1],k.appendChild(e),k):e}function l(a,e,k){"A"===a.tagName&&(a=a.firstChild);if(e[1]!==k[1]){if(e[2][0]!==k[2][0])return a.parentNode.replaceChild(j(k),a);var d=k[2],n=e[2];switch(d[0]){case "EText":d[1]!==n[1]&&
70−(a.style.textAlign=d[1]);d[2]!==n[2]&&(a.innerHTML=d[2]);break;case "EImage":d[1]!==n[1]&&(a.src=d[1]);break;case "EVideo":case "EFittedImage":if(!Value.eq(d,n)||k[3]!==e[3]||k[4]!==e[4])return a.parentNode.replaceChild(j(k),a);break;case "ECollage":if(d[1]!==n[1]||d[2]!==n[2]||d[3].length!==n[3].length)return a.parentNode.replaceChild(j(k),a);Collage.updateCollage(a,n[3],d[3]);break;case "EFlow":if(d[1]!==n[1])return a.parentNode.replaceChild(j(k),a);var h=d[2],s=a.childNodes;if(h.length!==s.length)return a.parentNode.replaceChild(j(k),
71−a);var n=n[2],v=function(a){return a};switch(d[1][0]){case "DDown":case "DUp":v=f;break;case "DRight":case "DLeft":v=b;break;case "DOut":case "DIn":v=c}for(d=s.length;d--;)l(s[d],n[d],h[d]),v(s[d]);break;case "EContainer":l(a.childNodes[0],n[2],d[2]);m(d[1],a.childNodes[0]);break;case "EHtml":k[1]!==e[1]&&(h=j(k),a.parentNode.replaceChild(h,a),a=h);"button"!==h.type&&(d=Value.getExcess(a),k[3]-=d[0],k[4]-=d[1]);break;case "EExternalHtml":k[1]!==e[1]&&a.parentNode.replaceChild(j(k),a)}k[3]!==e[3]&&
72−(a.style.width=~~k[3]+"px");k[4]!==e[4]&&(a.style.height=~~k[4]+"px");k[5]!==e[5]&&(a.style.opacity=k[5]);2===k[6].length&&(d=Elm.Color.extract(k[6][1]),d!==a.style.backgroundColor&&(a.style.backgroundColor=d));if(2===k[7].length&&(1===e[7].length||k[7][1]!==e[7][1]))a.parentNode.href=k[7][1];k[1]=e[1]}}return{render:j,update:l,addTo:function(a,b){a.appendChild(b)},newElement:d,flowWith:h,goIn:c}}();
73−Elm.Signal=function(){function d(a){this.id=Guid.guid();this.value=a;this.kids=[];this.defaultNumberOfKids=0;this.recv=function(a,b,e){if(b=b===this.id)this.value=e;l(this,a,b);return b};Dispatcher.inputs.push(this)}function f(a,b){this.id=Guid.guid();this.value=null;this.kids=[];this.count=0;this.changed=!1;b.reverse();this.recalc=function(){for(var c=a,d=b.length;d--;)c=c(b[d].value);this.value=c};this.recalc();this.recv=function(a,e){this.count+=1;e&&(this.changed=!0);this.count==b.length&&(this.changed&&
74−this.recalc(),l(this,a,this.changed),this.changed=!1,this.count=0)};for(var c=b.length;c--;)b[c].kids.push(this)}function b(a,b,c,d){this.id=Guid.guid();this.value=c?b(d.value):b;this.kids=[];this.recv=function(b,c){c&&(this.value=a(d.value)(this.value));l(this,b,c)};d.kids.push(this)}function c(a,b,c){this.id=Guid.guid();this.value=a(c.value)?b:c.value;this.kids=[];this.recv=function(b,d){var f=d&&!a(c.value);f&&(this.value=c.value);l(this,b,f)};c.kids.push(this)}function h(a){this.id=Guid.guid();
75−this.value=a.value;this.kids=[];this.recv=function(b,c){var d=c&&!Value.eq(this.value,a.value);d&&(this.value=a.value);l(this,b,d)};a.kids.push(this)}function a(a,b){this.id=Guid.guid();var c=(new window.Date).getTime();this.value=a?Value.Tuple(c,b.value):c;this.kids=[];this.recv=function(c,d){d&&(this.value=a?Value.Tuple(c,b.value):c);l(this,c,d)};b.kids.push(this)}function m(a,b){this.id=Guid.guid();this.value=b.value;this.kids=[];this.count=0;this.changed=!1;this.recv=function(c,d,f){f===a.id&&
76−(this.changed=d);this.count+=1;2==this.count&&(this.changed&&(this.value=b.value),l(this,c,this.changed),this.count=0,this.changed=!1)};a.kids.push(this);b.kids.push(this)}function j(a,b){this.id=Guid.guid();this.value=a.value;this.kids=[];this.next=null;this.count=0;this.changed=!1;this.recv=function(c,d,f){this.count+=1;d&&(this.changed=!0,f==b.id&&null===this.next&&(this.next=b.value),f==a.id&&(this.next=a.value));2==this.count&&(this.changed&&(this.value=this.next,this.next=null),l(this,c,this.changed),
77−this.changed=!1,this.count=0)};a.kids.push(this);b.kids.push(this)}var l=function(a,b,c){for(var d=a.kids,f=d.length;f--;)d[f].recv(b,c,a.id)},g=function(a){return function(b){return function(d){d=new f(function(a){return function(b){return[a,b]}},[a,d]);d=new c(function(a){return a[0]},[!0,b],d);return new f(function(a){return a[1]},[d])}}};return{constant:function(a){return new d(a)},lift:function(a){return function(b){return new f(a,[b])}},lift2:function(a){return function(b){return function(c){return new f(a,
78−[b,c])}}},lift3:function(a){return function(b){return function(c){return function(d){return new f(a,[b,c,d])}}}},lift4:function(a){return function(b){return function(c){return function(d){return function(j){return new f(a,[b,c,d,j])}}}}},lift5:function(a){return function(b){return function(c){return function(d){return function(j){return function(g){return new f(a,[b,c,d,j,g])}}}}}},lift6:function(a){return function(b){return function(c){return function(d){return function(j){return function(g){return function(h){return new f(a,
79−[b,c,d,j,g,h])}}}}}}},lift7:function(a){return function(b){return function(c){return function(d){return function(j){return function(g){return function(h){return function(l){return new f(a,[b,c,d,j,g,h,l])}}}}}}}},lift8:function(a){return function(b){return function(c){return function(d){return function(j){return function(g){return function(h){return function(l){return function(m){return new f(a,[b,c,d,j,g,h,l,m])}}}}}}}}},foldp:function(a){return function(c){return function(d){return new b(a,c,!1,
80−d)}}},foldp$:function(a){return function(c){return function(d){return new b(a,c,!0,d)}}},foldp1:function(a){return function(c){return new b(a,function(a){return a},!0,c)}},delay:function(a){return function(b){var c=new d(b.value),j=!0;b=new m(c,new f(function(a){return function(){return a}},[c,new f(function(b){j||setTimeout(function(){Dispatcher.notify(c.id,b)},a)},[b])]));j=!1;return b}},merge:function(a){return function(b){return new j(a,b)}},merges:function(a){return Elm.List.foldl1(function(a){return function(b){return new j(a,
81−b)}})(a)},mergeEither:function(a){return function(b){function c(a){return function(b){return[a,b]}}return new j(new f(c("Left"),[a]),new f(c("Right"),[b]))}},average:function(a){return function(b){for(var c=Array(a),d=a;d--;)c[d]=0;var d=0,j=!1,g=0;return new f(function(b){g+=b-c[d];c[d]=b;b=g/Math.max(1,j?a:d);++d==a&&(j=!0,d=0);return b},[b])}},count:function(a){return new b(function(){return function(a){return a+1}},0,!1,a)},countIf:function(a){return function(c){return new b(function(b){return function(c){return a(b)?
82−c+1:c}},0,!1,c)}},keepIf:function(a){return function(b){return function(d){return new c(function(b){return!a(b)},b,d)}}},dropIf:function(a){return function(b){return function(d){return new c(a,b,d)}}},keepWhen:function(a){return g(new f(function(a){return!a},[a]))},dropWhen:g,dropRepeats:function(a){return new h(a)},sampleOn:function(a){return function(b){return new m(a,b)}},timestamp:function(b){return new a(!0,b)},timeOf:function(b){return new a(!1,b)}}}();
83−var Dispatcher=function(){function d(b){if(!b.hasOwnProperty("defaultNumberOfKids"))return!0;var a=b.kids.length;if(0==a)return!1;if(a>b.defaultNumberOfKids)return!0;for(var c=!1;a--;)c=c||d(b.kids[a]);return c}var f=null,b=[],c=null;return{initialize:function(){f=Elm.main();f.hasOwnProperty("recv")||(f=Elm.Signal.constant(f));c=f.value;for(var h=[],a=b.length;a--;)d(b[a])&&h.push(b[a]);b=h;document.getElementById("content").appendChild(Render.render(c));h=document.getElementById("widthChecker").offsetWidth;
84−h!==window.innerWidth&&Dispatcher.notify(Elm.Window.dimensions.id,Value.Tuple(h,window.innerHeight));f=Elm.Signal.lift(function(a){var b=document.getElementById("content");Render.update(b.firstChild,c,a);return c=a})(f)},notify:function(c,a){for(var d=(new window.Date).getTime(),f=!1,l=b.length;l--;)f=b[l].recv(d,c,a)||f;return f},inputs:b}}();
85−Elm.HTTP=function(){function d(b){return function(c){return function(d){return function(e){return{"0":"Request",length:1,verb:a.castStringToJSString(b),url:a.castStringToJSString(c),data:null===d?null:a.castStringToJSString(d),headers:e}}}}}function f(a){return d("GET")(a)(null)(["Nil"])}function b(b,d){return function(f){if(""!==f.url){var e={value:["Waiting"]};b.push(e);var h=null;window.ActiveXObject&&(h=new ActiveXObject("Microsoft.XMLHTTP"));window.XMLHttpRequest&&(h=new XMLHttpRequest);h.onreadystatechange=
86−function(){4===h.readyState&&(e.value=200===h.status?["Success",m(h.responseText)]:["Failure",h.status,m(h.statusText)],setTimeout(function(){c(b,d)},0))};h.open(f.verb,f.url,!0);Elm.List.map(function(b){h.setRequestHeader(a.castStringToJSString(b[1]),a.castStringToJSString(b[2]))})(f.headers);h.send(f.data)}}}function c(a,b){0<a.length&&(Dispatcher.notify(b.id,a[0].value),"Waiting"!==a[0].value[0]&&(a.shift(),setTimeout(function(){c(a,b)},0)))}function h(a){var c=Elm.Signal.constant(["Waiting"]);
87−a=Elm.Signal.lift(b([],c))(a);return Elm.Signal.lift2(function(a){return function(){return a}})(c)(a)}var a=Elm.JavaScript,m=Elm.JavaScript.castJSStringToString;return{get:f,post:function(a){return function(b){return d("POST")(a)(b)(["Nil"])}},request:d,send:h,sendGet:function(a){return h(Elm.Signal.lift(f)(a))}}}();
88−Elm.Input=function(){var d=Elm.JavaScript,f=Elm.JavaScript.castJSStringToString,b=function(a,b){a.placeholder=d.castStringToJSString(b);var c=Elm.Signal.constant(["Nil"]);Value.addListener(a,"keyup",function(){Dispatcher.notify(c.id,f(a.value));a.focus()});a.style.padding="1px";return Value.Tuple(Value.wrap(a),c)},c=function(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a},h=function(a){for(var b=c("select"),d=[];"Cons"===a[0];){var f=c("option"),h=Value.toText(a[1][1]);
89−f.value=h;f.innerHTML=h;b.appendChild(f);d.push(a[1][2]);a=a[2]}var e=Elm.Signal.constant(d[0]);Value.addListener(b,"change",function(){Dispatcher.notify(e.id,d[b.selectedIndex])});return Value.Tuple(Value.wrap(b),e)};return{textArea:function(a){return function(d){var f=c("textarea");f.rows=d;f.cols=a;return b(f,"")}},textField:function(a){var d=c("input");d.type="text";return b(d,a)},password:function(a){var d=c("input");d.type="password";return b(d,a)},checkbox:function(a){var b=c("input");b.type=
90−"checkbox";b.checked=a;var d=Elm.Signal.constant(a);Value.addListener(b,"change",function(){Dispatcher.notify(d.id,b.checked)});return Value.Tuple(Value.wrap(b),d)},dropDown:h,stringDropDown:function(a){return h(Elm.List.map(function(a){return Value.Tuple(a,a)})(a))},button:function(a){var b=c("input");b.type="button";b.value=d.castStringToJSString(a);var f=Elm.Signal.constant(!1);Value.addListener(b,"click",function(){Dispatcher.notify(f.id,!0);Dispatcher.notify(f.id,!1)});return Value.Tuple(Value.wrap(b),
91−f)}}}();
92−Elm.Keyboard={Raw:function(){function d(b,f){return"Nil"===f[0]?f:f[1]===b?f[2]:["Cons",f[1],d(b,f[2])]}var f=Elm.Signal.constant(["Nil"]),b=Elm.Signal.constant(["Nothing"]);Value.addListener(document,"keydown",function(b){var d;a:{for(d=f.value;"Nil"!==d[0];){if(d[1]===b.keyCode){d=!0;break a}d=d[2]}d=!1}d||Dispatcher.notify(f.id,["Cons",b.keyCode,f.value])||this.removeEventListener("keydown",arguments.callee,!1)});Value.addListener(document,"keyup",function(b){var h=d(b.keyCode,f.value);Dispatcher.notify(f.id,
93−h)||this.removeEventListener("keyup",arguments.callee,!1)});Value.addListener(window,"blur",function(b){Dispatcher.notify(f.id,["Nil"])||this.removeEventListener("blur",arguments.callee,!1)});Value.addListener(document,"keypress",function(c){var d=Dispatcher.notify(b.id,["Just",c.charCode||c.keyCode]);Dispatcher.notify(b.id,["Nothing"]);d||this.removeEventListener("keypress",arguments.callee,!1)});return{keysDown:f,charPressed:b}}()};
94−(function(){function d(b){b=Elm.Signal.lift(b)(Elm.Keyboard.Raw.keysDown);Elm.Keyboard.Raw.keysDown.defaultNumberOfKids+=1;b.defaultNumberOfKids=0;return b}function f(b,f,a,m){return d(function(d){for(var l=0,g=0;"Cons"==d[0];){switch(d[1]){case b:--l;break;case f:++l;break;case a:++g;break;case m:--g}d=d[2]}return{_:[!0],x:[l],y:[g]}})}function b(b){return d(function(d){for(;"Cons"==d[0];){if(b==d[1])return!0;d=d[2]}return!1})}Elm.Keyboard.arrows=f(37,39,38,40);Elm.Keyboard.wasd=f(65,68,87,83);Elm.Keyboard.shift=
95−b(16);Elm.Keyboard.ctrl=b(17);Elm.Keyboard.space=b(32)})();
96−Elm.Mouse=function(){function d(a){var b=0,c=0;a||(a=window.event);if(a.pageX||a.pageY)b=a.pageX,c=a.pageY;else if(a.clientX||a.clientY)b=a.clientX+document.body.scrollLeft+document.documentElement.scrollLeft,c=a.clientY+document.body.scrollTop+document.documentElement.scrollTop;return Value.Tuple(b,c)}var f=Elm.Signal.constant(Value.Tuple(0,0));f.defaultNumberOfKids=2;var b=Elm.Signal.lift(function(a){return a[1]})(f);b.defaultNumberOfKids=0;var c=Elm.Signal.lift(function(a){return a[2]})(f);c.defaultNumberOfKids=
97−0;var h=Elm.Signal.constant(!1),a=Elm.Signal.constant(!1),m=Elm.Signal.constant(Value.Tuple());Value.addListener(document,"click",function(b){var c=Dispatcher.notify(a.id,!0),d=Dispatcher.notify(m.id,Value.Tuple());Dispatcher.notify(a.id,!1);!c&&!d&&this.removeEventListener("click",arguments.callee,!1)});Value.addListener(document,"mousedown",function(a){Dispatcher.notify(h.id,!0)||this.removeEventListener("mousedown",arguments.callee,!1)});Value.addListener(document,"mouseup",function(a){Dispatcher.notify(h.id,
98−!1)||this.removeEventListener("mouseup",arguments.callee,!1)});Value.addListener(document,"mousemove",function(a){Dispatcher.notify(f.id,d(a))||this.removeEventListener("mousemove",arguments.callee,!1)});return{position:f,x:b,y:c,isClicked:a,isDown:h,clicks:m,isClickedOn:function(a){a=Render.render(a);var b=Elm.Signal.constant(!1);Value.addListener(a,"click",function(){Dispatcher.notify(b.id,!0);Dispatcher.notify(b.id,!1)});return Value.Tuple(Value.wrap(a),b)}}}();
99−Elm.Random=function(){return{inRange:function(d){return function(f){return Elm.Signal.constant(Math.floor(Math.random()*(f-d+1))+d)}},randomize:function(d){return function(f){return function(b){return Elm.Signal.lift(function(){return Math.floor(Math.random()*(f-d+1))+d})(b)}}}}}();
100−Elm.Time=function(){function d(){return(new window.Date).getTime()}function f(b){return function(c){var f=1E3/b,a=d(),m=a,j=0,l=!0,g=Elm.Signal.constant(j),e=0;return Elm.Signal.lift2(function(b){return function(c){if(b){var n=!l&&b;e=setTimeout(function(){m=d();j=n?0:m-a;a=m;Dispatcher.notify(g.id,j)},f)}else l&&clearTimeout(e);l=b;return c}})(c)(g)}}Elm.Signal.constant(!0);return{fpsWhen:f,fps:function(b){return f(b)(Elm.Signal.constant(!0))},every:function(b){var c=Elm.Signal.constant(d());setInterval(function(){Dispatcher.notify(c.id,
101−d())},b);return c},delay:Elm.Signal.delay,since:function(b){return function(c){var d=Elm.Signal.count(Elm.Signal.delay(b)(c));return Elm.Signal.lift2(function(a){return function(b){return!Value.eq(a,b)}})(Elm.Signal.count(c))(d)}},after:function(b){b*=1E3;var c=Elm.Signal.constant(!1);setTimeout(function(){Dispatcher.notify(c.id,!0)},b);return c},before:function(b){b*=1E3;var c=Elm.Signal.constant(!0);setTimeout(function(){Dispatcher.notify(c.id,!1)},b);return c},hour:36E5,minute:6E4,second:1E3,ms:1,
102−inHours:function(b){return b/36E5},inMinutes:function(b){return b/6E4},inSeconds:function(b){return b/1E3},inMss:function(b){return b},toDate:function(b){return new window.Date(b)},read:function(b){b=window.Date.parse(b);return isNaN(b)?["Nothing"]:["Just",b]}}}();
103−Elm.Window=function(){var d=Elm.Signal.constant(Value.Tuple(window.innerWidth,window.innerHeight));d.defaultNumberOfKids=2;var f=Elm.Signal.lift(function(b){return b[1]})(d);f.defaultNumberOfKids=0;var b=Elm.Signal.lift(function(b){return b[2]})(d);b.defaultNumberOfKids=0;Value.addListener(window,"resize",function(b){var f=document.getElementById("widthChecker").offsetWidth;Dispatcher.notify(d.id,Value.Tuple(f,window.innerHeight))||this.removeEventListener("resize",arguments.callee,!1)});return{dimensions:d,
104−width:f,height:b}}();
105−Elm.Date=function(){var d="Sun Mon Tue Wed Thu Fri Sat".split(" "),f="Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec".split(" ");return{read:function(b){b=new window.Date(Elm.JavaScript.castStringToJSString(b));return isNaN(b.getTime())?["Nothing"]:["Just",b]},year:function(b){return b.getFullYear()},month:function(b){return[f[b.getMonth()]]},day:function(b){return b.getDate()},hour:function(b){return b.getHours()},minute:function(b){return b.getMinutes()},second:function(b){return b.getSeconds()},dayOfWeek:function(b){return[d[b.getDay()]]},
106−toTime:function(b){return b.getTime()},Mon:["Mon"],Tue:["Tue"],Wed:["Wed"],Thu:["Thu"],Fri:["Fri"],Sat:["Sat"],Sun:["Sun"],Jan:["Jan"],Feb:["Feb"],Mar:["Mar"],Apr:["Apr"],May:["May"],Jun:["Jun"],Jul:["Jul"],Aug:["Aug"],Sep:["Sep"],Oct:["Oct"],Nov:["Nov"],Dec:["Dec"]}}();Value.addListener(document,"elm_log",function(d){console.log(d.value)});Value.addListener(document,"elm_title",function(d){document.title=d.value});
107−Value.addListener(document,"elm_redirect",function(d){0<d.value.length&&(window.location=d.value)});Value.addListener(document,"elm_viewport",function(d){var f=document.getElementById("elm_viewport");f||(f=document.createElement("meta"),f.id="elm_viewport",f.name="viewport",document.head.appendChild(f));f.content=d.value;Dispatcher.notify(Elm.Window.dimensions.id,Value.Tuple(window.innerWidth,window.innerHeight))});
108−Elm.Prelude=function(){function d(b){return function(c){if(b instanceof Array&&c instanceof Array){var f=b.length;if(f==c.length){for(var a=1;a<f;++a){var m=d(b[a])(c[a]);if("EQ"!==m[0])return m}return["EQ"]}return[1==c.length?"GT":"LT"]}return[b===c?"EQ":b<c?"LT":"GT"]}}var f=function(b){return function(c){var d=b%c,d=0==b?0:0<c?0<=b?d:d+c:-f(-b)(-c);return d==c?0:d}};return{eq:Value.eq,id:function(b){return b},not:function(b){return!b},xor:function(b){return function(c){return b!=c}},fst:function(b){return b[1]},
109−snd:function(b){return b[2]},rem:function(b){return function(c){return b%c}},div:function(b){return function(c){return~~(b/c)}},otherwise:!0,compare:d,toFloat:function(b){return b},round:function(b){return Math.round(b)},floor:function(b){return Math.floor(b)},ceiling:function(b){return Math.ceil(b)},truncate:function(b){return~~b},readInt:function(b){b=Elm.JavaScript.castStringToJSString(b);var c=b.length;if(0===c)return["Nothing"];var d=0;if("-"==b[0]){if(1===c)return["Nothing"];d=1}for(;d<c;++d)if(!Elm.Char.isDigit(b[d]))return["Nothing"];
110−return["Just",parseInt(b)]},readFloat:function(b){b=Elm.JavaScript.castStringToJSString(b);var c=b.length;if(0===c)return["Nothing"];var d=0;if("-"==b[0]){if(1===c)return["Nothing"];d=1}for(var a=0;d<c;++d)if(!Elm.Char.isDigit(b[d])){if("."===b[d]&&(a+=1,1>=a))continue;return["Nothing"]}return["Just",parseFloat(b)]},sqrt:Math.sqrt,abs:Math.abs,pi:Math.PI,e:Math.E,sin:Math.sin,cos:Math.cos,tan:Math.tan,asin:Math.asin,acos:Math.acos,atan:Math.atan,atan2:function(b){return function(c){return Math.atan2(b,
111−c)}},mod:f,min:function(b){return function(c){return Math.min(b,c)}},max:function(b){return function(c){return Math.max(b,c)}},flip:function(b){return function(c){return function(d){return b(d)(c)}}},clamp:function(b){return function(c){return function(d){return Math.min(c,Math.max(b,d))}}},curry:function(b){return function(c){return function(d){return b(["Tuple2",c,d])}}},uncurry:function(b){return function(c){if("Tuple2"!==c[0])throw"Function was uncurry'd but was not given a pair.";return b(c[1])(c[2])}},
112−logBase:function(b){return function(c){return Math.log(c)/Math.log(b)}},Just:Elm.Maybe.Just,Nothing:Elm.Maybe.Nothing,maybe:Elm.Maybe.maybe,map:Elm.List.map,zip:Elm.List.zip,zipWith:Elm.List.zipWith,filter:Elm.List.filter,head:Elm.List.head,tail:Elm.List.tail,last:Elm.List.last,length:Elm.List.length,reverse:Elm.List.reverse,foldr:Elm.List.foldr,foldr1:Elm.List.foldr1,foldl:Elm.List.foldl,foldl1:Elm.List.foldl1,and:Elm.List.and,or:Elm.List.or,all:Elm.List.all,any:Elm.List.any,sum:Elm.List.sum,product:Elm.List.product,
113−concat:Elm.List.concat,concatMap:Elm.List.concatMap,maximum:Elm.List.maximum,minimum:Elm.List.minimum,scanl:Elm.List.scanl,scanl1:Elm.List.scanl1,take:Elm.List.take,drop:Elm.List.drop,zip:Elm.List.zip,unzip:Elm.List.unzip,lift:Elm.Signal.lift,lift2:Elm.Signal.lift2,lift3:Elm.Signal.lift3,lift4:Elm.Signal.lift4,lift5:Elm.Signal.lift5,lift6:Elm.Signal.lift6,lift7:Elm.Signal.lift7,lift8:Elm.Signal.lift8,foldp:Elm.Signal.foldp,foldp1:Elm.Signal.foldp1,foldp$:Elm.Signal.foldp$,constant:Elm.Signal.constant,
114−merge:Elm.Signal.merge,merges:Elm.Signal.merges,mergeEither:Elm.Signal.mergeEither,count:Elm.Signal.count,countIf:Elm.Signal.countIf,average:Elm.Signal.average,keepIf:Elm.Signal.keepIf,dropIf:Elm.Signal.dropIf,keepWhen:Elm.Signal.keepWhen,dropWhen:Elm.Signal.dropWhen,dropRepeats:Elm.Signal.dropRepeats,sampleOn:Elm.Signal.sampleOn,timestamp:Elm.Signal.timestamp,timeOf:Elm.Signal.timeOf}}();
115−(function(){var d=function(d){for(var b in d)Elm.Prelude[b]=d[b]};d(Elm.Color);d(Elm.Text);d(Elm.Graphics);d(Elm.Time);show=Value.show})();
116−Elm.Touch=function(){function d(b){b=j.remove(b.identifier);Date.now()-b.t<h&&(a=!0,m={_:[!0],x:[b.x],y:[b.y]})}function f(a,b){function d(f){for(var g=f.changedTouches.length;g--;)b(f.changedTouches[g]);for(var h=Array(f.touches.length),g=f.touches.length;g--;){var l=h,m=g,r=f.touches[g],q=j.lookup(r.identifier);l[m]={_:[!0],id:[r.identifier],x:[r.pageX],y:[r.pageY],x0:[q.x],y0:[q.y],t0:[q.t]}}if(!Dispatcher.notify(c.id,h))return document.removeEventListener(a,d);f.preventDefault()}Value.addListener(document,
117−a,d)}function b(a){a=Elm.Signal.lift(a)(c);c.defaultNumberOfKids+=1;a.defaultNumberOfKids=0;return a}var c=Elm.Signal.constant([]),h=500,a=!1,m={_:[!0],x:[0],y:[0]},j=new function(){this.keys=[];this.values=[];this.insert=function(a,b){this.keys.push(a);this.values.push(b)};this.lookup=function(a){a=this.keys.indexOf(a);return 0<=a?this.values[a]:{x:0,y:0,t:0}};this.remove=function(a){a=this.keys.indexOf(a);if(!(0>a)){var b=this.values[a];this.keys.splice(a,1);this.values.splice(a,1);return b}}};
118−f("touchstart",function(a){j.insert(a.identifier,{x:a.pageX,y:a.pageY,t:Date.now()})});f("touchmove",function(){});f("touchend",d);f("touchcancel",d);f("touchleave",d);var l=b(function(a){return Elm.JavaScript.castJSArrayToList(a)}),g=b(function(){return m});g.defaultNumberOfKids=1;g=Elm.Signal.keepIf(function(){var b=a;a=!1;return b})({_:[!0],x:[0],y:[0]})(g);g.defaultNumberOfKids=0;return{touches:l,taps:g}}();
119−Elm.Dict=function(){function d(a){return function(b){return function(c){return function(d){return function(e){return["RBNode",a,b,c,d,e]}}}}}function f(a){a:{switch(a[0]){case "RBEmpty":throw"(min RBEmpty) is not defined";case "RBNode":switch(a[4][0]){case "RBEmpty":a=["Tuple2",a[2],a[3]];break a}a=f(a[4]);break a}throw"Non-exhaustive pattern match in case";}return a}function b(a){return function(c){var d;a:{switch(c[0]){case "RBEmpty":d=w;break a;case "RBNode":d=function(){switch(q(a)(c[2])[0]){case "EQ":return z(c[3]);
120−case "GT":return b(a)(c[5]);case "LT":return b(a)(c[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";}return d}}function c(a){return function(b){return function(d){var e;a:{switch(d[0]){case "RBEmpty":e=a;break a;case "RBNode":e=function(){switch(q(b)(d[2])[0]){case "EQ":return d[3];case "GT":return c(a)(b)(d[5]);case "LT":return c(a)(b)(d[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";
121−}return e}}}function h(a){return function(c){return F(b(a)(c))}}function a(a){a:{switch(a[0]){case "RBNode":switch(a[5][0]){case "RBNode":a=d(a[1])(a[5][2])(a[5][3])(d(B)(a[2])(a[3])(a[4])(a[5][4]))(a[5][5]);break a}}throw"rotateLeft of a node without enough children";}return a}function m(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":a=d(a[1])(a[4][2])(a[4][3])(a[4][4])(d(B)(a[2])(a[3])(a[4][5])(a[5]));break a}}throw"rotateRight of a node without enough children";}return a}function j(a){a:{switch(a[0]){case "Black":a=
122−B;break a;case "Red":a=E;break a}throw"Non-exhaustive pattern match in case";}return a}function l(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[5][0]){case "RBNode":a=d(j(a[1]))(a[2])(a[3])(d(j(a[4][1]))(a[4][2])(a[4][3])(a[4][4])(a[4][5]))(d(j(a[5][1]))(a[5][2])(a[5][3])(a[5][4])(a[5][5]));break a}}}throw"color_flip called on a RBEmpty or RBNode with a RBEmpty child";}return a}function g(b){a:switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":b=
123−a(b);break a}}}a:switch(b[0]){case "RBNode":switch(b[4][0]){case "RBNode":switch(b[4][1][0]){case "Red":switch(b[4][4][0]){case "RBNode":switch(b[4][4][1][0]){case "Red":b=m(b);break a}}}}}a:switch(b[0]){case "RBNode":switch(b[4][0]){case "RBNode":switch(b[4][1][0]){case "Red":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":b=l(b);break a}}}}}return b}function e(a){a:switch(a[0]){case "RBNode":switch(a[1][0]){case "Red":a=d(E)(a[2])(a[3])(a[4])(a[5]);break a}}return a}function k(a){return function(b){return function(c){var f=
124−function(c){var e;a:{switch(c[0]){case "RBEmpty":e=d(B)(a)(b)(A)(A);break a;case "RBNode":e=function(){switch(q(a)(c[2])[0]){case "EQ":return d(c[1])(c[2])(b)(c[4])(c[5]);case "GT":return d(c[1])(c[2])(c[3])(c[4])(f(c[5]));case "LT":return d(c[1])(c[2])(c[3])(f(c[4]))(c[5])}throw"Non-exhaustive pattern match in case";}();e=g(e);break a}throw"Non-exhaustive pattern match in case";}return e};return e(f(c))}}}function x(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":a=
125−!0;break a}}}a=!1}return a}function n(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][4][0]){case "RBNode":switch(a[4][4][1][0]){case "Red":a=!0;break a}}}}a=!1}return a}function p(b){if(y(x(b))&&y(n(b))){b=l(b);a:switch(b[0]){case "RBNode":b:switch(b[5][0]){case "RBNode":switch(b[5][4][0]){case "RBNode":switch(b[5][4][1][0]){case "Red":b=l(a(d(b[1])(b[2])(b[3])(b[4])(m(b[5]))));break b}}}break a}}return b}function s(a){return function(b){var c=function(b){a:{switch(b[0]){case "RBEmpty":b=
126−A;break a;case "RBNode":if("LT"===q(a)(b[2])[0])b:{b=p(b);switch(b[0]){case "RBEmpty":throw"delLT on RBEmpty";case "RBNode":b=g(d(b[1])(b[2])(b[3])(c(b[4]))(b[5]));break b}break}else{var h=x(b)?m(b):b,j;b:{switch(h[0]){case "RBNode":switch(h[5][0]){case "RBEmpty":j=D(a,h[2]);break b}}j=!1}if(j)b=h[4];else{h=y;b:{switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":j=!0;break b}}}j=!1}if(h=h(j)){h=y;b:{switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][4][0]){case "RBNode":switch(b[5][4][1][0]){case "Red":j=
127−!0;break b}}}}j=!1}h=h(j)}h&&(b=l(b),b=n(b)?l(m(b)):b);b:{switch(b[0]){case "RBNode":h=D(a,b[2]);break b}h=!1}if(h)b:{switch(b[0]){case "RBEmpty":throw"delEQ called on a RBEmpty";case "RBNode":j=f(b[5]);c:{switch(j[0]){case "Tuple2":h=j[1];break c}break}c:{switch(j[0]){case "Tuple2":j=j[2];break c}break}var h=d(b[1])(h)(j)(b[4]),k=function(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBEmpty":a=A;break a}}b:{a=p(a);switch(a[0]){case "RBEmpty":a=A;break b;case "RBNode":a=g(d(a[1])(a[2])(a[3])(k(a[4]))(a[5]));
128−break b}throw"Non-exhaustive pattern match in case";}}return a};b=e(k(b[5]));b=g(h(b));break b}break}else b:{switch(b[0]){case "RBEmpty":throw"delGT called on a RBEmpty";case "RBNode":b=g(d(b[1])(b[2])(b[3])(b[4])(c(b[5])));break b}break}}}break a}throw"Non-exhaustive pattern match in case";}return b};return h(a)(b)?e(c(b)):b}}function v(a){return function(b){a:{switch(b[0]){case "RBEmpty":b=A;break a;case "RBNode":b=d(b[1])(b[2])(a(b[3]))(v(a)(b[4]))(v(a)(b[5]));break a}throw"Non-exhaustive pattern match in case";
129−}return b}}function t(a){return function(b){return function(c){a:{switch(c[0]){case "RBEmpty":c=b;break a;case "RBNode":c=t(a)(a(c[2])(c[3])(t(a)(b)(c[4])))(c[5]);break a}throw"Non-exhaustive pattern match in case";}return c}}}function r(a){return function(b){return function(c){a:{switch(c[0]){case "RBEmpty":c=b;break a;case "RBNode":c=r(a)(a(c[2])(c[3])(r(a)(b)(c[5])))(c[4]);break a}throw"Non-exhaustive pattern match in case";}return c}}}var q=Elm.Prelude.compare,u=Elm.Prelude.uncurry,w=Elm.Prelude.Nothing,
130−z=Elm.Prelude.Just,y=Elm.Prelude.not,D=Elm.Prelude.eq,F=Elm.Maybe.isJust,B=["Red"],E=["Black"],A=["RBEmpty"],C=A;return{$op:{},empty:C,lookup:b,findWithDefault:c,member:h,insert:k,singleton:function(a){return function(b){return k(a)(b)(A)}},remove:s,map:v,foldl:t,foldr:r,union:function(a){return function(b){return t(k)(b)(a)}},intersect:function(a){return function(b){return t(function(a){return function(c){return function(d){return h(a)(b)?k(a)(c)(d):d}}})(C)(a)}},diff:function(a){return function(b){return t(function(a){return function(){return function(b){return s(a)(b)}}})(a)(b)}},
131−keys:function(a){return r(function(a){return function(){return function(b){return["Cons",a,b]}}})(["Nil"])(a)},values:function(a){return r(function(){return function(a){return function(b){return["Cons",a,b]}}})(["Nil"])(a)},toList:function(a){return r(function(a){return function(b){return function(c){return["Cons",["Tuple2",a,b],c]}}})(["Nil"])(a)},fromList:function(a){return Elm.List.foldl(u(k))(C)(a)}}}();
132−Elm.Set=function(){var d=Elm.Dict.empty,f=Elm.Dict.remove,b=Elm.Dict.member,c=Elm.Dict.union,h=Elm.Dict.intersect,a=Elm.Dict.diff,m=Elm.Dict.keys,j=Elm.List.foldl(function(a){return function(b){return Elm.Dict.insert(a)(["Tuple0"])(b)}})(d);return{empty:d,singleton:function(a){return Elm.Dict.singleton(a)(["Tuple0"])},insert:function(a){return Elm.Dict.insert(a)(["Tuple0"])},remove:f,member:b,union:c,intersect:h,diff:a,toList:m,fromList:j,foldl:function(a){return Elm.Dict.foldl(function(b){return function(){return function(c){return a(b)(c)}}})},
133−foldr:function(a){return Elm.Dict.foldr(function(b){return function(){return function(c){return a(b)(c)}}})},map:function(a){return function(b){b=m(b);return j(Elm.List.map(a)(b))}}}}();
134−(function(){try{var d={};for(this.i in Elm)eval("var "+this.i+"=Elm[this.i];");if(Elm.Automaton)throw"Module name collision, 'Automaton' is already defined.";Elm.Automaton=function(){function b(a){return["Automaton",a]}function c(a){return b(function(b){var d=unzip(map(function(a){a:{switch(a[0]){case "Automaton":a=a[1](b);break a}throw"Non-exhaustive pattern match in case";}return a})(a)),e;a:{switch(d[0]){case "Tuple2":e=d[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(d[0]){case "Tuple2":d=
135−d[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",e,c(d)]})}function f(a){return b(function(b){return["Tuple2",a(b),f(a)]})}function a(c){return function(d){return b(function(b){b=d(b)(c);return["Tuple2",b,a(b)(d)]})}}function m(a){return function(c){return b(function(b){var d=c(b)(a);a:{switch(d[0]){case "Tuple2":b=d[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(d[0]){case "Tuple2":d=d[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",
136−b,m(d)(c)]})}}function j(a){return function(b){a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":b=["Tuple2",a[1]-b[1],a[2]-b[2]];break b}break}break a}throw"Non-exhaustive pattern match in case";}return b}}function l(a){return function(b){var c;a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":var d=function(a){return["Tuple2",b[2],["Tuple2",a,b[2]]]};c=function(){switch(b[1][0]){case "DragFrom":var c;a[1]?c=["Tuple2",uncurry(move)(j(a[2])(b[1][1]))(b[2]),["Tuple2",["DragFrom",
137−b[1][1]],b[2]]]:(c=uncurry(move)(j(a[2])(b[1][1]))(b[2]),c=["Tuple2",c,["Tuple2",k,c]]);return c;case "Ignore":return d(a[1]?x:k);case "Listen":return d(not(a[1])?k:isWithin(a[2])(b[2])?["DragFrom",a[2]]:x)}throw"Non-exhaustive pattern match in case";}();break b}break}break a}throw"Non-exhaustive pattern match in case";}return c}}try{if(!(Elm.Prelude instanceof Object))throw"module not found";}catch(g){throw"Module 'Prelude' is missing. Compile with --make flag or load missing module in a separate JavaScript file.";
138−}var e={};for(this.i in Elm.Prelude)e[this.i]||eval("var "+this.i+" = Elm.Prelude[this.i];");var k=["Listen"],x=["Ignore"];d[">>>"]=function(a){return function(c){var e;a:{switch(a[0]){case "Automaton":e=a[1];break a}throw"Non-exhaustive pattern match in case";}var f;a:{switch(c[0]){case "Automaton":f=c[1];break a}throw"Non-exhaustive pattern match in case";}return b(function(a){a=e(a);var b;a:{switch(a[0]){case "Tuple2":b=a[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(a[0]){case "Tuple2":a=
139−a[2];break a}throw"Non-exhaustive pattern match in case";}var c=f(b);a:{switch(c[0]){case "Tuple2":b=c[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(c[0]){case "Tuple2":c=c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",b,d[">>>"](a)(c)]})}};d["<<<"]=function(a){return function(b){return d[">>>"](b)(a)}};d["^>>"]=function(a){return function(b){return d[">>>"](f(a))(b)}};d[">>^"]=function(a){return function(b){return d[">>>"](a)(f(b))}};d["^<<"]=function(a){return function(b){return d[">>>"](b)(f(a))}};
140−d["<<^"]=function(a){return function(b){return d[">>>"](f(b))(a)}};e=a(0)(function(){return function(a){return 1+a}});return{$op:{">>>":d[">>>"],"<<<":d["<<<"],"^>>":d["^>>"],">>^":d[">>^"],"^<<":d["^<<"],"<<^":d["<<^"]},run:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=lift(fst)(foldp$(function(a){return function(b){a:{switch(b[0]){case "Tuple2":switch(b[2][0]){case "Automaton":b=b[2][1](a);break a}}throw"Non-exhaustive pattern match in case";}return b}})(a[1])(b));break a}throw"Non-exhaustive pattern match in case";
141−}return b}},step:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=a[1](b);break a}throw"Non-exhaustive pattern match in case";}return b}},combine:c,pure:f,init:a,init$:m,count:e,draggable:function(a){return m(["Tuple2",k,a])(l)}}}();Elm.main=function(){return Elm.Automaton.main}}catch(f){Elm.main=function(){document.body.innerHTML=Elm.Text.monospace('<br/><h2>Your browser may not be supported. Are you using a modern browser?</h2><br/><span style="color:grey">Runtime Error in Automaton module:<br/>'+
142−f+"</span>");throw f;}}})();
elm/elm-runtime-0.7.2.jsdeleted−4522
@@ -1,4522 +0,0 @@
1−
2−Elm = {};
3−
4−var Guid = function() {
5− var counter = 0;
6− var guid = function() { counter += 1; return counter; };
7− return {guid : guid};
8−}();
9−Elm.JavaScript = function() {
10− function castJSBoolToBool(b) { return b; }
11− function castBoolToJSBool(b) { return b; }
12−
13− function castJSNumberToFloat(n) { return n; }
14− function castFloatToJSNumber(n) { return n; }
15−
16− function castJSNumberToInt(n) { return ~~n; }
17− function castIntToJSNumber(n) { return n; }
18−
19− function castJSElementToElement(w) {
20− return function(h) {
21− return function(node) {
22− return ["Element",Guid.guid(),
23− ["EExternalHtml",node],
24− w,h,1,["Nothing"],["Nothing"]];
25− }
26− }
27− }
28− function castElementToJSElement(elem) { return Render.render(elem); }
29−
30− function castJSArrayToList(arr) {
31− var list = ["Nil"];
32− for (var i = arr.length; i--; ) {
33− list = [ "Cons", arr[i], list ];
34− }
35− return list;
36− }
37− function castListToJSArray(list) {
38− var a = [];
39− while (list[0] === "Cons") {
40− a.push(list[1]);
41− list = list[2];
42− }
43− return a;
44− }
45−
46− var castJSStringToString = castJSArrayToList;
47− function castStringToJSString(str) {
48− if (typeof str === "string") return str;
49− return castListToJSArray(str).join('');
50− }
51−
52− function fromTuple(t) { return t.slice(1); }
53− function toTuple(a) { return ["Tuple" + a.length].concat(a); }
54−
55− return {castJSBoolToBool:castJSBoolToBool,
56− castBoolToJSBool:castBoolToJSBool,
57− castJSNumberToFloat:castJSNumberToFloat,
58− castFloatToJSNumber:castFloatToJSNumber,
59− castJSNumberToInt:castJSNumberToInt,
60− castIntToJSNumber:castIntToJSNumber,
61− Experimental : {castJSElementToElement:castJSElementToElement,
62− castElementToJSElement:castElementToJSElement},
63− castJSArrayToList:castJSArrayToList,
64− castListToJSArray:castListToJSArray,
65− castJSStringToString:castJSStringToString,
66− castStringToJSString:castStringToJSString,
67− castTupleToJSTuple2:fromTuple,
68− castTupleToJSTuple3:fromTuple,
69− castTupleToJSTuple4:fromTuple,
70− castTupleToJSTuple5:fromTuple,
71− castJSTupleToTuple2:toTuple,
72− castJSTupleToTuple3:toTuple,
73− castJSTupleToTuple4:toTuple,
74− castJSTupleToTuple5:toTuple
75− };
76−}();
77−
78−var JSjson = window.JSON;
79−Elm.JSON = function() {
80− var JS = Elm.JavaScript;
81− var empty = ['JSON',{}];
82− function singleton(k) { return function(v) {
83− var obj = {};
84− obj[JS.castStringToJSString(k)] = v;
85− return ['JSON', obj ];
86− };
87− }
88− function insert(k) { return function(v) { return function(inObj) {
89− var obj = inObj[1];
90− var outObj = {};
91− for (var i in obj) {
92− outObj[i] = obj[i];
93− }
94− outObj[JS.castStringToJSString(k)] = v;
95− return ['JSON', outObj ];
96− };
97− };
98− }
99−
100− function lookup(key) { return function(obj) {
101− var k = JS.castStringToJSString(key);
102− return (k in obj[1]) ? ["Just", obj[1][k]] : ["Nothing"] ;
103− };
104− }
105− function find(tipe,base) { return function (key) { return function(obj) {
106− var k = JS.castStringToJSString(key);
107− if (k in obj[1]) {
108− var v = obj[1][k];
109− if (v[0] === tipe) { return v[1]; }
110− }
111− return base;
112− };
113− }
114− }
115− function lookupWithDefault(base) { return function(key) { return function(obj) {
116− var k = JS.castStringToJSString(key);
117− return (k in obj[1]) ? obj[1][k] : base ;
118− };
119− };
120− }
121−
122− function remove(k) { return function(inObj) {
123− var obj = inObj[1];
124− var outObj = {};
125− for (var i in obj) {
126− outObj[i] = obj[i];
127− }
128− delete outObj[JS.castStringToJSString(k)];
129− return ['JSON', outObj];
130− };
131− }
132−
133− function JsonString(v) { return [ "JsonString", v ]; }
134− function JsonNumber(v) { return [ "JsonNumber", v ]; }
135− function JsonBool(v) { return [ "JsonBool", v ]; }
136− var JsonNull = [ "JsonNull" ];
137− function JsonArray(v) { return [ "JsonArray", v ]; }
138− function JsonObject(v) { return [ "JsonObject", v ]; }
139−
140− function toList(json) {
141− var obj = json[1];
142− var arr = [];
143− for (var i in obj) {
144− arr.push(Value.Tuple(JS.castJSStringToString(i), obj[i]));
145− }
146− return JS.castJSArrayToList(arr);
147− }
148− function fromList(list) {
149− var arr = JS.castListToJSArray(list);
150− var obj = {};
151− for (var i = arr.length; i--; ) {
152− obj[JS.castStringToJSString(arr[i][1])] = arr[i][2];
153− }
154− return [ "JSON", obj ];
155− }
156−
157− function toPrettyJSString(sep) { return function (obj) {
158− function fromValue(v) {
159− switch (v[0]) {
160− case 'JsonNull' : return null;
161− case 'JsonString' : return JS.castStringToJSString(v[1]);
162− case 'JsonObject' :
163− var o = {};
164− var from = v[1][1];
165− for (var i in from) {
166− o[i] = fromValue(from[i]);
167− }
168− return o;
169− case 'JsonArray' :
170− var a = JS.castListToJSArray(v[1]);
171− for (var i = a.length; i--; ) {
172− a[i] = fromValue(a[i]);
173− }
174− return a;
175− default :
176− return v[1];
177− }
178− }
179− return JSjson.stringify(fromValue([ 'JsonObject', obj ]), null, JS.castStringToJSString(sep));
180− };
181− }
182− function fromJSString(str) {
183− var obj;
184− try {
185− obj = JSjson.parse(str);
186− } catch (e) {
187− return Elm.Maybe.Nothing;
188− }
189− function toValue(v) {
190− switch (typeof v) {
191− case 'string' : return [ "JsonString", JS.castJSStringToString(v) ];
192− case 'number' : return [ "JsonNumber", JS.castJSNumberToFloat(v) ];
193− case 'boolean' : return [ "JsonBool", JS.castJSBoolToBool(v) ];
194− case 'object' :
195− if (v === null) return [ "JsonNull" ];
196− for (var i in v) {
197− v[i] = toValue(v[i]);
198− }
199− if (v instanceof Array) return [ "JsonArray", JS.castJSArrayToList(v) ];
200− return [ "JsonObject", [ "JSON", v ] ];
201− }
202− }
203− for (var i in obj) {
204− obj[i] = toValue(obj[i]);
205− }
206− return Elm.Maybe.Just( ['JSON',obj] );
207− }
208− return {empty : empty,
209− singleton : singleton,
210− insert : insert,
211− lookup : lookup,
212− findNumber : find("JsonNumber",0),
213− findString : find("JsonString",["Nil"]),
214− findObject : find("JsonObject", empty ),
215− findArray : find("JsonArray" ,["Nil"]),
216− findWithDefault : lookupWithDefault,
217− remove : remove,
218− toPrettyJSString : toPrettyJSString,
219− toJSString : toPrettyJSString(''),
220− fromJSString : fromJSString,
221− toPrettyString : function(sep) { return function(v) {
222− return JS.castJSStringToString(toPrettyJSString(sep)(v)); }; },
223− toString : function(v) { return JS.castJSStringToString(toPrettyJSString('')(v)); },
224− fromString : function(v) { return fromJSString(JS.castStringToJSString(v)); },
225− toList : toList,
226− fromList : fromList,
227− JsonString : JsonString,
228− JsonNumber : JsonNumber,
229− JsonBool : JsonBool,
230− JsonNull : JsonNull,
231− JsonArray : JsonArray,
232− JsonObject : JsonObject
233− };
234−}();
235−
236−var Value = function(){
237−
238− var eq = function(x,y) {
239− if (typeof x === "object") {
240− if (x !== null && '_' in x) {
241− for (var i in x) { if (x[i] != y[i]) return false; }
242− for (var i in y) { if (!(i in x)) return false; }
243− return true;
244− }
245− if (x === y) return true;
246− if (x.length !== y.length) return false;
247− for (var i = x.length; i--; ) {
248− if (!eq(x[i],y[i])) return false;
249− }
250− return true;
251− }
252− return x === y;
253− };
254−
255− var Tuple = function() {
256− var len = arguments.length;
257− var arr = new Array(len+1);
258− arr[0] = "Tuple" + arguments.length;
259− for (var i = len; i--; ) {
260− arr[i+1] = arguments[i];
261− }
262− return arr;
263− };
264−
265− var listToArray = function(list) {
266− var arr = [];
267− while (list[0] === "Cons") {
268− arr.push(list[1]);
269− list = list[2];
270− }
271− return arr;
272− };
273−
274− function makeSpaces(s) {
275− if (s.length == 0) { return s; }
276− var arr = s.split('');
277− if (arr[0] == ' ') { arr[0] = "&nbsp;" }
278− for (var i = arr.length; --i; ) {
279− if (arr[i][0] == ' ' && arr[i-1] == ' ') {
280− arr[i-1] = arr[i-1] + arr[i];
281− arr[i] = '';
282− }
283− }
284− for (var i = arr.length; i--; ) {
285− if (arr[i].length > 1 && arr[i][0] == ' ') {
286− var spaces = arr[i].split('');
287− for (var j = spaces.length - 2; j >= 0; j -= 2) {
288− spaces[j] = '&nbsp;';
289− }
290− arr[i] = spaces.join('');
291− }
292− }
293− arr = arr.join('');
294− if (arr[arr.length-1] === " ") {
295− return arr.slice(0,-1) + '&nbsp;';
296− }
297− return arr;
298− }
299−
300− function properEscape(str) {
301− if (str.length == 0) return str;
302− str = str //.replace(/&/g, "&#38;")
303− .replace(/"/g, /*"*/ "&#34;")
304− .replace(/'/g, /*'*/ "&#39;")
305− .replace(/</g, "&#60;")
306− .replace(/>/g, "&#62;")
307− .replace(/\n/g, "<br/>");
308− var arr = str.split('<br/>');
309− for (var i = arr.length; i--; ) {
310− arr[i] = makeSpaces(arr[i]);
311− }
312− return arr.join('<br/>');
313− }
314−
315− var toText = function(elmList) {
316− if (typeof elmList === "string") return properEscape(elmList);
317− var a = [];
318− while (elmList[0] === "Cons") {
319− a.push(elmList[1]);
320− elmList = elmList[2];
321− }
322− return properEscape(a.join(''));
323− };
324−
325− function getTextSize(w,h,txt) {
326− var t = document.createElement('div');
327− t.innerHTML = txt;
328− t.style.textAlign = 'left';
329− if (w > 0) { t.style.width = w + "px"; }
330−
331− t.style.visibility = "hidden";
332− t.style.styleFloat = "left";
333− t.style.cssFloat = "left";
334−
335− document.body.appendChild(t);
336− var cStyle = window.getComputedStyle(t,null);
337− var realW = cStyle.getPropertyValue("width").slice(0,-2) - 0;
338− var realH = cStyle.getPropertyValue("height").slice(0,-2) - 0;
339− document.body.removeChild(t);
340− //delete t;
341− return [Math.ceil(realW),Math.ceil(Math.max(h,realH))];
342− }
343−
344− function getSize(e) {
345− var t = e.cloneNode(true);
346−
347− t.style.visibility = "hidden";
348− t.style.styleFloat = "left";
349− t.style.cssFloat = "left";
350−
351− document.body.appendChild(t);
352− var w = t.offsetWidth;
353− var h = t.offsetHeight;
354− document.body.removeChild(t);
355− //delete t;
356− return [w,h];
357− }
358−
359− function getExcess(e) {
360− var t = e.cloneNode(true);
361−
362− t.style.visibility = "hidden";
363− t.style.styleFloat = "left";
364− t.style.cssFloat = "left";
365−
366− document.body.appendChild(t);
367− var ow = t.offsetWidth;
368− var oh = t.offsetHeight;
369− var cStyle = window.getComputedStyle(t,null);
370− var w = cStyle.getPropertyValue("width").slice(0,-2) - 0;
371− var h = cStyle.getPropertyValue("height").slice(0,-2) - 0;
372− document.body.removeChild(t);
373− //delete t;
374− return [ow-w,oh-h];
375− }
376−
377−
378− function groupForms(forms) {
379− forms = Elm.JavaScript.castListToJSArray(forms);
380− var groups = [];
381− var arr = [];
382− for (var i = forms.length; i--; ) {
383− var f = forms[i];
384− switch(f[4][0]) {
385− case "FElement":
386− if (arr.length > 0) {
387− groups.push(arr);
388− arr = [];
389− }
390− groups.push(f);
391− break;
392− default:
393− arr.push(f);
394− }
395− }
396− if (arr.length > 0) groups.push(arr);
397− return groups;
398− }
399−
400− var toString = function(v) {
401− if (typeof v === "function") {
402− return "<function>";
403− } else if (typeof v === "boolean") {
404− return v ? "True" : "False";
405− } else if (typeof v === "number") {
406− return v+"";
407− } else if (typeof v === "string" && v.length < 2) {
408− return "'"+v+"'";
409− } else if (typeof v === "object" && ('_' in v)) {
410− var output = [];
411− for (var k in v._) {
412− console.log(k,v._[k]);
413− for (var i = v._[k].length; i--; ) {
414− output.push(k + " = " + toString(v._[k][i]));
415− }
416− }
417− for (var k in v) {
418− if (k === '_') continue;
419− output.push(k + " = " + toString(v[k]));
420− }
421− if (output.length === 0) return "{}";
422− return "{ " + output.join(", ") + " }";
423− } else if (v[0]) {
424− if (v[0].substring(0,5) === "Tuple") {
425− var output = new Array(v.length-1);
426− for (var i = v.length; --i; ) { output[i-1] = toString(v[i]); }
427− return "(" + output.join(",") + ")";
428− } else if (v[0] === "Cons") {
429− var start = (typeof v[1] === "string") ? '"' : "[";
430− var end = (typeof v[1] === "string") ? '"' : "]";
431− var div = (typeof v[1] === "string") ? "" : ",";
432− var f = (typeof v[1] === "string") ? function(x){return x} : toString;
433− var output = start + f(v[1]);
434− v = v[2];
435− while (true) {
436− if (v[0] === "Cons") {
437− output += div + f(v[1]);
438− v = v[2];
439− } else {
440− return output + end;
441− }
442− }
443− } else if (v[0] === "Nil") {
444− return "[]";
445− } else if (v[0] === "JSON") {
446− return "(JSON.fromList " + toString(Elm.JSON.toList(v)) + ")";
447− } else if (v[0] === "RBNode" || v[0] === "RBEmpty") {
448− function cons(k){ return function(v) { return function(acc) { return ["Cons",["Tuple2",k,v],acc]; }; }; }
449− var list = Elm.Dict.foldr(cons)(["Nil"])(v);
450− var name = "Dict";
451− if (list[0] === "Cons" && list[1][2][0] === "Tuple0") {
452− name = "Set";
453− list = Elm.List.map(function(x) { return x[1]; })(list);
454− }
455− return "(" + name + ".fromList " + toString(list) + ")";
456− } else {
457− var output = "";
458− for (var i = v.length; --i; ) { output = ' ' + toString(v[i]) + output; }
459− output = v[0] + output;
460− return (v.length > 1) ? "(" + output + ")" : output;
461− }
462− }
463− return v+"";
464− };
465− var show = function(v) { return str(toString(v)); };
466− var append = function(xs,ys) {
467− if (typeof xs === "string" && typeof ys === "string") {
468− return xs.concat(ys);
469− }
470− if (xs[0] === "Nil") {
471− return ys;
472− }
473− var root = ["Cons", xs[1], ["Nil"]];
474− var curr = root;
475− xs = xs[2];
476− while (xs[0]==="Cons") {
477− curr[2] = ["Cons", xs[1], ["Nil"]];
478− xs = xs[2];
479− curr = curr[2];
480− }
481− curr[2] = ys;
482− return root;
483− };
484−
485− var str = function(s) {
486− var out = ["Nil"];
487− for (var i = s.length; i--; ) {
488− out = ["Cons", s[i], out];
489− }
490− return out;
491− };
492−
493− function wrap(elem) {
494− var p = Value.getSize(elem);
495− return ["Element", Guid.guid(), ["EHtml",elem],
496− p[0], p[1], 1, ["Nothing"], ["Nothing"]];
497− }
498− var addListener = function() {
499− if(document.addEventListener) {
500− return function(element, event, handler) {
501− element.addEventListener(event, handler, false);
502− };
503− } else {
504− return function(element, event, handler) {
505− element.attachEvent('on' + event, handler);
506− };
507− }
508− }();
509−
510− return {eq:eq,
511− str:str,
512− show:show,
513− Tuple:Tuple,
514− append:append,
515− listToArray:listToArray,
516− toText : toText,
517− properEscape : properEscape,
518− getTextSize : getTextSize,
519− getSize : getSize,
520− getExcess : getExcess,
521− groupForms : groupForms,
522− wrap : wrap,
523− addListener : addListener
524− };
525−}();Elm.List = function() {
526−
527− var throwError = function(f) {
528− throw new Error("Function '" + f + "' expecting a list!");
529− }
530−
531− function length(xs) {
532− var out = 0;
533− while (xs[0] === "Cons") {
534− out += 1;
535− xs = xs[2];
536− }
537− return out;
538− };
539− var reverse = foldl(function(x_72) {
540− return function(y_73) {
541− return["Cons", x_72, y_73]
542− }
543− })(["Nil"]);
544− var concat = foldr(function(x_74) {
545− return function(y_75) {
546− return Value.append(x_74, y_75)
547− }
548− })(["Nil"]);
549− var and = foldl(function(x_77) {
550− return function(y_78) {
551− return x_77 && y_78
552− }
553− })(true);
554− var or = foldl(function(x_79) {
555− return function(y_80) {
556− return x_79 || y_80
557− }
558− })(false);
559− var sum = foldl(function(x_89) {
560− return function(y_90) {
561− return x_89 + y_90
562− }
563− })(0);
564− var product = foldl(function(x_91) {
565− return function(y_92) {
566− return x_91 * y_92
567− }
568− })(1);
569− var maximum = foldl1(function(x) { return function(y) { return Math.max(x,y) } });
570− var minimum = foldl1(function(x) { return function(y) { return Math.min(x,y) } });
571− function head(v) {
572− if (v[0] !== "Cons") {
573− throw new Error("Error: 'head' only accepts lists of length greater than one.");
574− }
575− return v[1];
576− }
577− function tail(v) {
578− if (v[0] !== "Cons") {
579− throw new Error("Error: 'tail' only accepts lists of length greater than one.");
580− }
581− return v[2];
582− }
583− function last(v) {
584− if (v[0] !== "Cons") {
585− throw new Error("Error: 'last' only accepts lists of length greater than one.");
586− }
587− var out = v[1];
588− while (v[0] === "Cons") {
589− out = v[1];
590− v = v[2];
591− }
592− return out;
593− }
594− function map(f) {
595− return function(xs) {
596− if (xs[0] === "Nil") { return xs; }
597− if (xs[0] !== "Cons") { throwError('map'); }
598− var root = ["Cons", f(xs[1]), ["Nil"]];
599− var curr = root;
600− xs = xs[2];
601− while (xs[0]==="Cons") {
602− curr[2] = ["Cons", f(xs[1]), ["Nil"]];
603− xs = xs[2];
604− curr = curr[2];
605− }
606− return root;
607− }
608− }
609− function foldl(f) {
610− return function(b) {
611− return function(xs) {
612− var acc = b;
613− if (xs[0] === "Nil") { return acc; }
614− if (xs[0] !== "Cons") { throwError('foldl'); }
615− while (xs[0] === "Cons") {
616− acc = f(xs[1])(acc);
617− xs = xs[2];
618− }
619− return acc;
620− }
621− }
622− }
623− function foldr(f) {
624− return function(b) {
625− return function(xs) {
626− var acc = b;
627− if (xs[0] === "Nil") { return acc; }
628− if (xs[0] !== "Cons") { throwError('foldr'); }
629− var arr = [];
630− while (xs[0] === "Cons") {
631− arr.push(xs[1]);
632− xs = xs[2];
633− }
634− for (var i = arr.length; i--; ) {
635− acc = f(arr[i])(acc);
636− }
637− return acc;
638− }
639− }
640− }
641− function foldl1(f_49) {
642− return function(_temp_50) {
643− return function(v) {
644− if("Cons" !== v[0]) {
645− return undefined
646− }else {
647− var x_51 = v[1];
648− var xs_52 = v[2];
649− return foldl(f_49)(x_51)(xs_52)
650− }
651− }(_temp_50)
652− }
653− }
654− function foldr1(f) {
655− return function(xs) {
656− if (xs[0] === "Nil") { throw new Error("'foldr1' requires an non-empty list.") }
657− if (xs[0] !== "Cons") { throwError('foldr1'); }
658− var arr = [];
659− while (xs[0] === "Cons") {
660− arr.push(xs[1]);
661− xs = xs[2];
662− }
663− var acc = arr.pop();
664− for (var i = arr.length; i--; ) {
665− acc = f(arr[i])(acc);
666− }
667− return acc;
668− }
669− }
670− function scanl(f) {
671− return function(b) {
672− return function(xs) {
673− if (xs[0] === "Nil") { return ["Cons",b,["Nil"]]; }
674− if (xs[0] !== "Cons") { throwError('scanl'); }
675− var arr = [b];
676− while (xs[0] === "Cons") {
677− b = f(xs[1])(b);
678− arr.push(b);
679− xs = xs[2];
680− }
681− var out = ["Nil"];
682− for (var i = arr.length; i--; ) {
683− out = ["Cons", arr[i], out];
684− }
685− return out;
686− }
687− }
688− }
689− function scanl1(f) {
690− return function(xs) {
691− if (xs[0] !== "Cons") {
692− throw new Error("Error: 'scanl1' requires a list of at least length 1.");
693− }
694− return scanl(f)(xs[1])(xs[2]);
695− }
696− }
697− function filter(pred) {
698− return function(xs) {
699− if (xs[0] === "Nil") { return xs; }
700− if (xs[0] !== "Cons") { throwError('filter'); }
701− var arr = [];
702− while (xs[0] === "Cons") {
703− if (pred(xs[1])) { arr.push(xs[1]); }
704− xs = xs[2];
705− }
706− var out = ["Nil"];
707− for (var i = arr.length; i--; ) {
708− out = ["Cons", arr[i], out];
709− }
710− return out;
711− }
712− }
713− function concatMap(f_76) {
714− return function(x) {
715− return concat(map(f_76)(x))
716− }
717− }
718− function all(pred) {
719− return foldl(function(x) { return function(acc) {
720− return acc && pred(x);
721− };})(true);
722− }
723− function any(pred) {
724− return foldl(function(x) { return function(acc) {
725− return acc || pred(x);
726− };})(false);
727− }
728− function partition(pred_93) {
729− return function(lst_94) {
730− return function() {
731− var v = lst_94;
732− var c = [function(v) {
733− if("Nil" !== v[0]) {
734− return undefined
735− }else {
736− return["Tuple2", ["Nil"], ["Nil"]]
737− }
738− }, function(v) {
739− if("Cons" !== v[0]) {
740− return undefined
741− }else {
742− var x_95 = v[1];
743− var xs_96 = v[2];
744− return function(v) {
745− if("Tuple2" !== v[0]) {
746− return undefined
747− }else {
748− var as_97 = v[1];
749− var bs_98 = v[2];
750− return pred_93(x_95) ? ["Tuple2", ["Cons", x_95, as_97], bs_98] : ["Tuple2", as_97, ["Cons", x_95, bs_98]]
751− }
752− }(partition(pred_93)(xs_96))
753− }
754− }];
755− for(var i = c.length;i--;) {
756− var r = c[i](v);
757− if(r !== undefined) {
758− return r
759− }
760− }
761− }()
762− }
763− }
764− function zipWith(f) {
765− return function(listA) {
766− return function(listB) {
767− if (listA[0] === "Nil" || listB[0] === "Nil") { return ["Nil"]; }
768− if (listA[0] !== "Cons" || listB[0] !== "Cons") { throwError('zipWith'); }
769− var arr = [];
770− while (listA[0] === "Cons" && listB[0] === "Cons") {
771− arr.push(f(listA[1])(listB[1]));
772− listA = listA[2];
773− listB = listB[2];
774− }
775− var out = ["Nil"];
776− for (var i = arr.length; i--; ) {
777− out = ["Cons", arr[i], out];
778− }
779− return out;
780− }
781− }
782− }
783− function zip(listA) {
784− return function(listB) {
785− if (listA[0] === "Nil" || listB[0] === "Nil") { return ["Nil"]; }
786− if (listA[0] !== "Cons" || listB[0] !== "Cons") { throwError('zip'); }
787− var arr = [];
788− while (listA[0] === "Cons" && listB[0] === "Cons") {
789− arr.push(["Tuple2", listA[1], listB[1]]);
790− listA = listA[2];
791− listB = listB[2];
792− }
793− var out = ["Nil"];
794− for (var i = arr.length; i--; ) {
795− out = ["Cons", arr[i], out];
796− }
797− return out;
798− }
799− }
800− function unzip(pairs_112) {
801− return function() {
802− var v = pairs_112;
803− var c = [function(v) {
804− if("Nil" !== v[0]) {
805− return undefined
806− }else {
807− return["Tuple2", ["Nil"], ["Nil"]]
808− }
809− }, function(v) {
810− if("Cons" !== v[0]) {
811− return undefined
812− }else {
813− var p_113 = v[1];
814− var ps_114 = v[2];
815− return function(v) {
816− if("Tuple2" !== v[0]) {
817− return undefined
818− }else {
819− if("Tuple2" !== v[1][0]) {
820− return undefined
821− }else {
822− var x_115 = v[1][1];
823− var y_116 = v[1][2];
824− if("Tuple2" !== v[2][0]) {
825− return undefined
826− }else {
827− var xs_117 = v[2][1];
828− var ys_118 = v[2][2];
829− return["Tuple2", ["Cons", x_115, xs_117], ["Cons", y_116, ys_118]]
830− }
831− }
832− }
833− }(["Tuple2", p_113, unzip(ps_114)])
834− }
835− }];
836− for(var i = c.length;i--;) {
837− var r = c[i](v);
838− if(r !== undefined) {
839− return r
840− }
841− }
842− }()
843− }
844− function intersperse(sep_119) {
845− return function(xs_120) {
846− return function() {
847− var v = xs_120;
848− var c = [function(v) {
849− if("Nil" !== v[0]) {
850− return undefined
851− }else {
852− return["Nil"]
853− }
854− }, function(v) {
855− if("Cons" !== v[0]) {
856− return undefined
857− }else {
858− var a_124 = v[1];
859− if("Nil" !== v[2][0]) {
860− return undefined
861− }else {
862− return["Cons", a_124, ["Nil"]]
863− }
864− }
865− }, function(v) {
866− if("Cons" !== v[0]) {
867− return undefined
868− }else {
869− var a_121 = v[1];
870− if("Cons" !== v[2][0]) {
871− return undefined
872− }else {
873− var b_122 = v[2][1];
874− var cs_123 = v[2][2];
875− return["Cons", a_121, ["Cons", sep_119, intersperse(sep_119)(["Cons", b_122, cs_123])]]
876− }
877− }
878− }];
879− for(var i = c.length;i--;) {
880− var r = c[i](v);
881− if(r !== undefined) {
882− return r
883− }
884− }
885− }()
886− }
887− }
888− function intercalate(sep_125) {
889− return function(xs_126) {
890− return function() {
891− var v = xs_126;
892− var c = [function(v) {
893− if("Nil" !== v[0]) {
894− return undefined
895− }else {
896− return["Nil"]
897− }
898− }, function(v) {
899− if("Cons" !== v[0]) {
900− return undefined
901− }else {
902− var a_130 = v[1];
903− if("Nil" !== v[2][0]) {
904− return undefined
905− }else {
906− return a_130
907− }
908− }
909− }, function(v) {
910− if("Cons" !== v[0]) {
911− return undefined
912− }else {
913− var a_127 = v[1];
914− if("Cons" !== v[2][0]) {
915− return undefined
916− }else {
917− var b_128 = v[2][1];
918− var cs_129 = v[2][2];
919− return Value.append(a_127, Value.append(sep_125, intercalate(sep_125)(["Cons", b_128, cs_129])))
920− }
921− }
922− }];
923− for(var i = c.length;i--;) {
924− var r = c[i](v);
925− if(r !== undefined) {
926− return r
927− }
928− }
929− }()
930− }
931− }
932− function sort(xs) {
933− if (xs[0] === "Nil") { return xs; }
934− if (xs[0] !== "Cons") { throwError('sort'); }
935− var arr = [];
936− while (xs[0] === "Cons") {
937− arr.push(xs[1]);
938− xs = xs[2];
939− }
940− arr.sort(function(a,b) { return a - b});
941− var out = ["Nil"];
942− for (var i = arr.length; i--; ) {
943− out = [ "Cons", arr[i], out ];
944− }
945− return out;
946− }
947− function take(n) { return function(xs) {
948− if (n <= 0) { return ["Nil"]; }
949− if (xs[0] === "Nil") { return xs; }
950− if (xs[0] !== "Cons") { throwError('take'); }
951− var out = [ "Cons", xs[1], ["Nil"] ];
952− var temp = out;
953− xs = xs[2];
954− --n;
955− while (xs[0] === "Cons" && n > 0) {
956− temp[2] = [ "Cons", xs[1], ["Nil"] ];
957− temp = temp[2];
958− xs = xs[2];
959− --n;
960− }
961− return out;
962− };
963− }
964− function drop(n) { return function(xs) {
965− if (xs[0] === "Nil") { return xs; }
966− if (xs[0] !== "Cons") { throwError('drop'); }
967− while (xs[0] === "Cons" && n > 0) {
968− xs = xs[2];
969− --n;
970− }
971− return xs;
972− };
973− }
974− return {head:head,
975− tail:tail,
976− last:last,
977− map:map,
978− foldl:foldl,
979− foldr:foldr,
980− foldl1:foldl1,
981− foldr1:foldr1,
982− scanl:scanl,
983− scanl1:scanl1,
984− filter:filter,
985− length:length,
986− reverse:reverse,
987− concat:concat,
988− concatMap:concatMap,
989− and:and,
990− or:or,
991− all:all,
992− any:any,
993− sum:sum,
994− product:product,
995− maximum:maximum,
996− minimum:minimum,
997− partition:partition,
998− zipWith:zipWith,
999− zip:zip,
1000− unzip:unzip,
1001− intersperse:intersperse,
1002− intercalate:intercalate,
1003− sort:sort,
1004− take:take,
1005− drop:drop};
1006−}();/*! Maybe
1007−!*/
1008−
1009−/*[Definition]*/
1010−
1011−/** data Maybe a = Just a | Nothing
1012− The Maybe datatype. Useful when a computation may or may not
1013− result in a value (e.g. logarithm is defined only for positive numbers).
1014−**/
1015−
1016−/*[Basic Utilities]*/
1017−
1018−/** maybe : b -> (a -> b) -> Maybe a -> b
1019− Apply a function to the contents of a `Maybe`.
1020− Return default when given `Nothing`.
1021−**/
1022−/** isJust : Maybe a -> Bool
1023− Check if constructed with `Just`.
1024−**/
1025−/** isNothing : Maybe a -> Bool
1026− Check if constructed with `Nothing`.
1027−**/
1028−
1029−/*[Maybe with Lists]*/
1030−
1031−/** cons : Maybe a -> [a] -> [a]
1032− If `Just`, adds the value to the front of the list.
1033− If `Nothing`, list is unchanged.
1034−**/
1035−/** justs : [Maybe a] -> [a]
1036− Filters out Nothings and extracts the remaining values.
1037−**/
1038−
1039−Elm.Maybe = function() {
1040− function consMaybe(x) { return function(xs) {
1041− if (x[0] === "Just") return ["Cons", x[1], xs];
1042− return xs;
1043− };
1044− }
1045− function mapCons(f) { return function(y) { return function(xs) {
1046− var x = f(y);
1047− if (x[0] === "Just") return ["Cons", x[1], xs];
1048− return xs;
1049− };
1050− };
1051− }
1052− function maybe(b) { return function(f) { return function(m) {
1053− if (m[0] === "Just") return f(m[1]);
1054− return b;
1055− };
1056− };
1057− }
1058−
1059− return {Just : function(x) { return ["Just",x]; },
1060− Nothing : ["Nothing"],
1061− justs : Elm.List.foldr(consMaybe)(["Nil"]),
1062− isJust : function(m) { return m[0] === "Just"; },
1063− isNothing : function(m) { return m[0] === "Nothing"; },
1064− cons : consMaybe,
1065− maybe : maybe
1066− };
1067−}();
1068−/*! Either
1069−!*/
1070−
1071−
1072−Elm.Either = function() {
1073− /*[Definition]*/
1074−
1075− /** data Either a b = Left a | Right b
1076− Represents any data that can take two different types.
1077−
1078− This can also be used for error handling (`Either String a`) where
1079− error messages are stored on the left, and the correct values
1080− ("right" values) are stored on the right.
1081− **/
1082− function Left(a1) { return ['Left',a1]; }
1083− function Right(a1){ return ['Right',a1]; }
1084−
1085− /*[Basics]*/
1086−
1087− /** either : (a -> c) -> (b -> c) -> Either a b -> c
1088− Apply the first function to a `Left` and the second function to a `Right`.
1089− This allows the extraction of a value from an `Either`.
1090− **/
1091− function either(f){ return function(g){ return function(e){
1092− switch(e[0]){
1093− case 'Left': return f(e[1]);
1094− case 'Right': return g(e[1]);
1095− }
1096− };};}
1097−
1098− /** isLeft : Either a b -> Bool
1099− True if the value is a `Left`.
1100− **/
1101− function isLeft(e) { return e[0] == 'Left'; }
1102−
1103− /** isRight : Either a b -> Bool
1104− True if the value is a `Right`.
1105− **/
1106− function isRight(e) { return e[0] == 'Right'; }
1107−
1108− /*[With Lists]*/
1109−
1110− function get(es) { return Elm.List.map(function(x){return x[1];})(es); }
1111−
1112− /** lefts : [Either a b] -> [a]
1113− Keep only the values held in `Left` values.
1114− **/
1115− function lefts(es) { return get(Elm.List.filter(isLeft)(es)); }
1116−
1117− /** rights : [Either a b] -> [a]
1118− Keep only the values held in `Right` values.
1119− **/
1120− function rights(es) { return get(Elm.List.filter(isRight)(es)); }
1121−
1122− /** partition : [Either a b] -> ([a],[b])
1123− Split into two lists, lefts on the left and rights on the right.
1124− So we have the equivalence:
1125−
1126− partition es == (lefts es, rights es)
1127− **/
1128− function partition(es) {
1129− var lrs = Elm.List.partition(isLeft)(es);
1130− lrs[1] = get(lrs[1]);
1131− lrs[2] = get(lrs[2]);
1132− return lrs;
1133− }
1134− return {Left:Left,
1135− Right:Right,
1136− either:either,
1137− isLeft:isLeft,
1138− isRight:isRight,
1139− lefts:lefts,
1140− rights:rights,
1141− partition:partition};
1142−}();
1143−/*! Char !*/
1144−
1145−/*[Classification]*/
1146−
1147−/** isUpper : Char -> Bool
1148− Selects upper case letters.
1149−**/
1150−/** isLower : Char -> Bool
1151− Selects lower case letters.
1152−**/
1153−/** isDigit : Char -> Bool
1154− Selects ASCII digits (0..9).
1155−**/
1156−/** isOctDigit : Char -> Bool
1157− Selects ASCII octal digits (0..7).
1158−**/
1159−/** isHexDigit : Char -> Bool
1160− Selects ASCII hexadecimal digits (0..9a..fA..F).
1161−**/
1162−
1163−/*[Conversion]*/
1164−
1165−/** toUpper : Char -> Char
1166− Convert to upper case.
1167−**/
1168−/** toLower : Char -> Char
1169− Convert to lower case.
1170−**/
1171−/** toLocaleUpper : Char -> Char
1172− Convert to upper case, according to any locale-specific case mappings.
1173−**/
1174−/** toLocaleLower : Char -> Char
1175− Convert to lower case, according to any locale-specific case mappings.
1176−**/
1177−/** toCode : Char -> Int
1178− Convert to unicode.
1179−**/
1180−/** fromCode : Int -> Char
1181− Convert from unicode.
1182−**/
1183−
1184−Elm.Char = function() {
1185− function isBetween(lo,hi) { return function(chr) {
1186− var c = chr.charCodeAt(0);
1187− return lo <= c && c <= hi;
1188− };
1189− }
1190− var isDigit = isBetween('0'.charCodeAt(0),'9'.charCodeAt(0));
1191− var chk1 = isBetween('a'.charCodeAt(0),'f'.charCodeAt(0));
1192− var chk2 = isBetween('A'.charCodeAt(0),'F'.charCodeAt(0));
1193−
1194− return {fromCode : function(c) { return String.fromCharCode(c); },
1195− toCode : function(c) { return c.charCodeAt(0); },
1196− toUpper : function(c) { return c.toUpperCase(); },
1197− toLower : function(c) { return c.toLowerCase(); },
1198− toLocaleUpper : function(c) { return c.toLocaleUpperCase(); },
1199− toLocaleLower : function(c) { return c.toLocaleLowerCase(); },
1200− isLower : isBetween('a'.charCodeAt(0),'z'.charCodeAt(0)),
1201− isUpper : isBetween('A'.charCodeAt(0),'Z'.charCodeAt(0)),
1202− isDigit : isDigit,
1203− isOctDigit : isBetween('0'.charCodeAt(0),'7'.charCodeAt(0)),
1204− isHexDigit : function(c) { return isDigit(c) || chk1(c) || chk2(c); }
1205− };
1206−}();
1207−Elm.Color = function() {
1208−
1209−function Color_0(a1) {
1210− return function(a2) {
1211− return function(a3) {
1212− return function(a4) {
1213− return["Color", a1, a2, a3, a4]
1214− }
1215− }
1216− }
1217−}
1218−var rgba_1 = Color_0;
1219−var red_3 = ["Color",255,0,0,1];
1220−var green_4 = ["Color",0,255,0,1];
1221−var blue_5 = ["Color",0,0,255,1];
1222−var yellow_6 = ["Color",255,255,0,1];
1223−var cyan_7 = ["Color",0,255,255,1];
1224−var magenta_8 = ["Color",255,0,255,1];
1225−var black_9 = ["Color",0,0,0,1];
1226−var white_10 = ["Color",255,255,255,1];
1227−var gray_11 = ["Color",128,128,128,1];
1228−var grey_12 = ["Color",128,128,128,1];
1229−function rgb_2(r_13) {
1230− return function(g_14) {
1231− return function(b_15) {
1232− return ["Color",r_13,g_14,b_15,1]
1233− }
1234− }
1235−}
1236−function extract(c) {
1237− if (c[4] === 1) { return 'rgb(' + c[1] + ',' + c[2] + ',' + c[3] + ')'; }
1238− return 'rgba(' + c[1] + ',' + c[2] + ',' + c[3] + ',' + c[4] + ')';
1239−}
1240−function complement(rgb) {
1241− var hsv = toHSV(rgb);
1242− hsv.hue = (hsv.hue + 180) % 360;
1243− return toRGB(hsv);
1244−}
1245−
1246−function hsva(h) { return function(s) { return function(v) { return function(a) {
1247− var clr = toRGB({hue:h, saturation:s, value:v});
1248− clr[4] = a;
1249− return clr;
1250− }; }; };
1251−}
1252−
1253−function hsv(h) { return function(s) { return function(v) {
1254− return toRGB({hue:h, saturation:s, value:v}); }; }; }
1255−
1256−function toHSV(rgb) {
1257− var hsv = {};
1258− var r = rgb[1] / 255.0, g = rgb[2] / 255.0, b = rgb[3] / 255.0;
1259− var M = Math.max(r,g,b);
1260− var m = Math.min(r,g,b);
1261− var c = M - m;
1262−
1263− var h = 0;
1264− if (c === 0) { h = 0; }
1265− else if (M === r) { h = ((g - b) / c) % 6; }
1266− else if (M === g) { h = ((b - r) / c) + 2; }
1267− else if (M === b) { h = ((r - g) / c) + 4; }
1268− h *= 60;
1269−
1270− return { value : M, hue : h, saturation : (M === 0 ? 0 : c / M) };
1271−}
1272−
1273−function between(lo,hi,x) { return lo <= x && x < hi; }
1274−function norm(n) { return Math.round(n*255); }
1275−
1276−function toRGB(hsv) {
1277− var c = hsv.value * hsv.saturation;
1278− var hue = hsv.hue / 60;
1279− var x = c * (1 - Math.abs((hue % 2) - 1));
1280− var r = 0, g = 0, b = 0;
1281− if (between(0,1,hue)) { r = c; g = x; b = 0; }
1282− else if (between(1,2,hue)) { r = x; g = c; b = 0; }
1283− else if (between(2,3,hue)) { r = 0; g = c; b = x; }
1284− else if (between(3,4,hue)) { r = 0; g = x; b = c; }
1285− else if (between(4,5,hue)) { r = x; g = 0; b = c; }
1286− else if (between(5,6,hue)) { r = c; g = 0; b = x; }
1287−
1288− var m = hsv.value - c;
1289− return ["Color", norm(r+m), norm(g+m), norm(b+m), 1 ];
1290−}
1291− return{rgba:rgba_1, rgb:rgb_2, hsva:hsva, hsv:hsv, red:red_3, green:green_4, blue:blue_5, yellow:yellow_6, cyan:cyan_7, magenta:magenta_8, black:black_9, white:white_10, gray:gray_11, grey:grey_12,complement:complement,extract:extract}
1292−}();
1293−var Collage = function() {
1294−
1295−var JS = Elm.JavaScript;
1296−
1297−function tracePoints(ctx,points) {
1298− var i = points.length - 1;
1299− if (i <= 0) return;
1300− ctx.moveTo(points[i][1], points[i][2]);
1301− while (i--) { ctx.lineTo(points[i][1], points[i][2]); }
1302−}
1303−
1304−function solid(ctx,color,points) {
1305− tracePoints(ctx,points);
1306− ctx.strokeStyle = Elm.Color.extract(color);
1307− ctx.stroke();
1308−};
1309−
1310−function filled(ctx,color,points) {
1311− tracePoints(ctx,points);
1312− ctx.fillStyle = Elm.Color.extract(color);
1313− ctx.fill();
1314−}
1315−
1316−function textured(redo,ctx,src,points) {
1317− var img = new Image();
1318− img.src = JS.castStringToJSString(src);
1319− img.onload = redo;
1320−
1321− tracePoints(ctx,points);
1322− ctx.fillStyle = ctx.createPattern(img,'repeat');
1323− ctx.fill();
1324−}
1325−
1326−function customLine(pattern,ctx,color,points) {
1327− if (pattern.length === 0) { pattern = [8,4]; }
1328− customLineHelp(ctx, pattern, points);
1329− ctx.strokeStyle = Elm.Color.extract(color);
1330− ctx.stroke();
1331−};
1332−
1333−var customLineHelp = function(ctx, pattern, points) {
1334− var i = points.length - 1;
1335− if (i <= 0) return;
1336− var x0 = points[i][1], y0 = points[i][2];
1337− var x1=0, y1=0, dx=0, dy=0, remaining=0, nx=0, ny=0;
1338− var pindex = 0, plen = pattern.length;
1339− var draw = true, segmentLength = pattern[0];
1340− ctx.moveTo(x0,y0);
1341− while (i--) {
1342− x1 = points[i][1]; y1 = points[i][2];
1343− dx = x1 - x0; dy = y1 - y0;
1344− remaining = Math.sqrt(dx * dx + dy * dy);
1345− while (segmentLength <= remaining) {
1346− x0 += dx * segmentLength / remaining;
1347− y0 += dy * segmentLength / remaining;
1348− ctx[draw ? 'lineTo' : 'moveTo'](x0, y0);
1349− // update starting position
1350− dx = x1 - x0; dy = y1 - y0;
1351− remaining = Math.sqrt(dx * dx + dy * dy);
1352− // update pattern
1353− draw = !draw;
1354− pindex = (pindex + 1) % plen;
1355− segmentLength = pattern[pindex];
1356− }
1357− if (remaining > 0) {
1358− ctx[draw ? 'lineTo' : 'moveTo'](x1, y1);
1359− segmentLength -= remaining;
1360− }
1361− x0 = x1; y0 = y1;
1362− }
1363−};
1364−
1365−function drawLine(ctx,form) {
1366− var points = form[3][1];
1367− switch(form[1][0]) {
1368− case "Solid" : return solid(ctx,form[2],points);
1369− case "Dotted": return customLine([3,3],ctx,form[2],points);
1370− case "Dashed": return customLine([8,4],ctx,form[2],points);
1371− case "Custom": return customLine(form[1][1],ctx,form[2],points);
1372− }
1373−};
1374−
1375−function drawShape(redo,ctx,shapeStyle,color,points) {
1376− switch(shapeStyle[0]) {
1377− case "Filled": return filled(ctx,color,points);
1378− case "Outlined": return solid(ctx,color,points);
1379− case "Textured": return textured(redo,ctx,shapeStyle[1],points);
1380− case "CustomOutline":
1381− return customLine(shapeStyle[1],ctx,color,points);
1382− }
1383−};
1384−
1385−function drawImage(redo,ctx,w,h,src) {
1386− var img = new Image();
1387− img.onload = redo;
1388− img.src = JS.castStringToJSString(src);
1389− ctx.drawImage(img,-w/2,-h/2,w,h);
1390−}
1391−
1392−function renderForm(redo,ctx,theta,scale,x,y,form) {
1393− ctx.save();
1394− if (x !== 0 || y !== 0) ctx.translate(x,y);
1395− if (theta !== ~~theta) ctx.rotate(2*Math.PI*theta);
1396− if (scale !== 1) ctx.scale(scale,scale);
1397− ctx.beginPath();
1398− switch(form[0]) {
1399− case "FLine": drawLine(ctx,form); break;
1400− case "FShape": drawShape(redo,ctx,form[1],form[2],form[3][1]); break;
1401− case "FImage": drawImage(redo,ctx,form[1],form[2],form[3]); break;
1402− }
1403− ctx.restore();
1404−};
1405−
1406−function renderForms(redo,ctx,w,h,forms) {
1407− ctx.clearRect(0,0,w,h);
1408− for (var i = forms.length; i--; ) {
1409− var f = forms[i];
1410− renderForm(redo,ctx,f[1],f[2],f[3][1],f[3][2],f[4]);
1411− }
1412−}
1413−
1414−function collageForms(w,h,forms) {
1415− var canvas = Render.newElement('canvas');
1416− w = ~~w;
1417− h = ~~h;
1418− canvas.style.width = w + 'px';
1419− canvas.style.height = h + 'px';
1420− canvas.style.display = "block";
1421− canvas.width = w;
1422− canvas.height = h;
1423− if (canvas.getContext) {
1424− var ctx = canvas.getContext('2d');
1425− function redo() { renderForms(this,ctx,w,h,forms); }
1426− renderForms(redo,ctx,w,h,forms);
1427− return canvas;
1428− }
1429− canvas.innerHTML = "Your browser does not support the canvas element.";
1430− return canvas;
1431−};
1432−
1433−function applyTransforms(theta,scale,x,y,w,h,e) {
1434− var t = "translate(" + (x - w / 2) + "px,"+ (y - h / 2) + "px)";
1435− var r = theta === (~~theta) ? "" : "rotate(" + theta*360 + "deg)";
1436− var s = scale === 1 ? "" : "scale(" + scale + "," + scale + ")";
1437− var transforms = t + " " + s + " " + r;
1438− e.style.transform = transforms;
1439− e.style.msTransform = transforms;
1440− e.style.MozTransform = transforms;
1441− e.style.webkitTransform = transforms;
1442− e.style.OTransform = transforms;
1443−}
1444−
1445−function collageElement(w,h,theta,scale,x,y,elem) {
1446− var e = Render.render(elem);
1447− applyTransforms(theta,scale,x,y,elem[3],elem[4],e);
1448− var div = Render.newElement('div');
1449− Render.addTo(div,e);
1450− div.style.width = (~~w) + "px";
1451− div.style.height = (~~h) + "px";
1452− div.style.overflow = "hidden";
1453− return div;
1454−}
1455−
1456−function collage(w,h,formss) {
1457− if (formss.length === 0) { return collageForms(w,h,[]); }
1458− var elems = new Array(formss.length);
1459− for (var i = formss.length; i--; ) {
1460− var f = formss[i];
1461− if (typeof f[0] === "string") {
1462− elems[i] = collageElement(w,h,f[1],f[2],f[3][1],f[3][2],f[4][1]);
1463− } else {
1464− elems[i] = collageForms(w,h,f);
1465− }
1466− }
1467− if (formss.length === 1) { return elems[0]; }
1468− return Render.flowWith(Render.goIn,function(x){return x},elems);
1469−}
1470−
1471−function updateFormSet(node,currSet,nextSet) {
1472− if (Value.eq(nextSet,currSet)) return;
1473− var w = node.style.width.slice(0,-2) - 0;
1474− var h = node.style.height.slice(0,-2) - 0;
1475− if (typeof nextSet[0] === "object") {
1476− if (typeof currSet[0] === "object") {
1477− if (node.getContext) {
1478− var ctx = node.getContext('2d');
1479− function redo() { renderForms(this,ctx,w,h,nextSet); }
1480− return renderForms(redo,ctx,w,h,nextSet);
1481− }
1482− }
1483− var newNode = collageForms(w,h,nextSet);
1484− newNode.style.position = 'absolute';
1485− return node.parentNode.replaceChild(newNode,node);
1486− }
1487− node.style.width = (~~w) + "px";
1488− node.style.height = (~~h) + "px";
1489− var f = nextSet;
1490− var next = nextSet[4][1];
1491− Render.update(node.firstChild, currSet[4][1], next);
1492− applyTransforms(f[1],f[2],f[3][1],f[3][2],next[3],next[4],node.firstChild);
1493−}
1494−
1495−// assumes that the form sets are the same length.
1496−function updateCollage(node,currs,nexts) {
1497− if (nexts.length === 1) {
1498− return updateFormSet(node,currs[0],nexts[0]);
1499− }
1500− var kids = node.childNodes;
1501− var len = kids.length;
1502− for (var i = len; i--; ) {
1503− updateFormSet(kids[len-i-1], currs[i], nexts[i]);
1504− }
1505−}
1506−
1507−function style(clr,n,list) {
1508− return ["Tuple2",
1509− '<span style="font-size:100%;color:' + clr + ';">' + n + '</span>',
1510− list];
1511−}
1512−
1513−function insideForm(point) { return function(form) {
1514− if (!inBoundsOf(point[1],point[2],form)) return false;
1515− var hw, hh;
1516− switch (form[4][0]) {
1517− case "FShape": return insideShape(point,form[1],form[2],form[3],form[4][3][1]);
1518− case "FLine": return false;
1519− case "FImage":
1520− hw = form[4][1] / 2;
1521− hh = form[4][2] / 2;
1522− break;
1523− case "FElement":
1524− hw = form[4][1][3] / 2;
1525− hh = form[4][1][4] / 2;
1526− break;
1527− }
1528− return insideShape(point,form[1],form[2],form[3],
1529− [ [null, hw, hh],
1530− [null,-hw, hh],
1531− [null,-hw,-hh],
1532− [null, hw,-hh],
1533− [null, hw, hh] ]);
1534− };
1535−}
1536−
1537−function inBoundsOf(px,py,form) {
1538− if (form.length < 6) {
1539− var fx = form[3][1], fy = form[3][2];
1540− var radiusSquared = 0;
1541− var scale = form[2];
1542− switch (form[4][0]) {
1543− case "FShape":
1544− var points = form[4][3][1];
1545− for (var i = points.length; --i; ) {
1546− var p = points[i];
1547− radiusSquared = Math.max(radiusSquared, p[1]*p[1] + p[2]*p[2]);
1548− }
1549− radiusSquared *= scale * scale;
1550− break;
1551− case "FLine":
1552− break;
1553− case "FImage":
1554− var x = scale * form[4][1] / 2;
1555− var y = scale * form[4][2] / 2;
1556− radiusSquared = x*x + y*y;
1557− break;
1558− case "FElement":
1559− var x = scale * form[4][1][3] / 2;
1560− var y = scale * form[4][1][4] / 2;
1561− radiusSquared = x*x + y*y;
1562− break;
1563− }
1564− form.push(function(px,py) {
1565− var dx = px - fx;
1566− var dy = py - fy;
1567− return dx*dx + dy*dy < radiusSquared + 1;
1568− });
1569− }
1570− return form[5](px,py);
1571−}
1572−
1573−function insideShape(point,theta,scale,pos,points) {
1574− var counter = 0;
1575− var list = ["Nil"];
1576− var p1,p2;
1577−
1578− var x = (point[1] - pos[1]) / scale;
1579− var y = (point[2] - pos[2]) / scale;
1580− if (theta !== 0) {
1581− var t = -2 * Math.PI * theta;
1582− var nx = x * Math.cos(t) - y * Math.sin(t);
1583− y = x * Math.sin(t) + y * Math.cos(t);
1584− x = nx;
1585− }
1586−
1587− if (points.length === 0) { return false; }
1588− p1 = points[0];
1589− for (var i = points.length - 1; i--; ) {
1590− p2 = points[i];
1591− var p1x = p1[1], p1y = p1[2], p2x = p2[1], p2y = p2[2];
1592−
1593− if (p1y < p2y) {var ymin=p1y, ymax=p2y;} else {var ymin=p2y, ymax=p1y;}
1594− if (p1x < p2x) {var xmin=p1x, xmax=p2x;} else {var xmin=p2x, xmax=p1x;}
1595−
1596− if (ymin < y && y <= ymax && x <= xmax) {
1597− if (x <= xmin || x <= ((y-p1y)*(p2x-p1x)/(p2y-p1y)+p1x)) {
1598− ++counter;
1599− }
1600− }
1601− p1 = p2;
1602− }
1603− return (counter % 2) === 1;
1604−}
1605−
1606−return {collage:collage, updateCollage:updateCollage, insideForm:insideForm};
1607−
1608−}();Elm.Graphics = function() {
1609− for (this['i'] in Elm.List) {
1610− eval('var ' + this['i'] + ' = Elm.List[this.i];');
1611− }
1612− var JS = Elm.JavaScript;
1613− var DLeft_0 = ["DLeft"];
1614− var DRight_1 = ["DRight"];
1615− var DUp_2 = ["DUp"];
1616− var DDown_3 = ["DDown"];
1617− var DIn_4 = ["DIn"];
1618− var DOut_5 = ["DOut"];
1619− function Absolute_12(a1) {
1620− return["Absolute", a1]
1621− }
1622− function Relative_13(a1) {
1623− return["Relative", a1]
1624− }
1625− var Near_14 = ["Near"];
1626− var Mid_15 = ["Mid"];
1627− var Far_16 = ["Far"];
1628− function Position_17(a1) {
1629− return function(a2) {
1630− return["Position", a1, a2]
1631− }
1632− }
1633− function PositionTL_18(a1) {
1634− return function(a2) {
1635− return["PositionTL", a1, a2]
1636− }
1637− }
1638− function PositionTR_19(a1) {
1639− return function(a2) {
1640− return["PositionTR", a1, a2]
1641− }
1642− }
1643− function PositionBL_20(a1) {
1644− return function(a2) {
1645− return["PositionBL", a1, a2]
1646− }
1647− }
1648− function PositionBR_21(a1) {
1649− return function(a2) {
1650− return["PositionBR", a1, a2]
1651− }
1652− }
1653− function Element_37(id,e,w,h,o,c,l) {
1654− return["Element", id, e, w, h, o, c, l ]
1655− }
1656− function EText_39(a1) {
1657− return function(a2) {
1658− return["EText", a1, a2]
1659− }
1660− }
1661− function EImage_40(a1) {
1662− return["EImage", JS.castStringToJSString(a1)]
1663− }
1664− function EVideo_41(a1) {
1665− return["EVideo", JS.castStringToJSString(a1)]
1666− }
1667− function EFittedImage_42(a1) {
1668− return["EFittedImage", JS.castStringToJSString(a1)]
1669− }
1670− function EFlow_43(a1) {
1671− return function(a2) {
1672− return["EFlow", a1, JS.castListToJSArray(a2)]
1673− }
1674− }
1675− function ECollage_44(a1) {
1676− return function(a2) {
1677− return function(a3) {
1678− return["ECollage", a1, a2, Value.groupForms(a3)]
1679− }
1680− }
1681− }
1682− var EEmpty_45 = ["EEmpty"];
1683− function EContainer_46(a1) {
1684− return function(a2) {
1685− return["EContainer", a1, a2]
1686− }
1687− }
1688− var Solid_68 = ["Solid"];
1689− var Dotted_69 = ["Dotted"];
1690− var Dashed_70 = ["Dashed"];
1691− function Custom_71(a1) {
1692− return["Custom", JS.castListToJSArray(a1)]
1693− }
1694− var Filled_72 = ["Filled"];
1695− var Outlined_73 = ["Outlined"];
1696− function CustomOutline_74(a1) {
1697− return["CustomOutline", JS.castListToJSArray(a1)]
1698− }
1699− function Line_75(a1) {
1700− return["Line", JS.castListToJSArray(a1)]
1701− }
1702− function Shape_78(a1) {
1703− return function(a2) {
1704− var points = JS.castListToJSArray(a1);
1705− if (points.length > 0) { points.push(points[0]); }
1706− return["Shape", points, a2];
1707− }
1708− }
1709− function Form_84(a1) {
1710− return function(a2) {
1711− return function(a3) {
1712− return function(a4) {
1713− return["Form", a1, a2, a3, a4]
1714− }
1715− }
1716− }
1717− }
1718− function FLine_85(a1) {
1719− return function(a2) {
1720− return function(a3) {
1721− return["FLine", a1, a2, a3]
1722− }
1723− }
1724− }
1725− function FShape_86(a1) {
1726− return function(a2) {
1727− return function(a3) {
1728− return["FShape", a1, a2, a3]
1729− }
1730− }
1731− }
1732− function FImage_87(a1) {
1733− return function(a2) {
1734− return function(a3) {
1735− return["FImage", a1, a2, JS.castStringToJSString(a3)]
1736− }
1737− }
1738− }
1739− function FElement_88(a1) {
1740− return["FElement", a1]
1741− }
1742− var left_6 = DLeft_0;
1743− var right_7 = DRight_1;
1744− var down_8 = DDown_3;
1745− var up_9 = DUp_2;
1746− var inward_10 = DIn_4;
1747− var outward_11 = DOut_5;
1748− var topLeft_22 = Position_17(Near_14)(Near_14);
1749− var topRight_23 = Position_17(Far_16)(Near_14);
1750− var bottomLeft_24 = Position_17(Near_14)(Far_16);
1751− var bottomRight_25 = Position_17(Far_16)(Far_16);
1752− var midLeft_26 = Position_17(Near_14)(Mid_15);
1753− var midRight_27 = Position_17(Far_16)(Mid_15);
1754− var midTop_28 = Position_17(Mid_15)(Near_14);
1755− var midBottom_29 = Position_17(Mid_15)(Far_16);
1756− var middle_30 = Position_17(Mid_15)(Mid_15);
1757− function middleAt(a1) {
1758− return function(a2) {
1759− return["PositionAt", a1, a2]
1760− }
1761− }
1762− var topLeftAt_31 = PositionTL_18;
1763− var topRightAt_32 = PositionTR_19;
1764− var bottomLeftAt_33 = PositionBL_20;
1765− var bottomRightAt_34 = PositionBR_21;
1766− var absolute_35 = Absolute_12;
1767− var relative_36 = Relative_13;
1768− function newElement_38(e,w,h,o,c,l) { return Element_37(Guid.guid(),e,w,h,o,c,l); }
1769− function basicNewElement(e,w,h) { return Element_37(Guid.guid(),e,w,h,1,["Nothing"],["Nothing"]); }
1770− var line_76 = Line_75;
1771− var polygon_79 = Shape_78;
1772− function sprite_96(src) {
1773− return function(w) {
1774− return function(h) {
1775− return function(pos) {
1776− return Form_84(0)(1)(pos)(FImage_87(w)(h)(src))
1777− }
1778− }
1779− }
1780− }
1781− function toForm_97(pos) {
1782− return function(e) {
1783− return Form_84(0)(1)(pos)(FElement_88(e))
1784− }
1785− }
1786− function width_47(w__101) {
1787− return function(e) {
1788− var be = e[2];
1789− switch(be[0]) {
1790− case "EImage":
1791− case "EVideo":
1792− return newElement_38(e[2],w__101,e[4] * w__101 / e[3], e[5], e[6], e[7]);
1793− case "EText":
1794− var p = Value.getTextSize(w__101,e[4],be[2]);
1795− return newElement_38(e[2], w__101, p[1], e[5], e[6], e[7]);
1796− }
1797− return newElement_38(e[2], w__101, e[4], e[5], e[6], e[7]);
1798− }
1799− }
1800− function height_48(h__108) {
1801− return function(e) {
1802− var be = e[2];
1803− switch(be[0]) {
1804− case "EImage":
1805− case "EVideo":
1806− return newElement_38(e[2], e[3] * h__108 / e[4], h__108, e[5], e[6], e[7]);
1807− }
1808− return newElement_38(e[2], e[3], h__108, e[5], e[6], e[7]);
1809− }
1810− }
1811− function size_49(w) {
1812− return function(h) {
1813− return function(e) {
1814− return newElement_38(e[2], w, h, e[5], e[6], e[7]);
1815− }
1816− }
1817− }
1818− function opacity_50(o) {
1819− return function(e) {
1820− return newElement_38(e[2], e[3], e[4], o, e[6], e[7]);
1821− }
1822− }
1823− function color_51(c) {
1824− return function(e) {
1825− return newElement_38(e[2], e[3], e[4], e[5], ["Just",c], e[7]);
1826− }
1827− }
1828− function link(lnk) {
1829− return function(e) {
1830− return newElement_38(e[2], e[3], e[4], e[5], e[6], ["Just", JS.castStringToJSString(lnk)]);
1831− }
1832− }
1833− function widthOf_52(e) { return ~~e[3]; }
1834− function heightOf_53(e) { return ~~e[4]; }
1835− function sizeOf_54(e) { return["Tuple2", ~~e[3], ~~e[4]] }
1836− function text_56(txt) {
1837− var p = Value.getTextSize(0,0,txt);
1838− return basicNewElement(EText_39("left")(txt), p[0], p[1])
1839− }
1840− function plainText(str) {
1841− var txt = Value.toText(str);
1842− var p = Value.getTextSize(0,0,txt);
1843− return basicNewElement(EText_39("left")(txt),p[0],p[1])
1844− }
1845− function asText(v) {
1846− var txt = Elm.Text.monospace(Value.toText(Value.show(v)));
1847− var p = Value.getTextSize(0,0,txt);
1848− return basicNewElement(EText_39("left")(txt),p[0],p[1])
1849− }
1850− function centeredText(txt) {
1851− var p = Value.getTextSize(0,0,txt);
1852− return basicNewElement(EText_39("center")(txt),p[0],p[1])
1853− }
1854− function justifiedText(txt) {
1855− var p = Value.getTextSize(0,0,txt);
1856− return basicNewElement(EText_39("justify")(txt),p[0],p[1])
1857− }
1858− function rightedText(txt) {
1859− var p = Value.getTextSize(0,0,txt);
1860− return basicNewElement(EText_39("right")(txt),p[0],p[1])
1861− }
1862− function image_57(w) {
1863− return function(h) {
1864− return function(src) {
1865− return basicNewElement(EImage_40(src),w,h)
1866− }
1867− }
1868− }
1869− function images(srcs) {
1870− var pics = Elm.Signal.constant(spacer_66(0)(0));
1871− var update = Elm.Signal.lift(function(src) {
1872− src = JS.castStringToJSString(src);
1873− var img = new Image();
1874− img.onload = function() {
1875− Dispatcher.notify(pics.id,
1876− image_57(this.width)(this.height)(src));
1877− };
1878− img.src = src;
1879− })(srcs);
1880− function f(x) { return function(y) { return x; } }
1881− var combine = Elm.Signal.lift2(f)(pics)(update);
1882− return combine;
1883− }
1884− function video_58(w) {
1885− return function(h) {
1886− return function(src) {
1887− return basicNewElement(EVideo_41(src),w,h)
1888− }
1889− }
1890− }
1891− function fittedImage_59(w_147) {
1892− return function(h_148) {
1893− return function(s_149) {
1894− return basicNewElement(EFittedImage_42(s_149),w_147,h_148)
1895− }
1896− }
1897− }
1898− function flow_60(dir_150) {
1899− return function(es_151) {
1900− return function() {
1901− var w_152 = function() {
1902− var ws_154 = map(widthOf_52)(es_151);
1903− return function(case1) {
1904− var case0 = case1;
1905− switch(case0[0]) {
1906− case "DLeft":
1907− return sum(ws_154);
1908− case "DRight":
1909− return sum(ws_154)
1910− }
1911− return maximum(ws_154)
1912− }(dir_150)
1913− }();
1914− var h_153 = function() {
1915− var hs_155 = map(heightOf_53)(es_151);
1916− return function(case3) {
1917− var case2 = case3;
1918− switch(case2[0]) {
1919− case "DDown":
1920− return sum(hs_155);
1921− case "DUp":
1922− return sum(hs_155)
1923− }
1924− return maximum(hs_155)
1925− }(dir_150)
1926− }();
1927− return basicNewElement(EFlow_43(dir_150)(es_151), w_152, h_153)
1928− }()
1929− }
1930− }
1931− function above_61(e1_156) {
1932− return function(e2_157) {
1933− return basicNewElement(EFlow_43(DDown_3)(["Cons", e1_156, ["Cons", e2_157, ["Nil"]]]), Math.max(widthOf_52(e1_156),widthOf_52(e2_157)), heightOf_53(e1_156) + heightOf_53(e2_157));
1934− }
1935− }
1936− function below_62(e1_158) {
1937− return function(e2_159) {
1938− return basicNewElement(EFlow_43(DDown_3)(["Cons", e2_159, ["Cons", e1_158, ["Nil"]]]), Math.max(widthOf_52(e1_158),widthOf_52(e2_159)), heightOf_53(e1_158) + heightOf_53(e2_159));
1939− }
1940− }
1941− function beside_63(e1_160) {
1942− return function(e2_161) {
1943− return basicNewElement(EFlow_43(DRight_1)(["Cons", e1_160, ["Cons", e2_161, ["Nil"]]]), widthOf_52(e1_160) + widthOf_52(e2_161), Math.max(heightOf_53(e1_160),heightOf_53(e2_161)));
1944− }
1945− }
1946− function layers_64(es_162) {
1947− return basicNewElement(EFlow_43(DOut_5)(es_162), maximum(map(widthOf_52)(es_162)), maximum(map(heightOf_53)(es_162)))
1948− }
1949− function collage_65(w_163) {
1950− return function(h_164) {
1951− return function(forms_165) {
1952− return basicNewElement(ECollage_44(w_163)(h_164)(forms_165),w_163,h_164)
1953− }
1954− }
1955− }
1956− function spacer_66(w_166) {
1957− return function(h_167) {
1958− return basicNewElement(EEmpty_45,w_166,h_167)
1959− }
1960− }
1961− function container_67(w_169) {
1962− return function(h_170) {
1963− return function(pos_168) {
1964− return function(e_171) {
1965− return basicNewElement(EContainer_46(pos_168)(e_171),w_169,h_170)
1966− }
1967− }
1968− }
1969− }
1970− function segment_77(p1_172) {
1971− return function(p2_173) {
1972− return Line_75(["Cons", p1_172, ["Cons", p2_173, ["Nil"]]])
1973− }
1974− }
1975− function rect_80(w_174) {
1976− return function(h_175) {
1977− return function(pos_176) {
1978− return Shape_78(["Cons", ["Tuple2", 0 - w_174 / 2, 0 - h_175 / 2],
1979− ["Cons", ["Tuple2", 0 - w_174 / 2, h_175 / 2],
1980− ["Cons", ["Tuple2", w_174 / 2, h_175 / 2],
1981− ["Cons", ["Tuple2", w_174 / 2, 0 - h_175 / 2], ["Nil"]]]]])(pos_176)
1982− }
1983− }
1984− }
1985− function oval_81(w_177) {
1986− return function(h_178) {
1987− return function(pos_179) {
1988− return function() {
1989− var n_180 = 50;
1990− return function() {
1991− function f_181(i_182) {
1992− return["Tuple2", w_177 / 2 * Math.cos(2 * (Math.PI / n_180) * i_182), h_178 / 2 * Math.sin(2 * (Math.PI / n_180) * i_182)];
1993− }
1994− return Shape_78(map(f_181)(function() {
1995− var lo = 0;
1996− var hi = n_180 - 1;
1997− var lst = ["Nil"];
1998− if(lo <= hi) {
1999− do {
2000− lst = ["Cons", hi, lst]
2001− }while(hi-- > lo)
2002− }
2003− return lst
2004− }()))(pos_179)
2005− }()
2006− }()
2007− }
2008− }
2009− }
2010− function circle_82(r_183) {
2011− return oval_81(2 * r_183)(2 * r_183)
2012− }
2013− function ngon_83(n_184) {
2014− return function(r_185) {
2015− return function(pos_186) {
2016− return function() {
2017− var m_187 = n_184;
2018− return function() {
2019− function f_188(i_189) {
2020− return["Tuple2", r_185 * Math.cos(2 * (Math.PI / m_187) * i_189), r_185 * Math.sin(2 * (Math.PI / m_187) * i_189)];
2021− }
2022− return Shape_78(map(f_188)(function() {
2023− var lo = 0;
2024− var hi = n_184 - 1;
2025− var lst = ["Nil"];
2026− if(lo <= hi) {
2027− do {
2028− lst = ["Cons", hi, lst]
2029− }while(hi-- > lo)
2030− }
2031− return lst
2032− }()))(pos_186)
2033− }()
2034− }()
2035− }
2036− }
2037− }
2038− function solid_89(clr_190) {
2039− return function(ln_191) {
2040− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Solid_68)(clr_190)(ln_191))
2041− }
2042− }
2043− function dotted_90(clr_192) {
2044− return function(ln_193) {
2045− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Dotted_69)(clr_192)(ln_193))
2046− }
2047− }
2048− function dashed_91(clr_194) {
2049− return function(ln_195) {
2050− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Dashed_70)(clr_194)(ln_195))
2051− }
2052− }
2053− function customLine_92(pattern_196) {
2054− return function(clr_197) {
2055− return function(ln_198) {
2056− return Form_84(0)(1)(["Tuple2", 0, 0])(FLine_85(Custom_71(pattern_196))(clr_197)(ln_198))
2057− }
2058− }
2059− }
2060− function filled_93(clr) {
2061− return function(shape) {
2062− return Form_84(0)(1)(shape[2])(FShape_86(Filled_72)(clr)(shape));
2063− }
2064− }
2065− function outlined_94(clr) {
2066− return function(shape) {
2067− return Form_84(0)(1)(shape[2])(FShape_86(Outlined_73)(clr)(shape));
2068− }
2069− }
2070− function customOutline_95(pattern) {
2071− return function(clr) {
2072− return function(shape) {
2073− return Form_84(0)(1)(shape[2])(FShape_86(CustomOutline_74(pattern))(clr)(shape));
2074− }
2075− }
2076− }
2077− function textured(src) {
2078− return function(shape) {
2079− return Form_84(0)(1)(shape[2])(FShape_86(["Textured",src])(null)(shape));
2080− }
2081− }
2082− function rotate_98(t_212) {
2083− return function(Form$thetascaleposform_213) {
2084− return function(case5) {
2085− var case0 = case5;
2086− switch(case0[0]) {
2087− case "Form":
2088− var case1 = case0[1], case2 = case0[2], case3 = case0[3], case4 = case0[4];
2089− return Form_84(t_212 + case1)(case2)(case3)(case4)
2090− }
2091− throw new Error("Non-exhaustive pattern match in case");
2092− }(Form$thetascaleposform_213)
2093− }
2094− }
2095− function scale_99(s) {
2096− return function(form) {
2097− return Form_84(form[1])(s * form[2])(form[3])(form[4])
2098− }
2099− }
2100− function move_100(x_224) {
2101− return function(y_225) {
2102− return function(Form$thetascaleTuple2$pxpyform_226) {
2103− return function(case7) {
2104− var case0 = case7;
2105− switch(case0[0]) {
2106− case "Form":
2107− var case1 = case0[1], case2 = case0[2], case3 = case0[3], case4 = case0[4];
2108− switch(case3[0]) {
2109− case "Tuple2":
2110− var case5 = case3[1], case6 = case3[2];
2111− return Form_84(case1)(case2)(["Tuple2", x_224 + case5, y_225 + case6])(case4)
2112− }
2113− break
2114− }
2115− throw new Error("Non-exhaustive pattern match in case");
2116− }(Form$thetascaleTuple2$pxpyform_226)
2117− }
2118− }
2119− }
2120− return{left:left_6, right:right_7, down:down_8, up:up_9, inward:inward_10, outward:outward_11, topLeft:topLeft_22, topRight:topRight_23, bottomLeft:bottomLeft_24, bottomRight:bottomRight_25, midLeft:midLeft_26, midRight:midRight_27, midTop:midTop_28, midBottom:midBottom_29, middle:middle_30, middleAt:middleAt, topLeftAt:topLeftAt_31, topRightAt:topRightAt_32, bottomLeftAt:bottomLeftAt_33, bottomRightAt:bottomRightAt_34, absolute:absolute_35, relative:relative_36, width:width_47, height:height_48, size:size_49, opacity:opacity_50,
2121− color:color_51, link:link, widthOf:widthOf_52, heightOf:heightOf_53, sizeOf:sizeOf_54, text:text_56, asText:asText, plainText:plainText, centeredText:centeredText, justifiedText:justifiedText, rightedText:rightedText, image:image_57, images:images, video:video_58, fittedImage:fittedImage_59, flow:flow_60, above:above_61, below:below_62, beside:beside_63, layers:layers_64, collage:collage_65, spacer:spacer_66, container:container_67, line:line_76, segment:segment_77, polygon:polygon_79, rect:rect_80, oval:oval_81, circle:circle_82, ngon:ngon_83, solid:solid_89, dotted:dotted_90, dashed:dashed_91, customLine:customLine_92, filled:filled_93,
2122− outlined:outlined_94, customOutline:customOutline_95, textured:textured, sprite:sprite_96, toForm:toForm_97, rotate:rotate_98, scale:scale_99, move:move_100,
2123− isWithin: Collage.insideForm}
2124−}();
2125−Elm.Text = function() {
2126− function fromString(s) { return Value.toText(s); }
2127−
2128− var addTag = function(tag) { return function(text) {
2129− return '<' + tag + ' style="padding:0;margin:0">' + text + '</' + tag + '>';
2130− };
2131− };
2132− var addStyle = function(style, value) { return function(text) {
2133− return "<span style='" + style + ":" + value + "'>" + text + "</span>";
2134− };
2135− };
2136−
2137− var typeface = function(name) {
2138− name = Elm.JavaScript.castStringToJSString(name);
2139− return addStyle('font-family', name);
2140− };
2141− var size = function(px) {
2142− return addStyle('font-size', px + 'px');
2143− };
2144− var header = addTag('h1');
2145− var height = function(h) { return addStyle('font-size', h+'em'); }
2146− var italic = addStyle('font-style', 'italic');
2147− var bold = addTag('b');
2148− var color = function(c) {
2149− return addStyle('color', Elm.Color.extract(c));
2150− };
2151− var underline = addStyle('text-decoration', 'underline');
2152− var overline = addStyle('text-decoration', 'overline');
2153− var strikeThrough = addStyle('text-decoration', 'line-through');
2154− var link = function(href) { return function(text) {
2155− return "<a href='" + fromString(href) + "'>" + text + "</a>";
2156− };
2157− };
2158−
2159− return {fromString : fromString,
2160− toText: fromString,
2161− header : header,
2162− height : height,
2163− italic : italic,
2164− bold : bold,
2165− underline : underline,
2166− overline : overline,
2167− strikeThrough : strikeThrough,
2168− monospace : typeface('monospace'),
2169− typeface : typeface,
2170− color : color,
2171− link : link };
2172−}();
2173−
2174−var Render = function(){
2175−
2176−function newElement(elementType) {
2177− var e = document.createElement(elementType);
2178− e.style.padding = "0";
2179− e.style.margin = "0";
2180− return e;
2181−};
2182−
2183−function addTo(container, elem) {
2184− container.appendChild(elem);
2185−};
2186−
2187−function makeText(pos,txt) {
2188− var e = newElement('div');
2189− e.innerHTML = txt;
2190− e.style.textAlign = pos;
2191− return e;
2192−};
2193−
2194−function image(src) {
2195− var img = newElement('img');
2196− img.src = src;
2197− img.name = src;
2198− img.style.display = "block";
2199− return img;
2200−}
2201−
2202−function fittedImage(w,h,src) {
2203− var e = newElement('div');
2204− e.style.width = w + 'px';
2205− e.style.height = h + 'px';
2206− e.style.position = "relative";
2207− e.style.overflow = "hidden";
2208−
2209− var img = newElement('img');
2210− img.onload = function() {
2211− img.style.position = 'absolute';
2212− img.style.margin = 'auto';
2213−
2214− var sw = w, sh = h;
2215− if (w / h > this.width / this.height) {
2216− sh = Math.round(this.height * w / this.width);
2217− } else {
2218− sw = Math.round(this.width * h / this.height);
2219− }
2220− img.style.width = sw + 'px';
2221− img.style.height = sh + 'px';
2222− img.style.left = ((w - sw) / 2) + 'px';
2223− img.style.top = ((h - sh) / 2) + 'px';
2224− };
2225− img.src = src;
2226− img.name = src;
2227− addTo(e,img);
2228− return e;
2229−};
2230−
2231−var video = function(src) {
2232− var e = newElement('video');
2233− e.controls = "controls";
2234− var source = newElement('source');
2235− source.src = src;
2236− var segs = src.split('.');
2237− source.type = "video/" + segs[segs.length-1];
2238− addTo(e, source);
2239− e.style.display = "block";
2240− return e;
2241−};
2242−
2243−function divify(e) {
2244− var div = newElement('div');
2245− addTo(div, e);
2246− return div;
2247−};
2248−function goDown(e) {
2249− return e //.tagName === "DIV" ? e : divify(e);
2250−};
2251−function goRight(e) {
2252− e.style.styleFloat = "left";
2253− e.style.cssFloat = "left";
2254− return e;
2255−};
2256−function goIn(e) {
2257− e.style.position = 'absolute';
2258− return e;
2259−};
2260−function flowWith(f, prep, elist) {
2261− var container = newElement('div');
2262− for (var i = elist.length; i--; ) {
2263− addTo(container, f(prep(elist[i])));
2264− }
2265− return container;
2266−};
2267−
2268−function flow(dir,elist) {
2269− switch(dir) {
2270− case "DDown": elist = elist.slice(0).reverse();
2271− case "DUp": return flowWith(goDown,render,elist);
2272− case "DRight": elist = elist.slice(0).reverse();
2273− case "DLeft": return flowWith(goRight,render,elist);
2274− case "DOut": elist = elist.slice(0).reverse();
2275− case "DIn": return flowWith(goIn,render,elist);
2276− };
2277−};
2278−
2279−function toPos(pos) {
2280− switch(pos[0]) {
2281− case "Absolute": return pos[1] + "px";
2282− case "Relative": return (pos[1] * 100) + "%";
2283− }
2284−}
2285−
2286−function setPos(pos,e) {
2287− e.style.position = 'absolute';
2288− e.style.margin = 'auto';
2289− switch(pos[0]) {
2290− case "Position":
2291− if (pos[1][0] !== "Far") e.style.left = 0;
2292− if (pos[1][0] !== "Near") e.style.right = 0;
2293− if (pos[2][0] !== "Far") e.style.top = 0;
2294− if (pos[2][0] !== "Near") e.style.bottom = 0;
2295− break;
2296− case "PositionAt":
2297− e.style.top = toPos(pos[2]);
2298− e.style.left = toPos(pos[1]);
2299− var shift = "translate(" + ~~(-e.style.width.slice(0,-2) / 2) + "px," + ~~(-e.style.height.slice(0,-2) / 2) + "px)";
2300− e.style.transform = shift;
2301− e.style.msTransform = shift;
2302− e.style.MozTransform = shift;
2303− e.style.webkitTransform = shift;
2304− e.style.OTransform = shift;
2305− break;
2306− default:
2307− var p = pos[0].slice(-2);
2308− e.style[p[0] === "T" ? 'top' : 'bottom'] = toPos(pos[2]);
2309− e.style[p[1] === "L" ? 'left' : 'right'] = toPos(pos[1]);
2310− }
2311−}
2312−
2313−function container(pos,elem) {
2314− var e = render(elem);
2315− setPos(pos,e);
2316− var div = newElement('div');
2317− div.style.position = "relative";
2318− div.style.overflow = "hidden";
2319− addTo(div,e);
2320− return div;
2321−};
2322−
2323−function render(elem) {
2324− var e = {};
2325− switch(elem[2][0]) {
2326− case "EText": e = makeText(elem[2][1],elem[2][2]); break;
2327− case "EImage": e = image(elem[2][1]); break;
2328− case "EVideo": e = video(elem[2][1]); break;
2329− case "EFittedImage": e = fittedImage(elem[3],elem[4],elem[2][1]); break;
2330− case "EFlow": e = flow(elem[2][1][0],elem[2][2]); break;
2331− case "ECollage": e = Collage.collage(elem[2][1],elem[2][2],elem[2][3]); break;
2332− case "EEmpty": e = newElement('div'); break;
2333− case "EContainer": e = container(elem[2][1],elem[2][2]); break;
2334− case "EHtml":
2335− e = elem[2][1];
2336− if (e.type !== 'button') {
2337− var p = Value.getExcess(e);
2338− elem[3] -= p[0];
2339− elem[4] -= p[1];
2340− }
2341− break;
2342− case "EExternalHtml":
2343− e = newElement('div');
2344− addTo(e, elem[2][1]);
2345− break;
2346− }
2347− e.id = elem[1];
2348− e.style.width = (~~elem[3]) + 'px';
2349− e.style.height = (~~elem[4]) + 'px';
2350− if (elem[5] !== 1) { e.style.opacity = elem[5]; }
2351− if (elem[6][0] === "Just") {
2352− e.style.backgroundColor = Elm.Color.extract(elem[6][1]);
2353− }
2354− if (elem[7][0] === "Just") {
2355− var a = newElement('a');
2356− a.href = elem[7][1];
2357− addTo(a,e);
2358− return a;
2359− }
2360− return e;
2361−};
2362−
2363−function update(node,curr,next) {
2364− if (node.tagName === 'A') { node = node.firstChild; }
2365− if (curr[1] === next[1]) return;
2366− if (curr[2][0] !== next[2][0]) {
2367− return node.parentNode.replaceChild(render(next),node);
2368− }
2369− var nextE = next[2], currE = curr[2];
2370− switch(nextE[0]) {
2371− case "EText":
2372− if (nextE[1] !== currE[1]) node.style.textAlign = nextE[1];
2373− if (nextE[2] !== currE[2]) node.innerHTML = nextE[2];
2374− break;
2375− case "EImage":
2376− if (nextE[1] !== currE[1]) node.src = nextE[1];
2377− break;
2378− case "EVideo":
2379− case "EFittedImage":
2380− if (!Value.eq(nextE,currE) || next[3]!==curr[3] || next[4]!==curr[4]) {
2381− return node.parentNode.replaceChild(render(next),node);
2382− }
2383− break;
2384− case "ECollage":
2385− if (nextE[1] !== currE[1] || nextE[2] !== currE[2] || nextE[3].length !== currE[3].length) {
2386− return node.parentNode.replaceChild(render(next),node);
2387− }
2388− Collage.updateCollage(node,currE[3],nextE[3]);
2389− break;
2390− case "EFlow":
2391− if (nextE[1] !== currE[1]) {
2392− return node.parentNode.replaceChild(render(next),node);
2393− }
2394− var nexts = nextE[2];
2395− var kids = node.childNodes;
2396− if (nexts.length !== kids.length) {
2397− return node.parentNode.replaceChild(render(next),node);
2398− }
2399− var currs = currE[2];
2400− var goDir = function(x) { return x; };
2401− switch(nextE[1][0]) {
2402− case "DDown": case "DUp": goDir = goDown; break;
2403− case "DRight": case "DLeft": goDir = goRight; break;
2404− case "DOut": case "DIn": goDir = goIn; break;
2405− }
2406− for (var i = kids.length; i-- ;) {
2407− update(kids[i],currs[i],nexts[i]);
2408− goDir(kids[i]);
2409− }
2410− break;
2411− case "EContainer":
2412− update(node.childNodes[0],currE[2],nextE[2]);
2413− setPos(nextE[1],node.childNodes[0]);
2414− break;
2415− case "EEmpty":
2416− break;
2417− case "EHtml":
2418− if (next[1] !== curr[1]) {
2419− var e = render(next);
2420− node.parentNode.replaceChild(e,node);
2421− node = e;
2422− }
2423− if (e.type !== 'button') {
2424− var p = Value.getExcess(node);
2425− next[3] -= p[0];
2426− next[4] -= p[1];
2427− }
2428− break;
2429− case "EExternalHtml":
2430− if (next[1] !== curr[1])
2431− node.parentNode.replaceChild(render(next),node);
2432− break;
2433− }
2434− if (next[3] !== curr[3]) node.style.width = (~~next[3]) + 'px';
2435− if (next[4] !== curr[4]) node.style.height = (~~next[4]) + 'px';
2436− if (next[5] !== curr[5]) node.style.opacity = next[5];
2437− if (next[6].length === 2) {
2438− var clr = Elm.Color.extract(next[6][1]);
2439− if (clr !== node.style.backgroundColor) node.style.backgroundColor = clr;
2440− }
2441− if (next[7].length === 2) {
2442− if (curr[7].length === 1 || next[7][1] !== curr[7][1]) node.parentNode.href = next[7][1];
2443− }
2444− next[1] = curr[1];
2445−}
2446−
2447−return {render:render,update:update,addTo:addTo,newElement:newElement,flowWith:flowWith,goIn:goIn};
2448−
2449−}();
2450−Elm.Signal = function() {
2451− var send = function(node, timestep, changed) {
2452− var kids = node.kids;
2453− for (var i = kids.length; i--; ) {
2454− kids[i].recv(timestep, changed, node.id);
2455− }
2456− };
2457− function input(base) {
2458− this.id = Guid.guid();
2459− this.value = base;
2460− this.kids = [];
2461− this.defaultNumberOfKids = 0;
2462− this.recv = function(timestep, eid, v) {
2463− var changed = eid === this.id;
2464− if (changed) { this.value = v; }
2465− send(this, timestep, changed);
2466− return changed;
2467− };
2468− Dispatcher.inputs.push(this);
2469− };
2470− function lift(func,args) {
2471− this.id = Guid.guid();
2472− this.value = null;
2473− this.kids = [];
2474− this.count = 0;
2475− this.changed = false;
2476−
2477− args.reverse();
2478− this.recalc = function() {
2479− var f = func;
2480− for (var i = args.length; i--; ) {
2481− f = f(args[i].value);
2482− }
2483− this.value = f;
2484− };
2485− this.recalc();
2486−
2487− this.recv = function(timestep, changed, parentID) {
2488− this.count += 1;
2489− if (changed) { this.changed = true; }
2490− if (this.count == args.length) {
2491− if (this.changed) { this.recalc() }
2492− send(this, timestep, this.changed);
2493− this.changed = false;
2494− this.count = 0;
2495− }
2496− };
2497− for (var i = args.length; i--; ) {
2498− args[i].kids.push(this);
2499− }
2500− };
2501− function fold(func,base,baseIsFunc,input) {
2502− this.id = Guid.guid();
2503− this.value = baseIsFunc ? base(input.value) : base;
2504− this.kids = [];
2505− this.recv = function(timestep, changed, parentID) {
2506− if (changed) { this.value = func(input.value)(this.value); }
2507− send(this, timestep, changed);
2508− };
2509− input.kids.push(this);
2510− };
2511−
2512− function dropIf(pred,base,input) {
2513− this.id = Guid.guid();
2514− this.value = pred(input.value) ? base : input.value;
2515− this.kids = [];
2516− this.recv = function(timestep, changed, parentID) {
2517− var chng = changed && !pred(input.value);
2518− if (chng) { this.value = input.value; }
2519− send(this, timestep, chng);
2520− };
2521− input.kids.push(this);
2522− };
2523−
2524− function dropRepeats(input) {
2525− this.id = Guid.guid();
2526− this.value = input.value;
2527− this.kids = [];
2528− this.recv = function(timestep, changed, parentID) {
2529− var chng = changed && !Value.eq(this.value,input.value);
2530− if (chng) { this.value = input.value; }
2531− send(this, timestep, chng);
2532− };
2533− input.kids.push(this);
2534− };
2535−
2536− var dropWhen = function(s1) { return function(b) { return function(s2) {
2537− var pairs = new lift(function(x){return function(y){return [x,y];};},[s1,s2]);
2538− var dropped = new dropIf(function(p){return p[0];},[true,b],pairs);
2539− return new lift(function(p){return p[1];},[dropped]); }; };
2540− };
2541−
2542− function timeIndex(pair,s) {
2543− this.id = Guid.guid();
2544− var t = (new window.Date).getTime();
2545− this.value = pair ? Value.Tuple(t,s.value) : t;
2546− this.kids = [];
2547− this.recv = function(timestep, changed, parentID) {
2548− if (changed) this.value = pair ? Value.Tuple(timestep, s.value) : timestep;
2549− send(this, timestep, changed);
2550− };
2551− s.kids.push(this);
2552− }
2553−
2554− function sampleOn(s1,s2) {
2555− this.id = Guid.guid();
2556− this.value = s2.value;
2557− this.kids = [];
2558− this.count = 0;
2559− this.changed = false;
2560−
2561− this.recv = function(timestep, changed, parentID) {
2562− if (parentID === s1.id) this.changed = changed;
2563− this.count += 1;
2564− if (this.count == 2) {
2565− if (this.changed) { this.value = s2.value; }
2566− send(this, timestep, this.changed);
2567− this.count = 0;
2568− this.changed = false;
2569− }
2570− };
2571− s1.kids.push(this);
2572− s2.kids.push(this);
2573− };
2574−
2575− function delay(t) { return function(s) {
2576− var delayed = new input(s.value);
2577− var firstEvent = true;
2578− function update(v) {
2579− if (firstEvent) return;
2580− setTimeout(function() { Dispatcher.notify(delayed.id,v); },t);
2581− }
2582− function first(a) { return function(b) { return a; }; }
2583− var out = new sampleOn(delayed,new lift(first, [delayed, new lift(update,[s])]));
2584− firstEvent = false;
2585− return out;
2586− };
2587− }
2588−
2589− function merge(s1,s2) {
2590− this.id = Guid.guid();
2591− this.value = s1.value;
2592− this.kids = [];
2593− this.next = null;
2594− this.count = 0;
2595− this.changed = false;
2596−
2597− this.recv = function(timestep, changed, parentID) {
2598− this.count += 1;
2599− if (changed) {
2600− this.changed = true;
2601− if (parentID == s2.id && this.next === null) { this.next = s2.value; }
2602− if (parentID == s1.id) { this.next = s1.value; }
2603− }
2604−
2605− if (this.count == 2) {
2606− if (this.changed) {
2607− this.value = this.next;
2608− this.next = null;
2609− }
2610− send(this, timestep, this.changed);
2611− this.changed = false;
2612− this.count = 0;
2613− }
2614− };
2615− s1.kids.push(this);
2616− s2.kids.push(this);
2617− };
2618−
2619− function merges(ss) {
2620− function mrg(x) { return function(y) { return new merge(x,y); }; }
2621− return Elm.List.foldl1(mrg)(ss);
2622− }
2623−
2624− function mergeEither(s1) { return function(s2) {
2625− function f(s) { return function(x) { return [s,x]; }; }
2626− return new merge(new lift(f('Left'),[s1]), new lift(f('Right'),[s2]));
2627− };
2628− }
2629−
2630− function average(sampleSize) { return function(s) {
2631− var sample = new Array(sampleSize);
2632− var i = sampleSize;
2633− while (i--) sample[i] = 0;
2634− i = 0;
2635− var full = false;
2636− var total = 0;
2637− function f(n) {
2638− total += n - sample[i];
2639− sample[i] = n;
2640− var avg = total / Math.max(1, full ? sampleSize : i);
2641− if (++i == sampleSize) { full = true; i = 0; }
2642− return avg;
2643− }
2644− return new lift(f, [s]);
2645− };
2646− }
2647−
2648− return {
2649− constant : function(v) { return new input(v); },
2650− lift : function(f){return function(e){return new lift(f,[e]);};},
2651− lift2 : function(f) {
2652− return function(e1) { return function(e2) {
2653− return new lift(f, [e1,e2]); };};},
2654− lift3 : function(f) {
2655− return function(e1) { return function(e2) {
2656− return function(e3){return new lift(f,[e1,e2,e3]);};};};},
2657− lift4 : function(f) {
2658− return function(e1) { return function(e2) {
2659− return function(e3) { return function(e4) {
2660− return new lift(f, [e1,e2,e3,e4]);};};};};},
2661− lift5 : function(f) {
2662− return function(e1) { return function(e2) {
2663− return function(e3) { return function(e4) {
2664− return function(e5) {
2665− return new lift(f, [e1,e2,e3,e4,e5]);};};};};};},
2666− lift6 : function(f) { return function(e1) { return function(e2) {
2667− return function(e3) { return function(e4) {
2668− return function(e5) { return function(e6) {
2669− return new lift(f, [e1,e2,e3,e4,e5,e6]); };};};};};};},
2670− lift7 : function(f) { return function(e1) { return function(e2) {
2671− return function(e3) { return function(e4) {
2672− return function(e5) { return function(e6) {
2673− return function(e7) {
2674− return new lift(f, [e1,e2,e3,e4,e5,e6,e7]);};};};};};};};},
2675− lift8 : function(f) { return function(e1) { return function(e2) {
2676− return function(e3) { return function(e4) {
2677− return function(e5) { return function(e6) {
2678− return function(e7) { return function(e8) {
2679− return new lift(f, [e1,e2,e3,e4,e5,e6,e7,e8]);};};};};};};};};},
2680− foldp : function(f) { return function(b) { return function(e) {
2681− return new fold(f,b,false,e); }; }; },
2682− foldp$ : function(f) { return function(b) { return function(e) {
2683− return new fold(f,b,true,e); }; }; },
2684− foldp1 : function(f) { return function(e) {
2685− return new fold(f,function(x){return x;},true,e); }; },
2686− delay : delay,
2687− merge : function(s1) { return function(s2) { return new merge(s1,s2)}; },
2688− merges : merges,
2689− mergeEither : mergeEither,
2690− average : average,
2691− count : function(sig) {
2692− var incr = function(_){return function(c){return c+1;};};
2693− return new fold(incr,0,false,sig) },
2694− countIf : function(pred) { return function(sig) {
2695− var incr = function(x){return function(c){return pred(x) ? c+1 : c;};};
2696− return new fold(incr,0,false,sig) }; },
2697− keepIf : function(pred) { return function(base) { return function(sig) {
2698− return new dropIf(function(x) { return !pred(x)},base,sig); }; }; },
2699− dropIf : function(pred) { return function(base) { return function(sig) {
2700− return new dropIf(pred,base,sig); }; }; },
2701− keepWhen : function(s) { return dropWhen(new lift(function(b){return !b;},[s])); },
2702− dropWhen : dropWhen,
2703− dropRepeats : function(s) { return new dropRepeats(s);},
2704− sampleOn : function(s1){return function(s2){return new sampleOn(s1,s2);};},
2705− timestamp : function(s) { return new timeIndex(true, s); },
2706− timeOf : function(s) { return new timeIndex(false, s); }
2707− };
2708−}();
2709−var Dispatcher = function() {
2710− var program = null;
2711− var inputs = [];
2712− var currentElement = null;
2713−
2714− var initialize = function() {
2715− program = Elm.main();
2716− if (!('recv' in program)) {
2717− program = Elm.Signal.constant(program);
2718− }
2719−
2720− currentElement = program.value;
2721− filterDeadInputs();
2722−
2723− var content = document.getElementById('content');
2724− content.appendChild(Render.render(currentElement));
2725− var w = document.getElementById('widthChecker').offsetWidth;
2726− if (w !== window.innerWidth) {
2727− Dispatcher.notify(Elm.Window.dimensions.id, Value.Tuple(w, window.innerHeight));
2728− }
2729− program = Elm.Signal.lift(function(value) {
2730− var content = document.getElementById('content');
2731− Render.update(content.firstChild,currentElement,value);
2732− currentElement = value;
2733− return value;
2734− })(program);
2735− };
2736− var notify = function(id, v) {
2737− var timestep = (new window.Date).getTime();
2738− var hasListener = false;
2739− for (var i = inputs.length; i--; ) {
2740− hasListener = inputs[i].recv(timestep, id, v) || hasListener;
2741− }
2742− return hasListener;
2743− };
2744−
2745− function isAlive(input) {
2746− if (!('defaultNumberOfKids' in input)) return true;
2747− var len = input.kids.length;
2748− if (len == 0) return false;
2749− if (len > input.defaultNumberOfKids) return true;
2750− var alive = false;
2751− for (var i = len; i--; ) {
2752− alive = alive || isAlive(input.kids[i]);
2753− }
2754− return alive;
2755− }
2756− function filterDeadInputs() {
2757− var temp = [];
2758− for (var i = inputs.length; i--; ) {
2759− if (isAlive(inputs[i])) temp.push(inputs[i]);
2760− }
2761− inputs = temp;
2762− }
2763−
2764− return {initialize:initialize, notify:notify, inputs:inputs};
2765−}();
2766−/*! HTTP
2767−A library for asynchronous HTTP requests (AJAX). See the
2768−[WebSocket](http://elm-lang.org/docs/WebSocket.elm) library if
2769−you have very strict latency requirements.
2770−!*/
2771−
2772−Elm.HTTP = function() {
2773− var JS = Elm.JavaScript;
2774− var toElmString = Elm.JavaScript.castJSStringToString;
2775−
2776− /*[Creating Requests]*/
2777−
2778− /** get : String -> Request String
2779− Create a GET request to the given url.
2780− **/
2781− function get(url) { return request("GET")(url)(null)(["Nil"]); }
2782−
2783− /** post : String -> String -> Request String
2784− Create a POST request to the given url, carrying the given data.
2785− **/
2786− function post(url) { return function(data) {
2787− return request("POST")(url)(data)(["Nil"]); }; }
2788−
2789− /** request : String -> String -> String -> [(String,String)] -> Request String
2790− Create a customized request. Arguments are request type (get, post, put,
2791− delete, etc.), target url, data, and a list of additional headers.
2792− **/
2793− function request(verb) { return function(url) { return function(data) {
2794− return function(headers) {
2795− return {0 : "Request",
2796− length : 1,
2797− verb : JS.castStringToJSString(verb),
2798− url : JS.castStringToJSString(url),
2799− data : data === null ? null : JS.castStringToJSString(data),
2800− headers : headers }; }; }; };
2801− }
2802−
2803− function registerReq(queue,responses) { return function(req) {
2804− if (req.url !== "") { sendReq(queue,responses,req); }
2805− };
2806− }
2807−
2808− function updateQueue(queue,responses) {
2809− if (queue.length > 0) {
2810− Dispatcher.notify(responses.id, queue[0].value);
2811− if (queue[0].value[0] !== "Waiting") {
2812− queue.shift();
2813− setTimeout(function() { updateQueue(queue,responses); }, 0);
2814− }
2815− }
2816− }
2817−
2818− function sendReq(queue,responses,req) {
2819− var response = { value: ["Waiting"] };
2820− queue.push(response);
2821−
2822− var request = null;
2823− if (window.ActiveXObject) { request = new ActiveXObject("Microsoft.XMLHTTP"); }
2824− if (window.XMLHttpRequest) { request = new XMLHttpRequest(); }
2825− request.onreadystatechange = function(e) {
2826− if (request.readyState === 4) {
2827− response.value = (request.status === 200
2828− ? ["Success", toElmString(request.responseText)]
2829− : ["Failure", request.status,
2830− toElmString(request.statusText)]);
2831− setTimeout(function() { updateQueue(queue,responses); }, 0);
2832− }
2833− };
2834− request.open(req.verb, req.url, true);
2835− Elm.List.map(function(pair) {
2836− request.setRequestHeader(
2837− JS.castStringToJSString(pair[1]),
2838− JS.castStringToJSString(pair[2]));
2839− })(req.headers);
2840− request.send(req.data);
2841− return null;
2842− }
2843−
2844− /*[Responses]*/
2845−
2846− /** data Response a = Waiting | Success a | Failure Int String
2847− The datatype for responses. Success contains only the returned message.
2848− Failures contain both an error code and an error message.
2849− **/
2850−
2851− /*[Sending Requests]*/
2852−
2853− /** send : Signal (Request a) -> Signal (Response String)
2854− Performs an HTTP request with the given requests. Produces a signal
2855− that carries the responses.
2856− **/
2857− function send(requests) {
2858− var responses = Elm.Signal.constant(["Waiting"]);
2859− var sender = Elm.Signal.lift(registerReq([],responses))(requests);
2860− function f(x) { return function(y) { return x; } }
2861− return Elm.Signal.lift2(f)(responses)(sender);
2862− }
2863−
2864− /** sendGet : Signal String -> Signal (Response String)
2865− Performs an HTTP GET request with the given urls. Produces a signal
2866− that carries the responses.
2867− **/
2868−
2869− return {get : get,
2870− post : post,
2871− request : request,
2872− send : send,
2873− sendGet : function(urls){return send(Elm.Signal.lift(get)(urls));}
2874− };
2875−}();
2876−/*! WebSocket
2877−A library for low latency HTTP communication. See the HTTP library for standard
2878−requests like GET, POST, etc.
2879−!*/
2880−
2881−Elm.WebSocket = function() {
2882− var JS = Elm.JavaScript;
2883−
2884− /** open : String -> Signal String -> Signal String
2885− Create a web-socket. The first argument is the URL of the desired
2886− web-socket server. The input signal holds the outgoing messages,
2887− and the resulting signal contains the incoming ones.
2888− **/
2889− function open(url) { return function(outgoing) {
2890− var incoming = Elm.Signal.constant(["Nil"]);
2891− var ws = new window.WebSocket(JS.castStringToJSString(url));
2892−
2893− var pending = [];
2894− var ready = false;
2895−
2896− ws.onopen = function(e) {
2897− var len = pending.length;
2898− for (var i = 0; i < len; ++i) { ws.send(pending[i]); }
2899− ready = true;
2900− };
2901− ws.onmessage = function(event) {
2902− Dispatcher.notify(incoming.id, JS.castJSStringToString(event.data));
2903− };
2904−
2905− function send(msg) {
2906− var s = JS.castStringToJSString(msg);
2907− ready ? ws.send(s) : pending.push(s);
2908− }
2909−
2910− function take1(x) { return function(y) { return x; } }
2911− return Elm.Signal.lift2(take1)(incoming)(Elm.Signal.lift(send)(outgoing));
2912− };
2913− }
2914−
2915− return {open:open};
2916−}();
2917−
2918−Elm.Input = function() {
2919− var JS = Elm.JavaScript;
2920− var toElmString = Elm.JavaScript.castJSStringToString;
2921− var newTextInput = function(elem, ghostText) {
2922− elem.placeholder = JS.castStringToJSString(ghostText);
2923− var str = Elm.Signal.constant(["Nil"]);
2924− Value.addListener(elem, 'keyup', function(e) {
2925− Dispatcher.notify(str.id, toElmString(elem.value));
2926− elem.focus();
2927− });
2928− elem.style.padding = "1px";
2929− return Value.Tuple(Value.wrap(elem), str);
2930− };
2931− var newElement = function(name) {
2932− var e = document.createElement(name);
2933− e.style.padding = "0";
2934− e.style.margin = "0";
2935− return e;
2936− };
2937− var textArea = function(cols) { return function(rows) {
2938− var textarea = newElement('textarea');
2939− textarea.rows = rows;
2940− textarea.cols = cols;
2941− return newTextInput(textarea, "");
2942− };
2943− };
2944− var textField = function(ghostText) {
2945− var field = newElement('input');
2946− field.type = 'text';
2947− return newTextInput(field, ghostText);
2948− };
2949− var password = function(ghostText) {
2950− var field = newElement('input');
2951− field.type = 'password';
2952− return newTextInput(field, ghostText);
2953− };
2954− var checkbox = function(checked) {
2955− var box = newElement('input');
2956− box.type = 'checkbox';
2957− box.checked = checked;
2958− var status = Elm.Signal.constant(checked);
2959− Value.addListener(box, 'change', function(e) {
2960− Dispatcher.notify(status.id, box.checked);
2961− });
2962− return Value.Tuple(Value.wrap(box), status);
2963− };
2964− var dropDown = function(options) {
2965− var slct = newElement('select');
2966− var opts = [];
2967− while (options[0] === "Cons") {
2968− var opt = newElement('option');
2969− var str = Value.toText(options[1][1]);
2970− opt.value = str;
2971− opt.innerHTML = str;
2972− slct.appendChild(opt);
2973− opts.push(options[1][2]);
2974− options = options[2];
2975− }
2976− var status = Elm.Signal.constant(opts[0]);
2977− Value.addListener(slct, 'change', function(e) {
2978− Dispatcher.notify(status.id, opts[slct.selectedIndex]);
2979− });
2980− return Value.Tuple(Value.wrap(slct), status);
2981− };
2982− var stringDropDown = function(opts) {
2983− return dropDown(Elm.List.map (function(x) {return Value.Tuple(x,x);}) (opts));
2984− };
2985− var button = function(name) {
2986− var b = newElement('input');
2987− b.type = "button";
2988− b.value = JS.castStringToJSString(name);
2989− var press = Elm.Signal.constant(false);
2990− Value.addListener(b, 'click', function(e) {
2991− Dispatcher.notify(press.id, true);
2992− Dispatcher.notify(press.id, false);
2993− });
2994− return Value.Tuple(Value.wrap(b),press);
2995− };
2996− return {textArea:textArea, textField:textField,
2997− password:password, checkbox:checkbox,
2998− dropDown:dropDown, stringDropDown:stringDropDown,
2999− button:button};
3000−}();
3001−
3002−Elm.Keyboard = { Raw : function() {
3003− var keysDown = Elm.Signal.constant(["Nil"]);
3004− var charPressed = Elm.Signal.constant(["Nothing"]);
3005−
3006− function remove(x,xs) {
3007− if (xs[0] === "Nil") return xs;
3008− if (xs[1] === x) return xs[2];
3009− return ["Cons", xs[1], remove(x,xs[2])];
3010− }
3011− function has(x,xs) {
3012− while (xs[0] !== "Nil") {
3013− if (xs[1] === x) return true;
3014− xs = xs[2];
3015− }
3016− return false;
3017− }
3018− Value.addListener(document, 'keydown', function(e) {
3019− if (has(e.keyCode, keysDown.value)) return;
3020− var hasListener = Dispatcher.notify(keysDown.id, ["Cons", e.keyCode, keysDown.value]);
3021− if (!hasListener)
3022− this.removeEventListener('keydown',arguments.callee,false);
3023− });
3024− Value.addListener(document, 'keyup', function(e) {
3025− var codes = remove(e.keyCode, keysDown.value);
3026− var hasListener = Dispatcher.notify(keysDown.id, codes);
3027− if (!hasListener)
3028− this.removeEventListener('keyup',arguments.callee,false);
3029− });
3030− Value.addListener(window, 'blur', function(e) {
3031− var hasListener = Dispatcher.notify(keysDown.id, ["Nil"]);
3032− if (!hasListener)
3033− this.removeEventListener('blur',arguments.callee,false);
3034− });
3035− Value.addListener(document, 'keypress', function(e) {
3036− var hasListener = Dispatcher.notify(charPressed.id, ["Just",e.charCode || e.keyCode]);
3037− Dispatcher.notify(charPressed.id, ["Nothing"]);
3038− if (!hasListener)
3039− this.removeEventListener('keypress',arguments.callee,false);
3040− });
3041− return {keysDown:keysDown,
3042− charPressed:charPressed};
3043− }()
3044−};
3045−
3046−/*! Keyboard
3047−These are nicely curated inputs from the keyboard. See the
3048−[Keyboard.Raw library](/docs/Signal/KeyboardRaw.elm) for a
3049−lower-level interface that will let you define more complicated behavior.
3050−!*/
3051−
3052−(function() {
3053− function keySignal(f) {
3054− var signal = Elm.Signal.lift(f)(Elm.Keyboard.Raw.keysDown);
3055− Elm.Keyboard.Raw.keysDown.defaultNumberOfKids += 1;
3056− signal.defaultNumberOfKids = 0;
3057− return signal;
3058− }
3059−
3060− function dir(left,right,up,down) {
3061− function f(ks) {
3062− var x = 0, y = 0;
3063− while (ks[0] == "Cons") {
3064− switch (ks[1]) {
3065− case left : --x; break;
3066− case right: ++x; break;
3067− case up : ++y; break;
3068− case down : --y; break;
3069− }
3070− ks = ks[2];
3071− }
3072− return { _:[true], x:[x], y:[y] };
3073− }
3074− return keySignal(f);
3075− }
3076−
3077− function is(key) {
3078− function f(ks) {
3079− while (ks[0] == "Cons") {
3080− if (key == ks[1]) return true;
3081− ks = ks[2];
3082− }
3083− return false;
3084− }
3085− return keySignal(f);
3086− }
3087−
3088− /*[Directions]*/
3089−
3090− /** arrows : Signal { x:Int, y:Int }
3091− A signal of records indicating which arrow keys are pressed.
3092−
3093− `{ x = 0, y = 0 }` when pressing no arrows.
3094− `{ x =-1, y = 0 }` when pressing the left arrow.
3095− `{ x = 1, y = 1 }` when pressing the up and right arrows.
3096− `{ x = 0, y =-1 }` when pressing the down, left, and right arrows.
3097− **/
3098− Elm.Keyboard.arrows = dir(37,39,38,40);
3099−
3100− /** wasd : Signal { x:Int, y:Int }
3101− Just like the arrows signal, but this uses keys w, a, s, and d,
3102− which are common controls for many computer games.
3103− **/
3104− Elm.Keyboard.wasd = dir(65,68,87,83);
3105−
3106− /*[Modifiers]*/
3107−
3108− /** shift : Signal Bool
3109− Whether the shift key is pressed.
3110− **/
3111− Elm.Keyboard.shift = is(16);
3112−
3113− /** ctrl : Signal Bool
3114− Whether the control key is pressed.
3115− **/
3116− Elm.Keyboard.ctrl = is(17);
3117−
3118− /** space : Signal Bool
3119− Whether the space key is pressed.
3120− **/
3121− Elm.Keyboard.space = is(32);
3122−
3123−}());
3124−/*! Mouse
3125− !*/
3126−
3127−Elm.Mouse = function() {
3128− /*[Position]*/
3129−
3130− /** position : Signal (Int,Int)
3131− The current mouse position.
3132− **/
3133− var position = Elm.Signal.constant(Value.Tuple(0,0));
3134− position.defaultNumberOfKids = 2;
3135−
3136− /** x : Signal Int
3137− The current x-coordinate of the mouse.
3138− **/
3139− var x = Elm.Signal.lift(function(p){return p[1];})(position);
3140− x.defaultNumberOfKids = 0;
3141−
3142− /** y : Signal Int
3143− The current y-coordinate of the mouse.
3144− **/
3145− var y = Elm.Signal.lift(function(p){return p[2];})(position);
3146− y.defaultNumberOfKids = 0;
3147−
3148− /*[Button Status]*/
3149−
3150− /** isDown : Signal Bool
3151− The current state of the left mouse-button.
3152− True when the button is down, and false otherwise.
3153− **/
3154− var isDown = Elm.Signal.constant(false);
3155−
3156− /** isClicked : Signal Bool
3157− True immediately after the left mouse-button has been clicked,
3158− and false otherwise.
3159− **/
3160− var isClicked = Elm.Signal.constant(false);
3161−
3162− /** clicks : Signal ()
3163− Always equal to unit. Event triggers on every mouse click.
3164− **/
3165− var clicks = Elm.Signal.constant(Value.Tuple());
3166−
3167− function getXY(e) {
3168− var posx = 0;
3169− var posy = 0;
3170− if (!e) e = window.event;
3171− if (e.pageX || e.pageY) {
3172− posx = e.pageX;
3173− posy = e.pageY;
3174− } else if (e.clientX || e.clientY) {
3175− posx = e.clientX + document.body.scrollLeft +
3176− document.documentElement.scrollLeft;
3177− posy = e.clientY + document.body.scrollTop +
3178− document.documentElement.scrollTop;
3179− }
3180− return Value.Tuple(posx, posy);
3181− }
3182−
3183− Value.addListener(document, 'click', function(e) {
3184− var hasListener1 = Dispatcher.notify(isClicked.id, true);
3185− var hasListener2 = Dispatcher.notify(clicks.id, Value.Tuple());
3186− Dispatcher.notify(isClicked.id, false);
3187− if (!hasListener1 && !hasListener2)
3188− this.removeEventListener('click',arguments.callee,false);
3189− });
3190− Value.addListener(document, 'mousedown', function(e) {
3191− var hasListener = Dispatcher.notify(isDown.id, true);
3192− if (!hasListener)
3193− this.removeEventListener('mousedown',arguments.callee,false);
3194− });
3195− Value.addListener(document, 'mouseup', function(e) {
3196− var hasListener = Dispatcher.notify(isDown.id, false);
3197− if (!hasListener)
3198− this.removeEventListener('mouseup',arguments.callee,false);
3199− });
3200− Value.addListener(document, 'mousemove', function(e) {
3201− var hasListener = Dispatcher.notify(position.id, getXY(e));
3202− if (!hasListener)
3203− this.removeEventListener('mousemove',arguments.callee,false);
3204− });
3205−
3206− /** isClickedOn : Element -> (Element, Signal Bool)
3207− Determine whether an element has been clicked. The resulting pair
3208− is a signal of booleans that is true when its paired element has
3209− been clicked. The signal is True immediately after the left
3210− mouse-button has been clicked, and false otherwise.
3211− **/
3212− var clickedOn = function(elem) {
3213− var node = Render.render(elem);
3214− var click = Elm.Signal.constant(false);
3215− Value.addListener(node, 'click', function(e) {
3216− Dispatcher.notify(click.id, true);
3217− Dispatcher.notify(click.id, false);
3218− });
3219− return Value.Tuple(Value.wrap(node), click);
3220− };
3221− return {position: position,
3222− x:x,
3223− y:y,
3224− isClicked: isClicked,
3225− isDown: isDown,
3226− clicks: clicks,
3227− isClickedOn: clickedOn
3228− };
3229− }();/*! Random
3230− !*/
3231−
3232−Elm.Random = function() {
3233− /*[In a Range]*/
3234−
3235− /** inRange : Int -> Int -> Signal Int
3236− Given a range from low to high, this produces a random number
3237− between 'low' and 'high' inclusive. The value in the signal does
3238− not change after the page has loaded.
3239− **/
3240− var inRange = function(min) { return function(max) {
3241− return Elm.Signal.constant(Math.floor(Math.random() * (max-min+1)) + min);
3242− };
3243− };
3244−
3245− /** randomize : Int -> Int -> Signal a -> Signal Int
3246− Given a range from low to high and a signal of values, this produces
3247− a new signal that changes whenever the input signal changes. The new
3248− values are random number between 'low' and 'high' inclusive.
3249− **/
3250− var randomize = function(min) { return function(max) { return function(signal) {
3251− function f(x) { return Math.floor(Math.random() * (max-min+1)) + min; }
3252− return Elm.Signal.lift(f)(signal);
3253− };
3254− };
3255− };
3256− return { inRange:inRange, randomize:randomize };
3257−}();/*! Time
3258−Library for working with time. Type `Time` represents some number of
3259−milliseconds.
3260−!*/
3261−
3262−Elm.Time = function() {
3263−
3264− /*[Times]*/
3265−
3266− /** hour, minute, second, ms : Time
3267− Units of time, making it easier to specify things like a
3268− half-second `(second / 2)`.
3269− **/
3270−
3271− function timeNow() { return (new window.Date).getTime(); }
3272−
3273− /*[Tickers]*/
3274−
3275− /** fps : Number -> Signal Time
3276− Takes desired number of frames per second (fps). The resulting signal
3277− gives a sequence of time deltas as quickly as possible until it reaches
3278− the desired FPS. A time delta is the time between the last frame and the
3279− current frame.
3280− **/
3281−
3282− /** fpsWhen : Number -> Signal Bool -> Signal Time
3283− Same as the fps function, but you can turn it on and off. Allows you
3284− to do brief animations based on user input without major ineffeciencies.
3285− The first time delta after a pause is always zero, no matter how long
3286− the pause was. This way summing the deltas will actually give the amount
3287− of time that the output signal has been running.
3288− **/
3289− function fpsWhen(desiredFPS) { return function (isOn) {
3290− var msPerFrame = 1000 / desiredFPS;
3291− var prev = timeNow(), curr = prev, diff = 0, wasOn = true;
3292− var ticker = Elm.Signal.constant(diff);
3293− function tick(zero) { return function() {
3294− curr = timeNow();
3295− diff = zero ? 0 : curr - prev;
3296− prev = curr;
3297− Dispatcher.notify(ticker.id, diff);
3298− };
3299− }
3300− var timeoutID = 0;
3301− function f(isOn) { return function(t) {
3302− if (isOn) {
3303− timeoutID = setTimeout(tick(!wasOn && isOn), msPerFrame);
3304− } else if (wasOn) {
3305− clearTimeout(timeoutID);
3306− }
3307− wasOn = isOn;
3308− return t;
3309− };
3310− }
3311− return Elm.Signal.lift2(f)(isOn)(ticker);
3312− };
3313− }
3314−
3315− /** every : Time -> Signal Time
3316− Takes a time interval t. The resulting signal is the current time,
3317− updated every t.
3318− **/
3319− function everyWhen(isOn) { return function(t) {
3320− var clock = Elm.Signal.constant(timeNow());
3321− function tellTime() { Dispatcher.notify(clock.id, timeNow()); }
3322− setInterval(tellTime, t);
3323− return clock;
3324− };
3325− }
3326−
3327− function since(t) { return function(s) {
3328− function cmp(a) { return function(b) { return !Value.eq(a,b); }; }
3329− var dcount = Elm.Signal.count(Elm.Signal.delay(t)(s));
3330− return Elm.Signal.lift2(cmp)(Elm.Signal.count(s))(dcount);
3331− };
3332− }
3333− function after(t) {
3334− t *= 1000;
3335− var thread = Elm.Signal.constant(false);
3336− setTimeout(function() { Dispatcher.notify(thread.id, true); }, t);
3337− return thread;
3338− }
3339− function before(t) {
3340− t *= 1000;
3341− var thread = Elm.Signal.constant(true);
3342− setTimeout(function() { Dispatcher.notify(thread.id, false); }, t);
3343− return thread;
3344− }
3345− function read(s) {
3346− var t = window.Date.parse(s);
3347− return isNaN(t) ? ["Nothing"] : ["Just",t];
3348− }
3349− return {fpsWhen : fpsWhen,
3350− fps : function(t) { return fpsWhen(t)(Elm.Signal.constant(true)); },
3351− every : everyWhen(Elm.Signal.constant(true)),
3352− delay : Elm.Signal.delay,
3353− since : since,
3354− after : after,
3355− before : before,
3356− hour : 3600000,
3357− minute : 60000,
3358− second : 1000,
3359− ms : 1,
3360− inHours : function(t) { return t / 3600000; },
3361− inMinutes : function(t) { return t / 60000; },
3362− inSeconds : function(t) { return t / 1000; },
3363− inMss : function(t) { return t; },
3364− toDate : function(t) { return new window.Date(t); },
3365− read : read
3366− };
3367−
3368−}();/*! Window !*/
3369−
3370−Elm.Window = function() {
3371−
3372− /*[Dimensions]*/
3373−
3374− /** dimensions : Signal (Int,Int)
3375− The current dimensions of the window (i.e. the area viewable to the
3376− user, not including scroll bars).
3377− **/
3378− var dimensions = Elm.Signal.constant(Value.Tuple(window.innerWidth,
3379− window.innerHeight));
3380− dimensions.defaultNumberOfKids = 2;
3381−
3382− /** width : Signal Int
3383− The current width of the window.
3384− **/
3385− var width = Elm.Signal.lift(function(p){return p[1];})(dimensions);
3386− width.defaultNumberOfKids = 0;
3387−
3388− /** height : Signal Int
3389− The current height of the window.
3390− **/
3391− var height = Elm.Signal.lift(function(p){return p[2];})(dimensions);
3392− height.defaultNumberOfKids = 0;
3393−
3394− Value.addListener(window, 'resize', function(e) {
3395− var w = document.getElementById('widthChecker').offsetWidth;
3396− var hasListener = Dispatcher.notify(dimensions.id,
3397− Value.Tuple(w, window.innerHeight));
3398− if (!hasListener)
3399− this.removeEventListener('resize',arguments.callee,false);
3400− });
3401− return {dimensions:dimensions,width:width,height:height};
3402−}();
3403−
3404−Elm.Date = function() {
3405−
3406− function dateNow() { return new window.Date; }
3407− function readDate(str) {
3408− var d = new window.Date(Elm.JavaScript.castStringToJSString(str));
3409− if (isNaN(d.getTime())) return ["Nothing"];
3410− return ["Just",d];
3411− }
3412−
3413− var dayTable = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
3414− var monthTable = ["Jan", "Feb", "Mar", "Apr", "May", "Jun",
3415− "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"];
3416−
3417− return {
3418− read : readDate,
3419− year : function(d) { return d.getFullYear(); },
3420− month : function(d) { return [monthTable[d.getMonth()]]; },
3421− day : function(d) { return d.getDate(); },
3422− hour : function(d) { return d.getHours(); },
3423− minute : function(d) { return d.getMinutes(); },
3424− second : function(d) { return d.getSeconds(); },
3425− dayOfWeek : function(d) { return [dayTable[d.getDay()]]; },
3426− toTime : function(d) { return d.getTime(); },
3427− Mon : ["Mon"], Tue : ["Tue"], Wed : ["Wed"],
3428− Thu : ["Thu"], Fri : ["Fri"], Sat : ["Sat"], Sun : ["Sun"],
3429− Jan : ["Jan"], Feb : ["Feb"], Mar : ["Mar"], Apr : ["Apr"],
3430− May : ["May"], Jun : ["Jun"], Jul : ["Jul"], Aug : ["Aug"],
3431− Sep : ["Sep"], Oct : ["Oct"], Nov : ["Nov"], Dec : ["Dec"]
3432− };
3433−
3434−}();
3435−function elmRecordCopy(r) {
3436− var o = {};
3437− for (var i in r) { o[i] = r[i]; }
3438− return o;
3439−}
3440−
3441−function elmRecordRemove(x,r) {
3442− var o = elmRecordCopy(r);
3443− if (x in o._) {
3444− o[x] = o._[x][0];
3445− o._[x] = o._[x].slice(1);
3446− if (o._[x].length === 0) { delete o._[x]; }
3447− } else {
3448− delete o[x];
3449− }
3450− return o;
3451−}
3452−
3453−function elmRecordReplace(kvs,r) {
3454− var o = elmRecordCopy(r);
3455− for (var i = kvs.length; i--; ) {
3456− kvsi = kvs[i];
3457− o[kvsi[0]] = kvsi[1];
3458− }
3459− return o;
3460−}
3461−
3462−function elmRecordInsert(x,v,r) {
3463− var o = elmRecordCopy(r);
3464− if (x in o) o._[x] = [o[x]].concat(x in o._ ? o._[x].slice(0) : []);
3465− o[x] = v;
3466− return o;
3467−}
3468−
3469−Value.addListener(document, 'elm_log', function(e) { console.log(e.value); });
3470−Value.addListener(document, 'elm_title', function(e) {document.title = e.value;});
3471−Value.addListener(document, 'elm_redirect', function(e) {
3472− if (e.value.length > 0) { window.location = e.value; }
3473− });
3474−Value.addListener(document, 'elm_viewport', function(e) {
3475− var node = document.getElementById('elm_viewport');
3476− if (!node) {
3477− node = document.createElement('meta');
3478− node.id = 'elm_viewport';
3479− node.name = 'viewport';
3480− document.head.appendChild(node);
3481− }
3482− node.content = e.value;
3483− Dispatcher.notify(Elm.Window.dimensions.id,
3484− Value.Tuple(window.innerWidth, window.innerHeight));
3485− });
3486−
3487−Elm.Prelude = function() {
3488− var mod = function(x) { return function(y) {
3489− var r = x % y;
3490− var m = x==0 ? 0 : (y>0 ? (x>=0 ? r : r+y) : -mod(-x)(-y));
3491− return m == y ? 0 : m;
3492− }; };
3493−
3494− var min = function(x) { return function(y) { return Math.min(x,y); }; };
3495− var max = function(x) { return function(y) { return Math.max(x,y); }; };
3496−
3497− var flip=function(f){return function(x){return function(y){return f(y)(x);};};};
3498− var clamp = function(lo) { return function(hi) {
3499− return function(x) { return Math.min(hi, Math.max(lo, x)); };
3500− };
3501− };
3502− var curry = function(f) { return function(x) { return function(y) {
3503− return f(["Tuple2",x,y]); }; };
3504− };
3505− var uncurry = function(f) { return function(p) {
3506− if (p[0] !== "Tuple2") {
3507− throw new Error("Function was uncurry'd but was not given a pair.");
3508− }
3509− return f(p[1])(p[2]); };
3510− };
3511−
3512− var logBase=function(b){return function(x){return Math.log(x)/Math.log(b);};};
3513−
3514− function readInt(str) {
3515− var s = Elm.JavaScript.castStringToJSString(str);
3516− var len = s.length;
3517− if (len === 0) { return ["Nothing"]; }
3518− var start = 0;
3519− if (s[0] == '-') {
3520− if (len === 1) { return ["Nothing"]; }
3521− start = 1;
3522− }
3523− for (var i = start; i < len; ++i) {
3524− if (!Elm.Char.isDigit(s[i])) { return ["Nothing"]; }
3525− }
3526− return ["Just", parseInt(s)];
3527− }
3528−
3529− function readFloat(str) {
3530− var s = Elm.JavaScript.castStringToJSString(str);
3531− var len = s.length;
3532− if (len === 0) { return ["Nothing"]; }
3533− var start = 0;
3534− if (s[0] == '-') {
3535− if (len === 1) { return ["Nothing"]; }
3536− start = 1;
3537− }
3538− var dotCount = 0;
3539− for (var i = start; i < len; ++i) {
3540− if (Elm.Char.isDigit(s[i])) { continue; }
3541− if (s[i] === '.') {
3542− dotCount += 1;
3543− if (dotCount <= 1) { continue; }
3544− }
3545− return ["Nothing"];
3546− }
3547− return ["Just", parseFloat(s)];
3548− }
3549−
3550− function compare(x) { return function (y) {
3551− if (x instanceof Array && y instanceof Array) {
3552− var len = x.length;
3553− if (len == y.length) {
3554− for (var i = 1; i < len; ++i) {
3555− var cmp = compare(x[i])(y[i]);
3556− if (cmp[0] === 'EQ') continue;
3557− return cmp;
3558− }
3559− return ['EQ'];
3560− }
3561− return [ y.length == 1 ? 'GT' : 'LT' ];
3562− }
3563− return [ x === y ? 'EQ' : (x < y ? 'LT' : 'GT') ];
3564− };
3565− }
3566− return {eq : Value.eq,
3567− id : function(x) { return x; },
3568− not : function(b) { return !b; },
3569− xor : function(x) { return function(y) { return x != y; }; },
3570− fst : function(p) { return p[1]; },
3571− snd : function(p) { return p[2]; },
3572− rem : function(x) { return function(y) { return x % y; }; },
3573− div : function(x) { return function(y) { return ~~(x / y); }; },
3574− otherwise : true,
3575− compare : compare,
3576− toFloat : function(x) { return x; },
3577− round : function(n) { return Math.round(n); },
3578− floor : function(n) { return Math.floor(n); },
3579− ceiling : function(n) { return Math.ceil(n); },
3580− truncate : function(n) { return ~~n; },
3581− readInt : readInt,
3582− readFloat : readFloat,
3583− sqrt : Math.sqrt,
3584− abs : Math.abs,
3585− pi : Math.PI,
3586− e : Math.E,
3587− sin : Math.sin,
3588− cos : Math.cos,
3589− tan : Math.tan,
3590− asin : Math.asin,
3591− acos : Math.acos,
3592− atan : Math.atan,
3593− atan2 : function(y) { return function(x) { return Math.atan2(y,x); }; },
3594− mod : mod,
3595− min : min,
3596− max : max,
3597− flip : flip,
3598− clamp : clamp,
3599− curry : curry,
3600− uncurry : uncurry,
3601− logBase : logBase,
3602− Just : Elm.Maybe.Just,
3603− Nothing : Elm.Maybe.Nothing,
3604− maybe : Elm.Maybe.maybe,
3605− map : Elm.List.map,
3606− zip : Elm.List.zip,
3607− zipWith : Elm.List.zipWith,
3608− filter : Elm.List.filter,
3609− head : Elm.List.head,
3610− tail : Elm.List.tail,
3611− last : Elm.List.last,
3612− length : Elm.List.length,
3613− reverse : Elm.List.reverse,
3614− foldr : Elm.List.foldr,
3615− foldr1 : Elm.List.foldr1,
3616− foldl : Elm.List.foldl,
3617− foldl1 : Elm.List.foldl1,
3618− and : Elm.List.and,
3619− or : Elm.List.or,
3620− all : Elm.List.all,
3621− any : Elm.List.any,
3622− sum : Elm.List.sum,
3623− product : Elm.List.product,
3624− concat : Elm.List.concat,
3625− concatMap : Elm.List.concatMap,
3626− maximum : Elm.List.maximum,
3627− minimum : Elm.List.minimum,
3628− scanl : Elm.List.scanl,
3629− scanl1 : Elm.List.scanl1,
3630− take : Elm.List.take,
3631− drop : Elm.List.drop,
3632− zip : Elm.List.zip,
3633− unzip : Elm.List.unzip,
3634− lift : Elm.Signal.lift,
3635− lift2 : Elm.Signal.lift2,
3636− lift3 : Elm.Signal.lift3,
3637− lift4 : Elm.Signal.lift4,
3638− lift5 : Elm.Signal.lift5,
3639− lift6 : Elm.Signal.lift6,
3640− lift7 : Elm.Signal.lift7,
3641− lift8 : Elm.Signal.lift8,
3642− foldp : Elm.Signal.foldp,
3643− foldp1 : Elm.Signal.foldp1,
3644− foldp$ : Elm.Signal.foldp$,
3645− constant : Elm.Signal.constant,
3646− merge : Elm.Signal.merge,
3647− merges : Elm.Signal.merges,
3648− mergeEither : Elm.Signal.mergeEither,
3649− count : Elm.Signal.count,
3650− countIf : Elm.Signal.countIf,
3651− average : Elm.Signal.average,
3652− keepIf : Elm.Signal.keepIf,
3653− dropIf : Elm.Signal.dropIf,
3654− keepWhen : Elm.Signal.keepWhen,
3655− dropWhen : Elm.Signal.dropWhen,
3656− dropRepeats : Elm.Signal.dropRepeats,
3657− sampleOn : Elm.Signal.sampleOn,
3658− timestamp : Elm.Signal.timestamp,
3659− timeOf : Elm.Signal.timeOf
3660− };
3661−
3662−}();
3663−
3664−(function() {
3665− var include = function(library) {
3666− for (var i in library) {
3667− Elm.Prelude[i] = library[i];
3668− }
3669− };
3670− include (Elm.Color);
3671− include (Elm.Text);
3672− include (Elm.Graphics);
3673− include (Elm.Time);
3674−
3675− show = Value.show;
3676−
3677−}());
3678−/*! Touch
3679−This is an early version of the touch library. It will likely grow to
3680−include gestures that would be useful for both games and web-pages.
3681−!*/
3682−
3683−Elm.Touch = function() {
3684−
3685− function Dict() {
3686− this.keys = [];
3687− this.values = [];
3688−
3689− this.insert = function(key,value) {
3690− this.keys.push(key);
3691− this.values.push(value);
3692− };
3693− this.lookup = function(key) {
3694− var i = this.keys.indexOf(key)
3695− return i >= 0 ? this.values[i] : {x:0,y:0,t:0};
3696− };
3697− this.remove = function(key) {
3698− var i = this.keys.indexOf(key);
3699− if (i < 0) return;
3700− var t = this.values[i];
3701− this.keys.splice(i,1);
3702− this.values.splice(i,1);
3703− return t;
3704− };
3705− }
3706−
3707− var root = Elm.Signal.constant([]),
3708− tapTime = 500,
3709− hasTap = false,
3710− tap = {_:[true],x:[0],y:[0]},
3711− dict = new Dict();
3712−
3713− function touch(t) {
3714− var r = dict.lookup(t.identifier);
3715− return {_ : [true], id: [t.identifier],
3716− x: [t.pageX], y: [t.pageY],
3717− x0: [r.x], y0: [r.y],
3718− t0: [r.t] };
3719− }
3720−
3721− function start(e) {
3722− dict.insert(e.identifier,{x:e.pageX,y:e.pageY,t:Date.now()});
3723− }
3724− function end(e) {
3725− var t = dict.remove(e.identifier);
3726− if (Date.now() - t.t < tapTime) {
3727− hasTap = true;
3728− tap = {_:[true], x:[t.x], y:[t.y]};
3729− }
3730− }
3731−
3732− function listen(name, f) {
3733− function update(e) {
3734− for (var i = e.changedTouches.length; i--; ) { f(e.changedTouches[i]); }
3735− var ts = new Array(e.touches.length);
3736− for (var i = e.touches.length; i--; ) { ts[i] = touch(e.touches[i]); }
3737− var hasListener = Dispatcher.notify(root.id, ts);
3738− if (!hasListener) return document.removeEventListener(name, update);
3739− e.preventDefault();
3740− }
3741− Value.addListener(document, name, update);
3742− }
3743−
3744− listen("touchstart", start);
3745− listen("touchmove", function(_){});
3746− listen("touchend", end);
3747− listen("touchcancel", end);
3748− listen("touchleave", end);
3749−
3750− function dependency(f) {
3751− var sig = Elm.Signal.lift(f)(root);
3752− root.defaultNumberOfKids += 1;
3753− sig.defaultNumberOfKids = 0;
3754− return sig;
3755− }
3756−
3757− /*[Touches]*/
3758−
3759− /** touches : Signal [{ x:Int, y:Int, id:Int, x0:Int, y0:Int, t0:Time }]
3760− A list of touches. Each ongoing touch is represented by a set of
3761− coordinates and an identifier id that allows you to distinguish
3762− between different touches. Each touch also contains the coordinates and
3763− time of the initial contact (x0, y0, and t0) which helps compute more
3764− complicated gestures.
3765− **/
3766− var touches = dependency(function(ts) {
3767− return Elm.JavaScript.castJSArrayToList(ts);
3768− });
3769−
3770− /*[Gestures]*/
3771−
3772− /** taps : Signal { x:Int, y:Int }
3773− The last position that was tapped. Default value is `{x=0,y=0}`.
3774− Updates whenever the user taps the screen.
3775− **/
3776− var taps = function() {
3777− var sig = dependency(function(_) { return tap; });
3778− sig.defaultNumberOfKids = 1;
3779− function pred(_) { var b = hasTap; hasTap = false; return b; }
3780− var sig2 = Elm.Signal.keepIf(pred)({_:[true],x:[0],y:[0]})(sig);
3781− sig2.defaultNumberOfKids = 0;
3782− return sig2;
3783− }();
3784−
3785− return { touches: touches, taps: taps };
3786−}();
3787−Elm.Dict=function(){
3788− var compare = Elm.Prelude.compare;
3789− var uncurry = Elm.Prelude.uncurry;
3790− var Nothing = Elm.Prelude.Nothing;
3791− var Just = Elm.Prelude.Just;
3792− var not = Elm.Prelude.not;
3793− var eq = Elm.Prelude.eq;
3794− var isJust=Elm.Maybe.isJust;
3795− var Red_0=['Red'];
3796− var Black_1=['Black'];
3797− function RBNode_2(a1){
3798− return function(a2){
3799− return function(a3){
3800− return function(a4){
3801− return function(a5){
3802− return ['RBNode',a1,a2,a3,a4,a5];};};};};}
3803− var RBEmpty_3=['RBEmpty'];
3804− function min_6(t_42){
3805− return function(){
3806− switch(t_42[0]){
3807− case 'RBEmpty':
3808− throw '(min RBEmpty) is not defined';
3809− case 'RBNode':
3810− switch(t_42[4][0]){
3811− case 'RBEmpty':
3812− return ['Tuple2',t_42[2],t_42[3]];
3813− }
3814− return min_6(t_42[4]);
3815− }
3816− throw new Error("Non-exhaustive pattern match in case");}();}
3817− function lookup_7(k_46){
3818− return function(t_47){
3819− return function(){
3820− switch(t_47[0]){
3821− case 'RBEmpty':
3822− return Nothing;
3823− case 'RBNode':
3824− return function(){
3825− var case12=compare(k_46)(t_47[2]);
3826− switch(case12[0]){
3827− case 'EQ':
3828− return Just(t_47[3]);
3829− case 'GT':
3830− return lookup_7(k_46)(t_47[5]);
3831− case 'LT':
3832− return lookup_7(k_46)(t_47[4]);
3833− }
3834− throw new Error("Non-exhaustive pattern match in case");}();
3835− }
3836− throw new Error("Non-exhaustive pattern match in case");}();};}
3837− function findWithDefault_8(base_52){
3838− return function(k_53){
3839− return function(t_54){
3840− return function(){
3841− switch(t_54[0]){
3842− case 'RBEmpty':
3843− return base_52;
3844− case 'RBNode':
3845− return function(){
3846− var case19=compare(k_53)(t_54[2]);
3847− switch(case19[0]){
3848− case 'EQ':
3849− return t_54[3];
3850− case 'GT':
3851− return findWithDefault_8(base_52)(k_53)(t_54[5]);
3852− case 'LT':
3853− return findWithDefault_8(base_52)(k_53)(t_54[4]);
3854− }
3855− throw new Error("Non-exhaustive pattern match in case");}();
3856− }
3857− throw new Error("Non-exhaustive pattern match in case");}();};};}
3858− function member_9(k_59){
3859− return function(t_60){
3860− return isJust(lookup_7(k_59)(t_60));};}
3861− function rotateLeft_10(t_61){
3862− return function(){
3863− switch(t_61[0]){
3864− case 'RBNode':
3865− switch(t_61[5][0]){
3866− case 'RBNode':
3867− return RBNode_2(t_61[1])(t_61[5][2])(t_61[5][3])(RBNode_2(Red_0)(t_61[2])(t_61[3])(t_61[4])(t_61[5][4]))(t_61[5][5]);
3868− }break;
3869− }
3870− throw 'rotateLeft of a node without enough children';}();}
3871− function rotateRight_11(t_71){
3872− return function(){
3873− switch(t_71[0]){
3874− case 'RBNode':
3875− switch(t_71[4][0]){
3876− case 'RBNode':
3877− return RBNode_2(t_71[1])(t_71[4][2])(t_71[4][3])(t_71[4][4])(RBNode_2(Red_0)(t_71[2])(t_71[3])(t_71[4][5])(t_71[5]));
3878− }break;
3879− }
3880− throw 'rotateRight of a node without enough children';}();}
3881− function rotateLeftIfNeeded_12(t_81){
3882− return function(){
3883− switch(t_81[0]){
3884− case 'RBNode':
3885− switch(t_81[5][0]){
3886− case 'RBNode':
3887− switch(t_81[5][1][0]){
3888− case 'Red':
3889− return rotateLeft_10(t_81);
3890− }break;
3891− }break;
3892− }
3893− return t_81;}();}
3894− function rotateRightIfNeeded_13(t_82){
3895− return function(){
3896− switch(t_82[0]){
3897− case 'RBNode':
3898− switch(t_82[4][0]){
3899− case 'RBNode':
3900− switch(t_82[4][1][0]){
3901− case 'Red':
3902− switch(t_82[4][4][0]){
3903− case 'RBNode':
3904− switch(t_82[4][4][1][0]){
3905− case 'Red':
3906− return rotateRight_11(t_82);
3907− }break;
3908− }break;
3909− }break;
3910− }break;
3911− }
3912− return t_82;}();}
3913− function otherColor_14(c_83){
3914− return function(){
3915− switch(c_83[0]){
3916− case 'Black':
3917− return Red_0;
3918− case 'Red':
3919− return Black_1;
3920− }
3921− throw new Error("Non-exhaustive pattern match in case");}();}
3922− function color_flip_15(t_84){
3923− return function(){
3924− switch(t_84[0]){
3925− case 'RBNode':
3926− switch(t_84[4][0]){
3927− case 'RBNode':
3928− switch(t_84[5][0]){
3929− case 'RBNode':
3930− return RBNode_2(otherColor_14(t_84[1]))(t_84[2])(t_84[3])(RBNode_2(otherColor_14(t_84[4][1]))(t_84[4][2])(t_84[4][3])(t_84[4][4])(t_84[4][5]))(RBNode_2(otherColor_14(t_84[5][1]))(t_84[5][2])(t_84[5][3])(t_84[5][4])(t_84[5][5]));
3931− }break;
3932− }break;
3933− }
3934− throw 'color_flip called on a RBEmpty or RBNode with a RBEmpty child';}();}
3935− function color_flipIfNeeded_16(t_98){
3936− return function(){
3937− switch(t_98[0]){
3938− case 'RBNode':
3939− switch(t_98[4][0]){
3940− case 'RBNode':
3941− switch(t_98[4][1][0]){
3942− case 'Red':
3943− switch(t_98[5][0]){
3944− case 'RBNode':
3945− switch(t_98[5][1][0]){
3946− case 'Red':
3947− return color_flip_15(t_98);
3948− }break;
3949− }break;
3950− }break;
3951− }break;
3952− }
3953− return t_98;}();}
3954− function fixUp_17(t_99){
3955− return color_flipIfNeeded_16(rotateRightIfNeeded_13(rotateLeftIfNeeded_12(t_99)));}
3956− function ensureBlackRoot_18(t_100){
3957− return function(){
3958− switch(t_100[0]){
3959− case 'RBNode':
3960− switch(t_100[1][0]){
3961− case 'Red':
3962− return RBNode_2(Black_1)(t_100[2])(t_100[3])(t_100[4])(t_100[5]);
3963− }break;
3964− }
3965− return t_100;}();}
3966− function insert_19(k_105){
3967− return function(v_106){
3968− return function(t_107){
3969− return function(){
3970− function ins_108(t_109){
3971− return function(){
3972− switch(t_109[0]){
3973− case 'RBEmpty':
3974− return RBNode_2(Red_0)(k_105)(v_106)(RBEmpty_3)(RBEmpty_3);
3975− case 'RBNode':
3976− return function(){
3977− var h_115=function(){
3978− var case114=compare(k_105)(t_109[2]);
3979− switch(case114[0]){
3980− case 'EQ':
3981− return RBNode_2(t_109[1])(t_109[2])(v_106)(t_109[4])(t_109[5]);
3982− case 'GT':
3983− return RBNode_2(t_109[1])(t_109[2])(t_109[3])(t_109[4])(ins_108(t_109[5]));
3984− case 'LT':
3985− return RBNode_2(t_109[1])(t_109[2])(t_109[3])(ins_108(t_109[4]))(t_109[5]);
3986− }
3987− throw new Error("Non-exhaustive pattern match in case");}();
3988− return fixUp_17(h_115);}();
3989− }
3990− throw new Error("Non-exhaustive pattern match in case");}();}
3991− return ensureBlackRoot_18(ins_108(t_107));}();};};}
3992− function singleton_20(k_116){
3993− return function(v_117){
3994− return insert_19(k_116)(v_117)(RBEmpty_3);};}
3995− function isRed_21(t_118){
3996− return function(){
3997− switch(t_118[0]){
3998− case 'RBNode':
3999− switch(t_118[1][0]){
4000− case 'Red':
4001− return true;
4002− }break;
4003− }
4004− return false;}();}
4005− function isRedLeft_22(t_119){
4006− return function(){
4007− switch(t_119[0]){
4008− case 'RBNode':
4009− switch(t_119[4][0]){
4010− case 'RBNode':
4011− switch(t_119[4][1][0]){
4012− case 'Red':
4013− return true;
4014− }break;
4015− }break;
4016− }
4017− return false;}();}
4018− function isRedLeftLeft_23(t_120){
4019− return function(){
4020− switch(t_120[0]){
4021− case 'RBNode':
4022− switch(t_120[4][0]){
4023− case 'RBNode':
4024− switch(t_120[4][4][0]){
4025− case 'RBNode':
4026− switch(t_120[4][4][1][0]){
4027− case 'Red':
4028− return true;
4029− }break;
4030− }break;
4031− }break;
4032− }
4033− return false;}();}
4034− function isRedRight_24(t_121){
4035− return function(){
4036− switch(t_121[0]){
4037− case 'RBNode':
4038− switch(t_121[5][0]){
4039− case 'RBNode':
4040− switch(t_121[5][1][0]){
4041− case 'Red':
4042− return true;
4043− }break;
4044− }break;
4045− }
4046− return false;}();}
4047− function isRedRightLeft_25(t_122){
4048− return function(){
4049− switch(t_122[0]){
4050− case 'RBNode':
4051− switch(t_122[5][0]){
4052− case 'RBNode':
4053− switch(t_122[5][4][0]){
4054− case 'RBNode':
4055− switch(t_122[5][4][1][0]){
4056− case 'Red':
4057− return true;
4058− }break;
4059− }break;
4060− }break;
4061− }
4062− return false;}();}
4063− function moveRedLeft_26(t_123){
4064− return function(){
4065− var t__124=color_flip_15(t_123);
4066− return function(){
4067− switch(t__124[0]){
4068− case 'RBNode':
4069− return function(){
4070− switch(t__124[5][0]){
4071− case 'RBNode':
4072− switch(t__124[5][4][0]){
4073− case 'RBNode':
4074− switch(t__124[5][4][1][0]){
4075− case 'Red':
4076− return color_flip_15(rotateLeft_10(RBNode_2(t__124[1])(t__124[2])(t__124[3])(t__124[4])(rotateRight_11(t__124[5]))));
4077− }break;
4078− }break;
4079− }
4080− return t__124;}();
4081− }
4082− return t__124;}();}();}
4083− function moveRedRight_27(t_130){
4084− return function(){
4085− var t__131=color_flip_15(t_130);
4086− return (isRedLeftLeft_23(t__131)?color_flip_15(rotateRight_11(t__131)):t__131);}();}
4087− function moveRedLeftIfNeeded_28(t_132){
4088− return ((not(isRedLeft_22(t_132))&&not(isRedLeftLeft_23(t_132)))?moveRedLeft_26(t_132):t_132);}
4089− function moveRedRightIfNeeded_29(t_133){
4090− return ((not(isRedRight_24(t_133))&&not(isRedRightLeft_25(t_133)))?moveRedRight_27(t_133):t_133);}
4091− function deleteMin_30(t_134){
4092− return function(){
4093− function del_135(t_136){
4094− return function(){
4095− switch(t_136[0]){
4096− case 'RBNode':
4097− switch(t_136[4][0]){
4098− case 'RBEmpty':
4099− return RBEmpty_3;
4100− }break;
4101− }
4102− return function(){
4103− var case198=moveRedLeftIfNeeded_28(t_136);
4104− switch(case198[0]){
4105− case 'RBEmpty':
4106− return RBEmpty_3;
4107− case 'RBNode':
4108− return fixUp_17(RBNode_2(case198[1])(case198[2])(case198[3])(del_135(case198[4]))(case198[5]));
4109− }
4110− throw new Error("Non-exhaustive pattern match in case");}();}();}
4111− return ensureBlackRoot_18(del_135(t_134));}();}
4112− function remove_31(k_142){
4113− return function(t_143){
4114− return function(){
4115− function eq_and_noRightNode_144(t_150){
4116− return function(){
4117− switch(t_150[0]){
4118− case 'RBNode':
4119− switch(t_150[5][0]){
4120− case 'RBEmpty':
4121− return eq(k_142,t_150[2]);
4122− }break;
4123− }
4124− return false;}();}
4125− function eq_145(t_152){
4126− return function(){
4127− switch(t_152[0]){
4128− case 'RBNode':
4129− return eq(k_142,t_152[2]);
4130− }
4131− return false;}();}
4132− function delLT_146(t_154){
4133− return function(){
4134− var case216=moveRedLeftIfNeeded_28(t_154);
4135− switch(case216[0]){
4136− case 'RBEmpty':
4137− throw 'delLT on RBEmpty';
4138− case 'RBNode':
4139− return fixUp_17(RBNode_2(case216[1])(case216[2])(case216[3])(del_149(case216[4]))(case216[5]));
4140− }
4141− throw new Error("Non-exhaustive pattern match in case");}();}
4142− function delEQ_147(t_160){
4143− return function(){
4144− switch(t_160[0]){
4145− case 'RBEmpty':
4146− throw 'delEQ called on a RBEmpty';
4147− case 'RBNode':
4148− return function(){
4149− var Tuple2$k_v__164=min_6(t_160[5]);
4150− var k__165=function(){
4151− switch(Tuple2$k_v__164[0]){
4152− case 'Tuple2':
4153− return Tuple2$k_v__164[1];
4154− }
4155− throw new Error("Non-exhaustive pattern match in case");}();
4156− var v__166=function(){
4157− switch(Tuple2$k_v__164[0]){
4158− case 'Tuple2':
4159− return Tuple2$k_v__164[2];
4160− }
4161− throw new Error("Non-exhaustive pattern match in case");}();
4162− return fixUp_17(RBNode_2(t_160[1])(k__165)(v__166)(t_160[4])(deleteMin_30(t_160[5])));}();
4163− }
4164− throw new Error("Non-exhaustive pattern match in case");}();}
4165− function delGT_148(t_171){
4166− return function(){
4167− switch(t_171[0]){
4168− case 'RBEmpty':
4169− throw 'delGT called on a RBEmpty';
4170− case 'RBNode':
4171− return fixUp_17(RBNode_2(t_171[1])(t_171[2])(t_171[3])(t_171[4])(del_149(t_171[5])));
4172− }
4173− throw new Error("Non-exhaustive pattern match in case");}();}
4174− function del_149(t_177){
4175− return function(){
4176− switch(t_177[0]){
4177− case 'RBEmpty':
4178− return RBEmpty_3;
4179− case 'RBNode':
4180− return ((compare(k_142)(t_177[2])[0] === 'LT')?delLT_146(t_177):function(){
4181− var u_179=(isRedLeft_22(t_177)?rotateRight_11(t_177):t_177);
4182− return (eq_and_noRightNode_144(u_179)?u_179[4]:function(){
4183− var t__180=moveRedRightIfNeeded_29(t_177);
4184− return (eq_145(t__180)?delEQ_147(t__180):delGT_148(t__180));}());}());
4185− }
4186− throw new Error("Non-exhaustive pattern match in case");}();}
4187− return (member_9(k_142)(t_143)?ensureBlackRoot_18(del_149(t_143)):t_143);}();};}
4188− function map_32(f_181){
4189− return function(t_182){
4190− return function(){
4191− switch(t_182[0]){
4192− case 'RBEmpty':
4193− return RBEmpty_3;
4194− case 'RBNode':
4195− return RBNode_2(t_182[1])(t_182[2])(f_181(t_182[3]))(map_32(f_181)(t_182[4]))(map_32(f_181)(t_182[5]));
4196− }
4197− throw new Error("Non-exhaustive pattern match in case");}();};}
4198− function foldl_33(f_188){
4199− return function(acc_189){
4200− return function(t_190){
4201− return function(){
4202− switch(t_190[0]){
4203− case 'RBEmpty':
4204− return acc_189;
4205− case 'RBNode':
4206− return foldl_33(f_188)(f_188(t_190[2])(t_190[3])(foldl_33(f_188)(acc_189)(t_190[4])))(t_190[5]);
4207− }
4208− throw new Error("Non-exhaustive pattern match in case");}();};};}
4209− function foldr_34(f_195){
4210− return function(acc_196){
4211− return function(t_197){
4212− return function(){
4213− switch(t_197[0]){
4214− case 'RBEmpty':
4215− return acc_196;
4216− case 'RBNode':
4217− return foldr_34(f_195)(f_195(t_197[2])(t_197[3])(foldr_34(f_195)(acc_196)(t_197[5])))(t_197[4]);
4218− }
4219− throw new Error("Non-exhaustive pattern match in case");}();};};}
4220− function union_35(t1_202){
4221− return function(t2_203){
4222− return foldl_33(insert_19)(t2_203)(t1_202);};}
4223− function intersect_36(t1_204){
4224− return function(t2_205){
4225− return foldl_33(function(k_206){
4226− return function(v_207){
4227− return function(t_208){
4228− return (member_9(k_206)(t2_205)?insert_19(k_206)(v_207)(t_208):t_208);};};})(empty_4)(t1_204);};}
4229− function diff_37(t1_209){
4230− return function(t2_210){
4231− return foldl_33(function(k_211){
4232− return function(v_212){
4233− return function(t_213){
4234− return remove_31(k_211)(t_213);};};})(t1_209)(t2_210);};}
4235− function keys_38(t_214){
4236− return foldr_34(function(k_215){
4237− return function(v_216){
4238− return function(acc_217){
4239− return ['Cons',k_215,acc_217];};};})(['Nil'])(t_214);}
4240− function values_39(t_218){
4241− return foldr_34(function(k_219){
4242− return function(v_220){
4243− return function(acc_221){
4244− return ['Cons',v_220,acc_221];};};})(['Nil'])(t_218);}
4245− function toList_40(t_222){
4246− return foldr_34(function(k_223){
4247− return function(v_224){
4248− return function(acc_225){
4249− return ['Cons',['Tuple2',k_223,v_224],acc_225];};};})(['Nil'])(t_222);}
4250− function fromList_41(assocs_226){
4251− return Elm.List.foldl(uncurry(insert_19))(empty_4)(assocs_226);}
4252− var empty_4=RBEmpty_3;
4253− return {$op : {},
4254− empty:empty_4,
4255− lookup:lookup_7,
4256− findWithDefault:findWithDefault_8,
4257− member:member_9,
4258− insert:insert_19,
4259− singleton:singleton_20,
4260− remove:remove_31,
4261− map:map_32,
4262− foldl:foldl_33,
4263− foldr:foldr_34,
4264− union:union_35,
4265− intersect:intersect_36,
4266− diff:diff_37,
4267− keys:keys_38,
4268− values:values_39,
4269− toList:toList_40,
4270− fromList:fromList_41};}();
4271−
4272−Elm.Set=function(){
4273− var empty_0=Elm.Dict.empty;
4274− var remove_3=Elm.Dict.remove;
4275− var member_4=Elm.Dict.member;
4276− var union_5=Elm.Dict.union;
4277− var intersect_6=Elm.Dict.intersect;
4278− var diff_7=Elm.Dict.diff;
4279− var toList_8=Elm.Dict.keys;
4280− var fromList_9=Elm.List.foldl(function(k_15){
4281− return function(t_16){
4282− return Elm.Dict.insert(k_15)(["Tuple0"])(t_16);};})(empty_0);
4283− function singleton_1(k_13){
4284− return Elm.Dict.singleton(k_13)(["Tuple0"]);};
4285− function insert_2(k_14){
4286− return Elm.Dict.insert(k_14)(["Tuple0"]);};
4287− function foldl_10(f_17){
4288− return Elm.Dict.foldl(function(k_18){
4289− return function(v_19){
4290− return function(b_20){
4291− return f_17(k_18)(b_20);};};});};
4292− function foldr_11(f_21){
4293− return Elm.Dict.foldr(function(k_22){
4294− return function(v_23){
4295− return function(b_24){
4296− return f_21(k_22)(b_24);};};});};
4297− function map_12(f_25){
4298− return function(t_26){
4299− return function(x){
4300− return fromList_9(Elm.List.map(f_25)(x));}(toList_8(t_26));};};
4301− return {empty:empty_0,singleton:singleton_1,insert:insert_2,remove:remove_3,member:member_4,union:union_5,intersect:intersect_6,diff:diff_7,toList:toList_8,fromList:fromList_9,foldl:foldl_10,foldr:foldr_11,map:map_12};}();
4302−
4303−(function() {
4304−try{
4305−
4306−var $op={};
4307−for(this['i'] in Elm){eval('var '+this['i']+'=Elm[this.i];');}
4308−if (Elm.Automaton) throw new Error("Module name collision, 'Automaton' is already defined.");
4309−Elm.Automaton=function(){
4310− try{
4311− if (!(Elm.Prelude instanceof Object)) throw 'module not found';
4312− } catch(e) {
4313− throw ("Module 'Prelude' is missing. Compile with --make flag or load missing module in a separate JavaScript file.");
4314− }
4315− var hiddenVars={};
4316− for (this['i'] in Elm.Prelude) {
4317− if (hiddenVars[this['i']]) continue;
4318− eval('var ' + this['i'] + ' = Elm.Prelude[this.i];');}
4319− function Automaton_0(a1){
4320− return ["Automaton",a1];}
4321− var Listen_8=["Listen"];
4322− var Ignore_9=["Ignore"];
4323− function DragFrom_10(a1){
4324− return ["DragFrom",a1];}
4325− $op['>>>'] = function(a1_24){
4326− return function(a2_25){
4327− return function(){
4328− var Automaton$m1_26=a1_24;
4329− var m1_27=function(){
4330− switch(Automaton$m1_26[0]){
4331− case "Automaton":
4332− return Automaton$m1_26[1];
4333− }
4334− throw new Error("Non-exhaustive pattern match in case");}();
4335− var Automaton$m2_28=a2_25;
4336− var m2_29=function(){
4337− switch(Automaton$m2_28[0]){
4338− case "Automaton":
4339− return Automaton$m2_28[1];
4340− }
4341− throw new Error("Non-exhaustive pattern match in case");}();
4342− return Automaton_0(function(a_32){
4343− return function(){
4344− var Tuple2$bm1__33=m1_27(a_32);
4345− var b_34=function(){
4346− switch(Tuple2$bm1__33[0]){
4347− case "Tuple2":
4348− return Tuple2$bm1__33[1];
4349− }
4350− throw new Error("Non-exhaustive pattern match in case");}();
4351− var m1__35=function(){
4352− switch(Tuple2$bm1__33[0]){
4353− case "Tuple2":
4354− return Tuple2$bm1__33[2];
4355− }
4356− throw new Error("Non-exhaustive pattern match in case");}();
4357− return function(){
4358− var Tuple2$cm2__40=m2_29(b_34);
4359− var c_41=function(){
4360− switch(Tuple2$cm2__40[0]){
4361− case "Tuple2":
4362− return Tuple2$cm2__40[1];
4363− }
4364− throw new Error("Non-exhaustive pattern match in case");}();
4365− var m2__42=function(){
4366− switch(Tuple2$cm2__40[0]){
4367− case "Tuple2":
4368− return Tuple2$cm2__40[2];
4369− }
4370− throw new Error("Non-exhaustive pattern match in case");}();
4371− return ["Tuple2",c_41,$op['>>>'](m1__35)(m2__42)];}();}();});}();};};
4372− $op['<<<'] = function(a2_47){
4373− return function(a1_48){
4374− return $op['>>>'](a1_48)(a2_47);};};
4375− $op['^>>'] = function(f_49){
4376− return function(a_50){
4377− return $op['>>>'](pure_4(f_49))(a_50);};};
4378− $op['>>^'] = function(a_51){
4379− return function(f_52){
4380− return $op['>>>'](a_51)(pure_4(f_52));};};
4381− $op['^<<'] = function(f_53){
4382− return function(a_54){
4383− return $op['>>>'](a_54)(pure_4(f_53));};};
4384− $op['<<^'] = function(a_55){
4385− return function(f_56){
4386− return $op['>>>'](pure_4(f_56))(a_55);};};
4387− var count_7=init_5(0)(function(__84){
4388− return function(c_85){
4389− return (1+c_85);};});
4390− function run_1(Automaton$m0_14){
4391− return function(input_15){
4392− return function(){
4393− switch(Automaton$m0_14[0]){
4394− case "Automaton":
4395− return lift(fst)(foldp$(function(a_17){
4396− return function(Tuple2$bAutomaton$m_18){
4397− return function(){
4398− switch(Tuple2$bAutomaton$m_18[0]){
4399− case "Tuple2":
4400− switch(Tuple2$bAutomaton$m_18[2][0]){
4401− case "Automaton":
4402− return Tuple2$bAutomaton$m_18[2][1](a_17);
4403− }break;
4404− }
4405− throw new Error("Non-exhaustive pattern match in case");}();};})(Automaton$m0_14[1])(input_15));
4406− }
4407− throw new Error("Non-exhaustive pattern match in case");}();};}
4408− function step_2(Automaton$m_21){
4409− return function(a_22){
4410− return function(){
4411− switch(Automaton$m_21[0]){
4412− case "Automaton":
4413− return Automaton$m_21[1](a_22);
4414− }
4415− throw new Error("Non-exhaustive pattern match in case");}();};}
4416− function combine_3(autos_57){
4417− return Automaton_0(function(a_58){
4418− return function(){
4419− var Tuple2$bsautos__59=unzip(map(function(Automaton$m_62){
4420− return function(){
4421− switch(Automaton$m_62[0]){
4422− case "Automaton":
4423− return Automaton$m_62[1](a_58);
4424− }
4425− throw new Error("Non-exhaustive pattern match in case");}();})(autos_57));
4426− var bs_60=function(){
4427− switch(Tuple2$bsautos__59[0]){
4428− case "Tuple2":
4429− return Tuple2$bsautos__59[1];
4430− }
4431− throw new Error("Non-exhaustive pattern match in case");}();
4432− var autos__61=function(){
4433− switch(Tuple2$bsautos__59[0]){
4434− case "Tuple2":
4435− return Tuple2$bsautos__59[2];
4436− }
4437− throw new Error("Non-exhaustive pattern match in case");}();
4438− return ["Tuple2",bs_60,combine_3(autos__61)];}();});}
4439− function pure_4(f_68){
4440− return Automaton_0(function(x_69){
4441− return ["Tuple2",f_68(x_69),pure_4(f_68)];});}
4442− function init_5(s_70){
4443− return function(step_71){
4444− return Automaton_0(function(a_72){
4445− return function(){
4446− var s__73=step_71(a_72)(s_70);
4447− return ["Tuple2",s__73,init_5(s__73)(step_71)];}();});};}
4448− function init__6(s_74){
4449− return function(step_75){
4450− return Automaton_0(function(a_76){
4451− return function(){
4452− var Tuple2$bs__77=step_75(a_76)(s_74);
4453− var b_78=function(){
4454− switch(Tuple2$bs__77[0]){
4455− case "Tuple2":
4456− return Tuple2$bs__77[1];
4457− }
4458− throw new Error("Non-exhaustive pattern match in case");}();
4459− var s__79=function(){
4460− switch(Tuple2$bs__77[0]){
4461− case "Tuple2":
4462− return Tuple2$bs__77[2];
4463− }
4464− throw new Error("Non-exhaustive pattern match in case");}();
4465− return ["Tuple2",b_78,init__6(s__79)(step_75)];}();});};}
4466− function vecSub_11(Tuple2$x1y1_86){
4467− return function(Tuple2$x2y2_87){
4468− return function(){
4469− switch(Tuple2$x1y1_86[0]){
4470− case "Tuple2":
4471− return function(){
4472− switch(Tuple2$x2y2_87[0]){
4473− case "Tuple2":
4474− return ["Tuple2",(Tuple2$x1y1_86[1]-Tuple2$x2y2_87[1]),(Tuple2$x1y1_86[2]-Tuple2$x2y2_87[2])];
4475− }
4476− throw new Error("Non-exhaustive pattern match in case");}();
4477− }
4478− throw new Error("Non-exhaustive pattern match in case");}();};}
4479− function stepDrag_12(Tuple2$presspos_92){
4480− return function(Tuple2$dsform_93){
4481− return function(){
4482− switch(Tuple2$presspos_92[0]){
4483− case "Tuple2":
4484− return function(){
4485− switch(Tuple2$dsform_93[0]){
4486− case "Tuple2":
4487− return function(){
4488− function wrap_98(ds__99){
4489− return ["Tuple2",Tuple2$dsform_93[2],["Tuple2",ds__99,Tuple2$dsform_93[2]]];}
4490− return function(){
4491− switch(Tuple2$dsform_93[1][0]){
4492− case "DragFrom":
4493− return (Tuple2$presspos_92[1]?["Tuple2",uncurry(move)(vecSub_11(Tuple2$presspos_92[2])(Tuple2$dsform_93[1][1]))(Tuple2$dsform_93[2]),["Tuple2",DragFrom_10(Tuple2$dsform_93[1][1]),Tuple2$dsform_93[2]]]:function(){
4494− var form__101=uncurry(move)(vecSub_11(Tuple2$presspos_92[2])(Tuple2$dsform_93[1][1]))(Tuple2$dsform_93[2]);
4495− return ["Tuple2",form__101,["Tuple2",Listen_8,form__101]];}());
4496− case "Ignore":
4497− return wrap_98((Tuple2$presspos_92[1]?Ignore_9:Listen_8));
4498− case "Listen":
4499− return wrap_98((not(Tuple2$presspos_92[1])?Listen_8:(isWithin(Tuple2$presspos_92[2])(Tuple2$dsform_93[2])?DragFrom_10(Tuple2$presspos_92[2]):Ignore_9)));
4500− }
4501− throw new Error("Non-exhaustive pattern match in case");}();}();
4502− }
4503− throw new Error("Non-exhaustive pattern match in case");}();
4504− }
4505− throw new Error("Non-exhaustive pattern match in case");}();};}
4506− function draggable_13(form_102){
4507− return init__6(["Tuple2",Listen_8,form_102])(stepDrag_12);}
4508− return {$op : {'>>>' : $op['>>>'], '<<<' : $op['<<<'], '^>>' : $op['^>>'], '>>^' : $op['>>^'], '^<<' : $op['^<<'], '<<^' : $op['<<^']},
4509− run:run_1,
4510− step:step_2,
4511− combine:combine_3,
4512− pure:pure_4,
4513− init:init_5,
4514− init$:init__6,
4515− count:count_7,
4516− draggable:draggable_13};}();
4517−Elm.main=function(){
4518− return Elm.Automaton.main;};
4519−} catch (e) {
4520−Elm.main=function() {
4521−var msg = ('<br/><h2>Your browser may not be supported. Are you using a modern browser?</h2>' + '<br/><span style="color:grey">Runtime Error in Automaton module:<br/>' + e + '</span>');
4522−document.body.innerHTML = Elm.Text.monospace(msg);throw e;};}}());
elm/elm-runtime-0.7.jsdeleted−135
@@ -1,135 +0,0 @@
1−Elm={};var Guid=function(){var e=0;return{guid:function(){return e+=1}}}();
2−Elm.JavaScript=function(){function e(b){for(var a=["Nil"],m=b.length;m--;)a=["Cons",b[m],a];return a}function k(b){for(var a=[];"Cons"===b[0];)a.push(b[1]),b=b[2];return a}function b(b){return b.slice(1)}function d(b){return["Tuple"+b.length].concat(b)}return{castJSBoolToBool:function(b){return b},castBoolToJSBool:function(b){return b},castJSNumberToFloat:function(b){return b},castFloatToJSNumber:function(b){return b},castJSNumberToInt:function(b){return~~b},castIntToJSNumber:function(b){return b},
3−Experimental:{castJSElementToElement:function(b){return function(a){return function(m){return["Element",Guid.guid(),["EExternalHtml",m],b,a,1,["Nothing"],["Nothing"]]}}},castElementToJSElement:function(b){return Render.render(b)}},castJSArrayToList:e,castListToJSArray:k,castJSStringToString:e,castStringToJSString:function(b){return"string"===typeof b?b:k(b).join("")},castTupleToJSTuple2:b,castTupleToJSTuple3:b,castTupleToJSTuple4:b,castTupleToJSTuple5:b,castJSTupleToTuple2:d,castJSTupleToTuple3:d,
4−castJSTupleToTuple4:d,castJSTupleToTuple5:d}}();var JSjson=window.JSON;
5−Elm.JSON=function(){function e(a,b){return function(g){return function(l){var h=d.castStringToJSString(g);return l[1].hasOwnProperty(h)&&(l=l[1][h],l[0]===a)?l[1]:b}}}function k(a){return function(b){function g(a){switch(a[0]){case "JsonNull":return null;case "JsonString":return d.castStringToJSString(a[1]);case "JsonObject":var h={};a=a[1][1];for(var c in a)h[c]=g(a[c]);return h;case "JsonArray":h=d.castListToJSArray(a[1]);for(c=h.length;c--;)h[c]=g(h[c]);return h;default:return a[1]}}return JSjson.stringify(g(["JsonObject",
6−b]),null,d.castStringToJSString(a))}}function b(a){function b(a){switch(typeof a){case "string":return["JsonString",d.castJSStringToString(a)];case "number":return["JsonNumber",d.castJSNumberToFloat(a)];case "boolean":return["JsonBool",d.castJSBoolToBool(a)];case "object":if(null===a)return["JsonNull"];for(var h in a)a[h]=b(a[h]);return a instanceof Array?["JsonArray",d.castJSArrayToList(a)]:["JsonObject",["JSON",a]]}}a=JSjson.parse(a);for(var g in a)a[g]=b(a[g]);return["JSON",a]}var d=Elm.JavaScript,
7−j=["JSON",{}];return{empty:j,singleton:function(a){return function(b){var g={};g[d.castStringToJSString(a)]=b;return["JSON",g]}},insert:function(a){return function(b){return function(g){g=g[1];var l={},h;for(h in g)l[h]=g[h];l[d.castStringToJSString(a)]=b;return["JSON",l]}}},lookup:function(a){return function(b){var g=d.castStringToJSString(a);return b[1].hasOwnProperty(g)?["Just",b[1][g]]:["Nothing"]}},findString:e("JsonString",["Nil"]),findObject:e("JsonObject",j),findArray:e("JsonArray",["Nil"]),
8−findWithDefault:function(a){return function(b){return function(g){var l=d.castStringToJSString(b);return g[1].hasOwnProperty(l)?g[1][l]:a}}},remove:function(a){return function(b){b=b[1];var g={},l;for(l in b)g[l]=b[l];delete g[d.castStringToJSString(a)];return["JSON",g]}},toPrettyJSString:k,toJSString:k(""),fromJSString:b,toPrettyString:function(a){return function(b){return d.castJSStringToString(k(a)(b))}},toString:function(a){return d.castJSStringToString(k("")(a))},fromString:function(a){return b(d.castStringToJSString(a))},
9−toList:function(a){a=a[1];var b=[],g;for(g in a)b.push(Value.Tuple(d.castJSStringToString(g),a[g]));return d.castJSArrayToList(b)},fromList:function(a){a=d.castListToJSArray(a);for(var b={},g=a.length;g--;)b[d.castStringToJSString(a[g][1])]=a[g][2];return["JSON",b]},JsonString:function(a){return["JsonString",a]},JsonNumber:function(a){return["JsonNumber",a]},JsonBool:function(a){return["JsonBool",a]},JsonNull:["JsonNull"],JsonArray:function(a){return["JsonArray",a]},JsonObject:function(a){return["JsonObject",
10−a]}}}();
11−var Value=function(){function e(a){if(0==a.length)return a;a=a.replace(/"/g,"&#34;").replace(/'/g,"&#39;").replace(/</g,"&#60;").replace(/>/g,"&#62;").replace(/\n/g,"<br/>");a=a.split("<br/>");for(var b=a.length;b--;){var g=a,d=b,h;h=a[b];if(0!=h.length){h=h.split("");" "==h[0]&&(h[0]="&nbsp;");for(var c=h.length;--c;)" "==h[c][0]&&" "==h[c-1]&&(h[c-1]+=h[c],h[c]="");for(c=h.length;c--;)if(1<h[c].length&&" "==h[c][0]){for(var f=h[c].split(""),v=f.length-2;0<=v;v-=2)f[v]="&nbsp;";h[c]=f.join("")}h=h.join("");
12−h=" "===h[h.length-1]?h.slice(0,-1)+"&nbsp;":h}g[d]=h}return a.join("<br/>")}var k=function(a,b){if("object"===typeof a){if(a.hasOwnProperty("_")){for(var g in a)if(a[g]!=b[g])return!1;for(g in b)if(a[g]!=b[g])return!1;return!0}if(a===b)return!0;if(a.length!==b.length)return!1;for(g=a.length;g--;)if(!k(a[g],b[g]))return!1;return!0}return a===b},b=function(a){if("function"===typeof a)return"<function>";if("boolean"===typeof a)return a?"True":"False";if("number"!==typeof a){if("string"===typeof a&&
13−2>a.length)return"'"+a+"'";if("object"===typeof a&&a.hasOwnProperty("_")){var d=[],g;for(g in a)if("_"!=g)for(var l=a[g].length;l--;)d.push(g+" = "+b(a[g][l]));return 0===d.length?"{}":"{ "+d.join(", ")+" }"}if(a[0]){if("Tuple"===a[0].substring(0,5)){d=Array(a.length-1);for(l=a.length;--l;)d[l-1]=b(a[l]);return"("+d.join(",")+")"}if("Cons"===a[0]){g="string"===typeof a[1]?'"':"]";var l="string"===typeof a[1]?"":",",h="string"===typeof a[1]?function(a){return a}:b,d=("string"===typeof a[1]?'"':"[")+
14−h(a[1]);for(a=a[2];;)if("Cons"===a[0])d+=l+h(a[1]),a=a[2];else return d+g}else{if("Nil"===a[0])return"[]";if("JSON"===a[0])return"(JSON.fromList "+b(Elm.JSON.toList(a))+")";if("RBNode"===a[0]||"RBEmpty"===a[0])return a=Elm.Dict.foldr(function(a){return function(b){return function(h){return["Cons",["Tuple2",a,b],h]}}})(["Nil"])(a),d="Dict","Cons"===a[0]&&"Tuple0"===a[1][2][0]&&(d="Set",a=Elm.List.map(function(a){return a[1]})(a)),"("+d+".fromList "+b(a)+")";d=[];for(l=a.length;--l;)d.push(b(a[l]));
15−d=a[0]+" "+d.join(" ");return 1<a.length?"("+d+")":d}}}return a+""},d=function(a){for(var b=["Nil"],d=a.length;d--;)b=["Cons",a[d],b];return b},j;j=document.addEventListener?function(a,b,d){a.addEventListener(b,d,!1)}:function(a,b,d){a.attachEvent("on"+b,d)};return{eq:k,str:d,show:function(a){return d(b(a))},Tuple:function(){var a=arguments.length,b=Array(a+1);for(b[0]="Tuple"+arguments.length;a--;)b[a+1]=arguments[a];return b},append:function(a,b){if("string"===typeof a&&"string"===typeof b)return a.concat(b);
16−if("Nil"===a[0])return b;var d=["Cons",a[1],["Nil"]],l=d;for(a=a[2];"Cons"===a[0];)l[2]=["Cons",a[1],["Nil"]],a=a[2],l=l[2];l[2]=b;return d},listToArray:function(a){for(var b=[];"Cons"===a[0];)b.push(a[1]),a=a[2];return b},toText:function(a){if("string"===typeof a)return e(a);for(var b=[];"Cons"===a[0];)b.push(a[1]),a=a[2];return e(b.join(""))},properEscape:e,getTextSize:function(a,b,d){var l=document.createElement("div");l.innerHTML=d;l.style.textAlign="left";0<a&&(l.style.width=a+"px");l.style.visibility=
17−"hidden";l.style.styleFloat="left";l.style.cssFloat="left";document.body.appendChild(l);d=window.getComputedStyle(l,null);a=d.getPropertyValue("width").slice(0,-2)-0;d=d.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(l);return[Math.ceil(a),Math.ceil(Math.max(b,d))]},getSize:function(a){a=a.cloneNode(!0);a.style.visibility="hidden";a.style.styleFloat="left";a.style.cssFloat="left";document.body.appendChild(a);var b=a.offsetWidth,d=a.offsetHeight;document.body.removeChild(a);return[b,
18−d]},getExcess:function(b){b=b.cloneNode(!0);b.style.visibility="hidden";b.style.styleFloat="left";b.style.cssFloat="left";document.body.appendChild(b);var d=b.offsetWidth,g=b.offsetHeight,l=window.getComputedStyle(b,null),h=l.getPropertyValue("width").slice(0,-2)-0,l=l.getPropertyValue("height").slice(0,-2)-0;document.body.removeChild(b);return[d-h,g-l]},groupForms:function(b){b=Elm.JavaScript.castListToJSArray(b);for(var d=[],g=[],l=b.length;l--;){var h=b[l];switch(h[4][0]){case "FElement":0<g.length&&
19−(d.push(g),g=[]);d.push(h);break;default:g.push(h)}}0<g.length&&d.push(g);return d},wrap:function(b){var d=Value.getSize(b);return["Element",Guid.guid(),["EHtml",b],d[0],d[1],1,["Nothing"],["Nothing"]]},addListener:j}}();
20−Elm.List=function(){function e(b){return function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&h("map");var c=["Cons",b(a[1]),["Nil"]],f=c;for(a=a[2];"Cons"===a[0];)f[2]=["Cons",b(a[1]),["Nil"]],a=a[2],f=f[2];return c}}function k(b){return function(a){return function(c){var f=a;if("Nil"===c[0])return f;for("Cons"!==c[0]&&h("foldl");"Cons"===c[0];)f=b(c[1])(f),c=c[2];return f}}}function b(b){return function(a){return function(c){var f=a;if("Nil"===c[0])return f;"Cons"!==c[0]&&h("foldr");for(var d=[];"Cons"===
21−c[0];)d.push(c[1]),c=c[2];for(c=d.length;c--;)f=b(d[c])(f);return f}}}function d(b){return function(a){var h;"Cons"!==a[0]?h=void 0:(h=a[1],a=a[2],h=k(b)(h)(a));return h}}function j(b){return function(a){return function(c){if("Nil"===c[0])return["Cons",a,["Nil"]];"Cons"!==c[0]&&h("scanl");for(var f=[a];"Cons"===c[0];)a=b(c[1])(a),f.push(a),c=c[2];c=["Nil"];for(var d=f.length;d--;)c=["Cons",f[d],c];return c}}}function a(b){return function(h){a:{for(var c=[function(b){return"Nil"!==b[0]?void 0:["Tuple2",
22−["Nil"],["Nil"]]},function(h){if("Cons"===h[0]){var c=h[1];h=h[2];var f=a(b)(h);"Tuple2"!==f[0]?c=void 0:(h=f[1],f=f[2],c=b(c)?["Tuple2",["Cons",c,h],f]:["Tuple2",h,["Cons",c,f]]);return c}}],f=c.length;f--;){var d=c[f](h);if(void 0!==d){h=d;break a}}h=void 0}return h}}function m(b){a:{for(var a=[function(b){return"Nil"!==b[0]?void 0:["Tuple2",["Nil"],["Nil"]]},function(b){if("Cons"!==b[0])b=void 0;else if(b=["Tuple2",b[1],m(b[2])],"Tuple2"!==b[0]||"Tuple2"!==b[1][0])b=void 0;else{var a=b[1][1],h=
23−b[1][2];b="Tuple2"!==b[2][0]?void 0:["Tuple2",["Cons",a,b[2][1]],["Cons",h,b[2][2]]]}return b}],h=a.length;h--;){var c=a[h](b);if(void 0!==c){b=c;break a}}b=void 0}return b}function g(b){return function(a){a:{for(var h=[function(b){return"Nil"!==b[0]?void 0:["Nil"]},function(b){if("Cons"===b[0]){var a=b[1];return"Nil"!==b[2][0]?void 0:["Cons",a,["Nil"]]}},function(a){if("Cons"===a[0]){var h=a[1];if("Cons"===a[2][0]){var c=a[2][1];a=a[2][2];return["Cons",h,["Cons",b,g(b)(["Cons",c,a])]]}}}],c=h.length;c--;){var f=
24−h[c](a);if(void 0!==f){a=f;break a}}a=void 0}return a}}function l(b){return function(a){a:{for(var h=[function(b){return"Nil"!==b[0]?void 0:["Nil"]},function(b){if("Cons"===b[0]){var a=b[1];return"Nil"!==b[2][0]?void 0:a}},function(a){if("Cons"===a[0]){var h=a[1];if("Cons"===a[2][0]){var c=a[2][1];a=a[2][2];return Value.append(h,Value.append(b,l(b)(["Cons",c,a])))}}}],c=h.length;c--;){var f=h[c](a);if(void 0!==f){a=f;break a}}a=void 0}return a}}var h=function(b){throw"Function '"+b+"' expecting a list!";
25−},c=k(function(b){return function(a){return["Cons",b,a]}})(["Nil"]),f=b(function(b){return function(a){return Value.append(b,a)}})(["Nil"]),v=k(function(b){return function(a){return b&&a}})(!0),n=k(function(b){return function(a){return b||a}})(!1),p=k(function(b){return function(a){return b+a}})(0),r=k(function(b){return function(a){return b*a}})(1),y=d(function(b){return function(a){return Math.max(b,a)}}),s=d(function(b){return function(a){return Math.min(b,a)}});return{head:function(b){if("Cons"!==
26−b[0])throw"Error: 'head' only accepts lists of length greater than one.";return b[1]},tail:function(b){if("Cons"!==b[0])throw"Error: 'tail' only accepts lists of length greater than one.";return b[2]},last:function(b){if("Cons"!==b[0])throw"Error: 'last' only accepts lists of length greater than one.";for(var a=b[1];"Cons"===b[0];)a=b[1],b=b[2];return a},map:e,foldl:k,foldr:b,foldl1:d,foldr1:function(b){return function(a){if("Nil"===a[0])throw"'foldr1' requires an non-empty list.";"Cons"!==a[0]&&
27−h("foldr1");for(var c=[];"Cons"===a[0];)c.push(a[1]),a=a[2];a=c.pop();for(var f=c.length;f--;)a=b(c[f])(a);return a}},scanl:j,scanl1:function(b){return function(a){if("Cons"!==a[0])throw"Error: 'scanl1' requires a list of at least length 1.";return j(b)(a[1])(a[2])}},filter:function(b){return function(a){if("Nil"===a[0])return a;"Cons"!==a[0]&&h("filter");for(var c=[];"Cons"===a[0];)b(a[1])&&c.push(a[1]),a=a[2];a=["Nil"];for(var f=c.length;f--;)a=["Cons",c[f],a];return a}},length:function(b){for(var a=
28−0;"Cons"===b[0];)a+=1,b=b[2];return a},reverse:c,concat:f,concatMap:function(b){return function(a){return f(e(b)(a))}},and:v,or:n,all:function(b){return k(function(a){return function(h){return h&&b(a)}})(!0)},any:function(b){return k(function(a){return function(h){return h||b(a)}})(!1)},sum:p,product:r,maximum:y,minimum:s,partition:a,zipWith:function(b){return function(a){return function(c){if("Nil"===a[0]||"Nil"===c[0])return["Nil"];("Cons"!==a[0]||"Cons"!==c[0])&&h("zipWith");for(var f=[];"Cons"===
29−a[0]&&"Cons"===c[0];)f.push(b(a[1])(c[1])),a=a[2],c=c[2];c=["Nil"];for(var d=f.length;d--;)c=["Cons",f[d],c];return c}}},zip:function(b){return function(a){if("Nil"===b[0]||"Nil"===a[0])return["Nil"];("Cons"!==b[0]||"Cons"!==a[0])&&h("zip");for(var c=[];"Cons"===b[0]&&"Cons"===a[0];)c.push(["Tuple2",b[1],a[1]]),b=b[2],a=a[2];a=["Nil"];for(var f=c.length;f--;)a=["Cons",c[f],a];return a}},unzip:m,intersperse:g,intercalate:l,sort:function(b){if("Nil"===b[0])return b;"Cons"!==b[0]&&h("sort");for(var a=
30−[];"Cons"===b[0];)a.push(b[1]),b=b[2];a.sort(function(b,a){return b-a});b=["Nil"];for(var c=a.length;c--;)b=["Cons",a[c],b];return b},take:function(b){return function(a){if(0>=b)return["Nil"];if("Nil"===a[0])return a;"Cons"!==a[0]&&h("take");var c=["Cons",a[1],["Nil"]],f=c;a=a[2];for(--b;"Cons"===a[0]&&0<b;)f[2]=["Cons",a[1],["Nil"]],f=f[2],a=a[2],--b;return c}},drop:function(b){return function(a){if("Nil"===a[0])return a;for("Cons"!==a[0]&&h("drop");"Cons"===a[0]&&0<b;)a=a[2],--b;return a}}}}();
31−Elm.Maybe=function(){function e(b){return function(d){return"Just"===b[0]?["Cons",b[1],d]:d}}function k(b){return function(d){return function(j){var a=b(d);return"Just"===a[0]?["Cons",a[1],j]:j}}}return{Just:function(b){return["Just",b]},Nothing:["Nothing"],catMaybes:Elm.List.foldr(e)(["Nil"]),isJust:function(b){return"Just"===b[0]},isNothing:function(b){return"Nothing"===b[0]},fromMaybe:function(b){return function(d){return"Just"===d[0]?d[1]:b}},consMaybe:e,mapMaybe:function(b){return Elm.List.foldr(k(b))(["Nil"])},
32−maybe:function(b){return function(d){return function(j){return"Just"===j[0]?d(j[1]):b}}}}}();
33−Elm.Char=function(){function e(b,a){return function(d){d=d.charCodeAt(0);return b<=d&&d<=a}}var k=e(48,57),b=e(97,102),d=e(65,70);return{fromCode:function(b){return String.fromCharCode(b)},toCode:function(b){return b.charCodeAt(0)},toUpper:function(b){return b.toUpperCase()},toLower:function(b){return b.toLowerCase()},toLocaleUpper:function(b){return b.toLocaleUpperCase()},toLocaleLower:function(b){return b.toLocaleLowerCase()},isLower:e(97,122),isUpper:e(65,90),isDigit:k,isOctDigit:e(48,55),isHexDigit:function(e){return k(e)||
34−b(e)||d(e)}}}();
35−Elm.Color=function(){function e(e){var b=e.value*e.saturation,d=e.hue/60,j=b*(1-Math.abs(d%2-1)),a=0,m=0,g=0;0<=d&&1>d?(a=b,m=j,g=0):1<=d&&2>d?(a=j,m=b,g=0):2<=d&&3>d?(a=0,m=b,g=j):3<=d&&4>d?(a=0,m=j,g=b):4<=d&&5>d?(a=j,m=0,g=b):5<=d&&6>d&&(a=b,m=0,g=j);e=e.value-b;return["Color",Math.round(255*(a+e)),Math.round(255*(m+e)),Math.round(255*(g+e)),1]}return{rgba:function(e){return function(b){return function(d){return function(j){return["Color",e,b,d,j]}}}},rgb:function(e){return function(b){return function(d){return["Color",e,
36−b,d,1]}}},hsva:function(k){return function(b){return function(d){return function(j){var a=e({hue:k,saturation:b,value:d});a[4]=j;return a}}}},hsv:function(k){return function(b){return function(d){return e({hue:k,saturation:b,value:d})}}},red:["Color",255,0,0,1],green:["Color",0,255,0,1],blue:["Color",0,0,255,1],yellow:["Color",255,255,0,1],cyan:["Color",0,255,255,1],magenta:["Color",255,0,255,1],black:["Color",0,0,0,1],white:["Color",255,255,255,1],gray:["Color",128,128,128,1],grey:["Color",128,128,
37−128,1],complement:function(k){var b;b=k[1]/255;var d=k[2]/255;k=k[3]/255;var j=Math.max(b,d,k),a=Math.min(b,d,k),a=j-a,m=0;0===a?m=0:j===b?m=(d-k)/a%6:j===d?m=(k-b)/a+2:j===k&&(m=(b-d)/a+4);b={value:j,hue:60*m,saturation:0===j?0:a/j};b.hue=(b.hue+180)%360;return e(b)},extract:function(e){return 1===e[4]?"rgb("+e[1]+","+e[2]+","+e[3]+")":"rgba("+e[1]+","+e[2]+","+e[3]+","+e[4]+")"}}}();
38−var Collage=function(){function e(b,a){var c=a.length-1;if(!(0>=c))for(b.moveTo(a[c][1],a[c][2]);c--;)b.lineTo(a[c][1],a[c][2])}function k(b,a,c,f){0===b.length&&(b=[8,4]);var d=f.length-1;if(!(0>=d)){var n=f[d][1],g=f[d][2],e=0,j=0,k=0,m=0,q=0,t=0,w=b.length,A=!0,x=b[0];for(a.moveTo(n,g);d--;){e=f[d][1];j=f[d][2];k=e-n;m=j-g;for(q=Math.sqrt(k*k+m*m);x<=q;)n+=k*x/q,g+=m*x/q,a[A?"lineTo":"moveTo"](n,g),k=e-n,m=j-g,q=Math.sqrt(k*k+m*m),A=!A,t=(t+1)%w,x=b[t];0<q&&(a[A?"lineTo":"moveTo"](e,j),x-=q);n=
39−e;g=j}}a.strokeStyle=Elm.Color.extract(c);a.stroke()}function b(b,a,c,f,d){a.clearRect(0,0,c,f);for(c=d.length;c--;){var n=d[c],p=b;f=a;var j=n[1],m=n[2],s=n[3][1],u=n[3][2],n=n[4];f.save();(0!==s||0!==u)&&f.translate(s,u);j!==~~j&&f.rotate(2*Math.PI*j);1!==m&&f.scale(m,m);f.beginPath();switch(n[0]){case "FLine":a:switch(p=f,j=n,n=j[3][1],j[1][0]){case "Solid":j=j[2];e(p,n);p.strokeStyle=Elm.Color.extract(j);p.stroke();break;case "Dotted":k([3,3],p,j[2],n);break a;case "Dashed":k([8,4],p,j[2],n);
40−break a;case "Custom":k(j[1][1],p,j[2],n)}break;case "FShape":a:switch(s=p,m=f,p=n[1],j=n[2],n=n[3][1],p[0]){case "Filled":p=m;e(p,n);p.fillStyle=Elm.Color.extract(j);p.fill();break a;case "Outlined":p=m;e(p,n);p.strokeStyle=Elm.Color.extract(j);p.stroke();break a;case "Textured":j=s;p=p[1];s=new Image;s.src=g.castStringToJSString(p);s.onload=j;e(m,n);m.fillStyle=m.createPattern(s,"repeat");m.fill();break a;case "CustomOutline":k(p[1],m,j,n)}break;case "FImage":j=f,m=n[1],s=n[2],n=n[3],u=new Image,
41−u.onload=p,u.src=g.castStringToJSString(n),j.drawImage(u,-m/2,-s/2,m,s)}f.restore()}}function d(a,h,c){var f=Render.newElement("canvas");a=~~a;h=~~h;f.style.width=a+"px";f.style.height=h+"px";f.style.display="block";f.width=a;f.height=h;if(f.getContext){var d=f.getContext("2d");b(function(){b(this,d,a,h,c)},d,a,h,c);return f}f.innerHTML="Your browser does not support the canvas element.";return f}function j(b,a,c,f,d,n,g){var e=Render.render(g);c="translate("+(d-g[3]/2)+"px,"+(n-g[4]/2)+"px) "+(1===
42−f?"":"scale("+f+","+f+")")+" "+(c===~~c?"":"rotate("+360*c+"deg)");e.style.transform=c;e.style.msTransform=c;e.style.MozTransform=c;e.style.webkitTransform=c;e.style.OTransform=c;c=Render.newElement("div");Render.addTo(c,e);c.style.width=~~b+"px";c.style.height=~~a+"px";c.style.overflow="hidden";return c}function a(a,h,c){if(!Value.eq(c,h)){var f=a.style.width.slice(0,-2)-0,g=a.style.height.slice(0,-2)-0;if("object"===typeof c[0]){if("object"===typeof h[0]&&a.getContext){var n=a.getContext("2d");
43−return b(function(){b(this,n,f,g,c)},n,f,g,c)}h=d(f,g,c);h.style.position="absolute";return a.parentNode.replaceChild(h,a)}h=j(f,g,c[1],c[2],c[3][1],c[3][2],c[4][1]);h.style.position="absolute";return a.parentNode.replaceChild(h,a)}}function m(b,a,c,f,d){var g=0,e,j=(b[1]-f[1])/c;b=(b[2]-f[2])/c;0!==a&&(a*=-2*Math.PI,c=j*Math.cos(a)-b*Math.sin(a),b=j*Math.sin(a)+b*Math.cos(a),j=c);if(0===d.length)return!1;e=d[0];for(c=d.length-1;c--;){a=d[c];f=e[1];e=e[2];var k=a[1],m=a[2];if(e<m)var u=e,q=m;else u=
44−m,q=e;if(f<k)var t=f,w=k;else t=k,w=f;u<b&&b<=q&&j<=w&&(j<=t||j<=(b-e)*(k-f)/(m-e)+f)&&++g;e=a}return 1===g%2}var g=Elm.JavaScript;return{collage:function(b,a,c){if(0===c.length)return d(b,a,[]);for(var f=Array(c.length),e=c.length;e--;){var g=c[e];f[e]="string"===typeof g[0]?j(b,a,g[1],g[2],g[3][1],g[3][2],g[4][1]):d(b,a,g)}return 1===c.length?f[0]:Render.flowWith(Render.goIn,function(b){return b},f)},updateCollage:function(b,h,c){if(1===c.length)return a(b,h[0],c[0]);b=b.childNodes;for(var f=b.length,
45−d=f;d--;)a(b[f-d-1],h[d],c[d])},insideForm:function(b){return function(a){var c=b[1],f=b[2];if(6>a.length){var d=a[3][1],g=a[3][2],e=0,j=a[2];switch(a[4][0]){case "FShape":for(var k=a[4][3][1],s=k.length;--s;)var u=k[s],e=Math.max(e,u[1]*u[1]+u[2]*u[2]);e*=j*j;break;case "FImage":k=j*a[4][1]/2;j=j*a[4][2]/2;e=k*k+j*j;break;case "FElement":k=j*a[4][1][3]/2,j=j*a[4][1][4]/2,e=k*k+j*j}a.push(function(a,b){var c=a-d,h=b-g;return c*c+h*h<e+1})}if(!a[5](c,f))return!1;var q,t;switch(a[4][0]){case "FShape":return m(b,
46−a[1],a[2],a[3],a[4][3][1]);case "FLine":return!1;case "FImage":q=a[4][1]/2;t=a[4][2]/2;break;case "FElement":q=a[4][1][3]/2,t=a[4][1][4]/2}return m(b,a[1],a[2],a[3],[[null,q,t],[null,-q,t],[null,-q,-t],[null,q,-t],[null,q,t]])}}}}();
47−Elm.Graphics=function(){function e(a){return function(b){return["Position",a,b]}}function k(a){return function(b){return["EText",a,b]}}function b(a){return function(b){return["EFlow",a,r.castListToJSArray(b)]}}function d(a){return["Line",r.castListToJSArray(a)]}function j(a){return function(b){var c=r.castListToJSArray(a);0<c.length&&c.push(c[0]);return["Shape",c,b]}}function a(a){return function(b){return function(c){return function(h){return["Form",a,b,c,h]}}}}function m(a){return function(b){return function(c){return["FLine",
48−a,b,c]}}}function g(a){return function(b){return function(c){return["FShape",a,b,c]}}}function l(a,b,c,h,f,d){return["Element",Guid.guid(),a,b,c,h,f,d]}function h(a,b,c){return["Element",Guid.guid(),a,b,c,1,["Nothing"],["Nothing"]]}function c(a){return~~a[3]}function f(a){return~~a[4]}function v(a){return function(b){return function(c){return h(["EImage",r.castStringToJSString(c)],a,b)}}}function n(a){return function(b){return h(A,a,b)}}function p(a){return function(b){return function(c){var h=map(function(c){return["Tuple2",
49−a/2*Math.cos(2*(Math.PI/50)*c),b/2*Math.sin(2*(Math.PI/50)*c)]}),f=49,d=["Nil"];if(0<=f){do d=["Cons",f,d];while(0<f--)}return j(h(d))(c)}}}for(this.i in Elm.List)eval("var "+this.i+" = Elm.List[this.i];");var r=Elm.JavaScript,y=["DRight"],s=["DDown"],u=["DOut"],q=["Near"],t=["Mid"],w=["Far"],A=["EEmpty"],x=["Solid"],D=["Dotted"],F=["Dashed"],B=["Filled"],E=["Outlined"],z=e(q)(q),C=e(w)(q),G=e(q)(w),H=e(w)(w),I=e(q)(t),J=e(w)(t),q=e(t)(q),w=e(t)(w),t=e(t)(t);return{left:["DLeft"],right:y,down:s,up:["DUp"],
50−inward:["DIn"],outward:u,topLeft:z,topRight:C,bottomLeft:G,bottomRight:H,midLeft:I,midRight:J,midTop:q,midBottom:w,middle:t,middleAt:function(a){return function(b){return["PositionAt",a,b]}},topLeftAt:function(a){return function(b){return["PositionTL",a,b]}},topRightAt:function(a){return function(b){return["PositionTR",a,b]}},bottomLeftAt:function(a){return function(b){return["PositionBL",a,b]}},bottomRightAt:function(a){return function(b){return["PositionBR",a,b]}},absolute:function(a){return["Absolute",
51−a]},relative:function(a){return["Relative",a]},width:function(a){return function(b){var c=b[2];switch(c[0]){case "EImage":case "EVideo":return l(b[2],a,b[4]*a/b[3],b[5],b[6],b[7]);case "EText":return c=Value.getTextSize(a,b[4],c[2]),l(b[2],a,c[1],b[5],b[6],b[7])}return l(b[2],a,b[4],b[5],b[6],b[7])}},height:function(a){return function(b){switch(b[2][0]){case "EImage":case "EVideo":return l(b[2],b[3]*a/b[4],a,b[5],b[6],b[7])}return l(b[2],b[3],a,b[5],b[6],b[7])}},size:function(b){return function(a){return function(c){return l(c[2],
52−b,a,c[5],c[6],c[7])}}},opacity:function(b){return function(a){return l(a[2],a[3],a[4],b,a[6],a[7])}},color:function(a){return function(b){return l(b[2],b[3],b[4],b[5],["Just",a],b[7])}},link:function(b){return function(a){return l(a[2],a[3],a[4],a[5],a[6],["Just",r.castStringToJSString(b)])}},widthOf:c,heightOf:f,sizeOf:function(a){return["Tuple2",~~a[3],~~a[4]]},text:function(a){var b=Value.getTextSize(0,0,a);return h(k("left")(a),b[0],b[1])},asText:function(a){a=Elm.Text.monospace(Value.toText(Value.show(a)));
53−var b=Value.getTextSize(0,0,a);return h(k("left")(a),b[0],b[1])},plainText:function(a){a=Value.toText(a);var b=Value.getTextSize(0,0,a);return h(k("left")(a),b[0],b[1])},centeredText:function(a){var b=Value.getTextSize(0,0,a);return h(k("center")(a),b[0],b[1])},justifiedText:function(a){var b=Value.getTextSize(0,0,a);return h(k("justify")(a),b[0],b[1])},rightedText:function(a){var b=Value.getTextSize(0,0,a);return h(k("right")(a),b[0],b[1])},image:v,images:function(a){var b=Elm.Signal.constant(n(0)(0));
54−a=Elm.Signal.lift(function(a){a=r.castStringToJSString(a);var c=new Image;c.onload=function(){Dispatcher.notify(b.id,v(this.width)(this.height)(a))};c.src=a})(a);return Elm.Signal.lift2(function(a){return function(){return a}})(b)(a)},video:function(a){return function(b){return function(c){return h(["EVideo",r.castStringToJSString(c)],a,b)}}},fittedImage:function(a){return function(b){return function(c){return h(["EFittedImage",r.castStringToJSString(c)],a,b)}}},flow:function(a){return function(d){var e;
55−e=map(c)(d);a:{switch(a[0]){case "DLeft":e=sum(e);break a;case "DRight":e=sum(e);break a}e=maximum(e)}var g;g=map(f)(d);a:{switch(a[0]){case "DDown":g=sum(g);break a;case "DUp":g=sum(g);break a}g=maximum(g)}return h(b(a)(d),e,g)}},above:function(a){return function(c){return h(b(s)(["Cons",a,["Cons",c,["Nil"]]]),Math.max(~~a[3],~~c[3]),~~a[4]+~~c[4])}},below:function(a){return function(c){return h(b(s)(["Cons",c,["Cons",a,["Nil"]]]),Math.max(~~a[3],~~c[3]),~~a[4]+~~c[4])}},beside:function(a){return function(c){return h(b(y)(["Cons",
56−a,["Cons",c,["Nil"]]]),~~a[3]+~~c[3],Math.max(~~a[4],~~c[4]))}},layers:function(a){return h(b(u)(a),maximum(map(c)(a)),maximum(map(f)(a)))},collage:function(a){return function(b){return function(c){return h(["ECollage",a,b,Value.groupForms(c)],a,b)}}},spacer:n,container:function(a){return function(b){return function(c){return function(f){return h(["EContainer",c,f],a,b)}}}},line:d,segment:function(a){return function(b){return d(["Cons",a,["Cons",b,["Nil"]]])}},polygon:j,rect:function(a){return function(b){return function(c){return j(["Cons",
57−["Tuple2",0-a/2,0-b/2],["Cons",["Tuple2",0-a/2,b/2],["Cons",["Tuple2",a/2,b/2],["Cons",["Tuple2",a/2,0-b/2],["Nil"]]]]])(c)}}},oval:p,circle:function(a){return p(2*a)(2*a)},ngon:function(a){return function(b){return function(c){var h=map(function(c){return["Tuple2",b*Math.cos(2*(Math.PI/a)*c),b*Math.sin(2*(Math.PI/a)*c)]}),f=a-1,d=["Nil"];if(0<=f){do d=["Cons",f,d];while(0<f--)}return j(h(d))(c)}}},solid:function(b){return function(c){return a(0)(1)(["Tuple2",0,0])(m(x)(b)(c))}},dotted:function(b){return function(c){return a(0)(1)(["Tuple2",
58−0,0])(m(D)(b)(c))}},dashed:function(b){return function(c){return a(0)(1)(["Tuple2",0,0])(m(F)(b)(c))}},customLine:function(b){return function(c){return function(h){return a(0)(1)(["Tuple2",0,0])(m(["Custom",r.castListToJSArray(b)])(c)(h))}}},filled:function(b){return function(c){return a(0)(1)(c[2])(g(B)(b)(c))}},outlined:function(b){return function(c){return a(0)(1)(c[2])(g(E)(b)(c))}},customOutline:function(b){return function(c){return function(h){return a(0)(1)(h[2])(g(["CustomOutline",r.castListToJSArray(b)])(c)(h))}}},
59−textured:function(b){return function(c){return a(0)(1)(c[2])(g(["Textured",b])(null)(c))}},sprite:function(b){return function(c){return function(h){return function(f){return a(0)(1)(f)(["FImage",c,h,r.castStringToJSString(b)])}}}},toForm:function(b){return function(c){return a(0)(1)(b)(["FElement",c])}},rotate:function(b){return function(c){a:{switch(c[0]){case "Form":var h=c[2],f=c[3],d=c[4];c=a(b+c[1])(h)(f)(d);break a}throw"Non-exhaustive pattern match in case";}return c}},scale:function(b){return function(c){return a(c[1])(b*
60−c[2])(c[3])(c[4])}},move:function(b){return function(c){return function(h){var f;a:{switch(h[0]){case "Form":f=h[1];var d=h[2],e=h[3];h=h[4];switch(e[0]){case "Tuple2":var g=e[1],e=e[2];f=a(f)(d)(["Tuple2",b+g,c+e])(h);break a}}throw"Non-exhaustive pattern match in case";}return f}}},isWithin:Collage.insideForm}}();
61−Elm.Text=function(){function e(a){return Value.toText(a)}var k=function(a){return function(b){return"<"+a+' style="padding:0;margin:0">'+b+"</"+a+">"}},b=function(a,b){return function(f){return"<span style='"+a+":"+b+"'>"+f+"</span>"}},d=function(a){a=Elm.JavaScript.castStringToJSString(a);return b("font-family",a)},j=k("h1"),a=b("font-style","italic"),k=k("b"),m=b("text-decoration","underline"),g=b("text-decoration","overline"),l=b("text-decoration","line-through");return{fromString:e,toText:e,header:j,
62−height:function(a){return b("font-size",a+"em")},italic:a,bold:k,underline:m,overline:g,strikeThrough:l,monospace:d("monospace"),typeface:d,color:function(a){return b("color",Elm.Color.extract(a))},link:function(a){return function(b){return"<a href='"+e(a)+"'>"+b+"</a>"}}}}();
63−var Render=function(){function e(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a}function k(a){return a}function b(a){a.style.styleFloat="left";a.style.cssFloat="left";return a}function d(a){a.style.position="absolute";return a}function j(a,b,f){for(var d=e("div"),g=f.length;g--;){var j=a(b(f[g]));d.appendChild(j)}return d}function a(a){switch(a[0]){case "Absolute":return a[1]+"px";case "Relative":return 100*a[1]+"%"}}function m(b,c){c.style.position="absolute";c.style.margin=
64−"auto";switch(b[0]){case "Position":"Far"!==b[1][0]&&(c.style.left=0);"Near"!==b[1][0]&&(c.style.right=0);"Far"!==b[2][0]&&(c.style.top=0);"Near"!==b[2][0]&&(c.style.bottom=0);break;case "PositionAt":c.style.top=a(b[2]);c.style.left=a(b[1]);var f="translate("+~~(-c.style.width.slice(0,-2)/2)+"px,"+~~(-c.style.height.slice(0,-2)/2)+"px)";c.style.transform=f;c.style.msTransform=f;c.style.MozTransform=f;c.style.webkitTransform=f;c.style.OTransform=f;break;default:f=b[0].slice(-2),c.style["T"===f[0]?
65−"top":"bottom"]=a(b[2]),c.style["L"===f[1]?"left":"right"]=a(b[1])}}function g(a){var c={};switch(a[2][0]){case "EText":var c=a[2][1],f=a[2][2],l=e("div");l.innerHTML=f;l.style.textAlign=c;c=l;break;case "EImage":c=a[2][1];f=e("img");f.src=c;f.name=c;f.style.display="block";c=f;break;case "EVideo":l=a[2][1];c=e("video");c.controls="controls";f=e("source");f.src=l;l=l.split(".");f.type="video/"+l[l.length-1];c.appendChild(f);c.style.display="block";break;case "EFittedImage":var n=a[3],p=a[4],c=a[2][1],
66−f=e("div");f.style.width=n+"px";f.style.height=p+"px";f.style.position="relative";f.style.overflow="hidden";var r=e("img");r.onload=function(){r.style.position="absolute";r.style.margin="auto";var a=n,b=p;n/p>this.width/this.height?b=Math.round(this.height*n/this.width):a=Math.round(this.width*p/this.height);r.style.width=a+"px";r.style.height=b+"px";r.style.left=(n-a)/2+"px";r.style.top=(p-b)/2+"px"};r.src=c;r.name=c;f.appendChild(r);c=f;break;case "EFlow":a:{c=a[2][2];switch(a[2][1][0]){case "DDown":c=
67−c.slice(0).reverse();case "DUp":c=j(k,g,c);break a;case "DRight":c=c.slice(0).reverse();case "DLeft":c=j(b,g,c);break a;case "DOut":c=c.slice(0).reverse();case "DIn":c=j(d,g,c);break a}c=void 0}break;case "ECollage":c=Collage.collage(a[2][1],a[2][2],a[2][3]);break;case "EEmpty":c=e("div");break;case "EContainer":f=a[2][1];c=g(a[2][2]);m(f,c);f=e("div");f.style.position="relative";f.style.overflow="hidden";f.appendChild(c);c=f;break;case "EHtml":c=a[2][1];"button"!==c.type&&(f=Value.getExcess(c),a[3]-=
68−f[0],a[4]-=f[1]);break;case "EExternalHtml":c=e("div"),c.appendChild(a[2][1])}c.id=a[1];c.style.width=~~a[3]+"px";c.style.height=~~a[4]+"px";1!==a[5]&&(c.style.opacity=a[5]);"Just"===a[6][0]&&(c.style.backgroundColor=Elm.Color.extract(a[6][1]));return"Just"===a[7][0]?(f=e("a"),f.href=a[7][1],f.appendChild(c),f):c}function l(a,c,f){"A"===a.tagName&&(a=a.firstChild);if(c[1]!==f[1]){if(c[2][0]!==f[2][0])return a.parentNode.replaceChild(g(f),a);var e=f[2],j=c[2];switch(e[0]){case "EText":e[1]!==j[1]&&
69−(a.style.textAlign=e[1]);e[2]!==j[2]&&(a.innerHTML=e[2]);break;case "EImage":e[1]!==j[1]&&(a.src=e[1]);break;case "EVideo":case "EFittedImage":if(!Value.eq(e,j)||f[3]!==c[3]||f[4]!==c[4])return a.parentNode.replaceChild(g(f),a);break;case "ECollage":if(e[1]!==j[1]||e[2]!==j[2]||e[3].length!==j[3].length)return a.parentNode.replaceChild(g(f),a);Collage.updateCollage(a,j[3],e[3]);break;case "EFlow":if(e[1]!==j[1])return a.parentNode.replaceChild(g(f),a);var p=e[2],r=a.childNodes;if(p.length!==r.length)return a.parentNode.replaceChild(g(f),
70−a);var j=j[2],y=function(a){return a};switch(e[1][0]){case "DDown":case "DUp":y=k;break;case "DRight":case "DLeft":y=b;break;case "DOut":case "DIn":y=d}for(e=r.length;e--;)l(r[e],j[e],p[e]),y(r[e]);break;case "EContainer":l(a.childNodes[0],j[2],e[2]);m(e[1],a.childNodes[0]);break;case "EHtml":f[1]!==c[1]&&(p=g(f),a.parentNode.replaceChild(p,a),a=p);"button"!==p.type&&(e=Value.getExcess(a),f[3]-=e[0],f[4]-=e[1]);break;case "EExternalHtml":f[1]!==c[1]&&a.parentNode.replaceChild(g(f),a)}f[3]!==c[3]&&
71−(a.style.width=~~f[3]+"px");f[4]!==c[4]&&(a.style.height=~~f[4]+"px");f[5]!==c[5]&&(a.style.opacity=f[5]);2===f[6].length&&(e=Elm.Color.extract(f[6][1]),e!==a.style.backgroundColor&&(a.style.backgroundColor=e));if(2===f[7].length&&(1===c[7].length||f[7][1]!==c[7][1]))a.parentNode.href=f[7][1];f[1]=c[1]}}return{render:g,update:l,addTo:function(a,b){a.appendChild(b)},newElement:e,flowWith:j,goIn:d}}();
72−Elm.Signal=function(){function e(a){this.id=Guid.guid();this.value=a;this.kids=[];this.defaultNumberOfKids=0;this.recv=function(a,b,c){if(b=b===this.id)this.value=c;l(this,a,b);return b};Dispatcher.inputs.push(this)}function k(a,b){this.id=Guid.guid();this.value=null;this.kids=[];this.count=0;this.changed=!1;b.reverse();this.recalc=function(){for(var d=a,e=b.length;e--;)d=d(b[e].value);this.value=d};this.recalc();this.recv=function(a,c){this.count+=1;c&&(this.changed=!0);this.count==b.length&&(this.changed&&
73−this.recalc(),l(this,a,this.changed),this.changed=!1,this.count=0)};for(var d=b.length;d--;)b[d].kids.push(this)}function b(a,b,d,e){this.id=Guid.guid();this.value=d?b(e.value):b;this.kids=[];this.recv=function(b,d){d&&(this.value=a(e.value)(this.value));l(this,b,d)};e.kids.push(this)}function d(a,b,d){this.id=Guid.guid();this.value=a(d.value)?b:d.value;this.kids=[];this.recv=function(b,f){var e=f&&!a(d.value);e&&(this.value=d.value);l(this,b,e)};d.kids.push(this)}function j(a){this.id=Guid.guid();
74−this.value=a.value;this.kids=[];this.recv=function(b,d){var e=d&&!Value.eq(this.value,a.value);e&&(this.value=a.value);l(this,b,e)};a.kids.push(this)}function a(a,b){this.id=Guid.guid();var d=(new window.Date).getTime();this.value=a?Value.Tuple(d,b.value):d;this.kids=[];this.recv=function(d,e){e&&(this.value=a?Value.Tuple(d,b.value):d);l(this,d,e)};b.kids.push(this)}function m(a,b){this.id=Guid.guid();this.value=b.value;this.kids=[];this.count=0;this.changed=!1;this.recv=function(d,e,g){g===a.id&&
75−(this.changed=e);this.count+=1;2==this.count&&(this.changed&&(this.value=b.value),l(this,d,this.changed),this.count=0,this.changed=!1)};a.kids.push(this);b.kids.push(this)}function g(a,b){this.id=Guid.guid();this.value=a.value;this.kids=[];this.next=null;this.count=0;this.changed=!1;this.recv=function(d,e,g){this.count+=1;e&&(this.changed=!0,g==b.id&&null===this.next&&(this.next=b.value),g==a.id&&(this.next=a.value));2==this.count&&(this.changed&&(this.value=this.next,this.next=null),l(this,d,this.changed),
76−this.changed=!1,this.count=0)};a.kids.push(this);b.kids.push(this)}var l=function(a,b,d){for(var e=a.kids,g=e.length;g--;)e[g].recv(b,d,a.id)},h=function(a){return function(b){return function(e){e=new k(function(a){return function(b){return[a,b]}},[a,e]);e=new d(function(a){return a[0]},[!0,b],e);return new k(function(a){return a[1]},[e])}}};return{constant:function(a){return new e(a)},lift:function(a){return function(b){return new k(a,[b])}},lift2:function(a){return function(b){return function(d){return new k(a,
77−[b,d])}}},lift3:function(a){return function(b){return function(d){return function(e){return new k(a,[b,d,e])}}}},lift4:function(a){return function(b){return function(d){return function(e){return function(g){return new k(a,[b,d,e,g])}}}}},lift5:function(a){return function(b){return function(d){return function(e){return function(g){return function(h){return new k(a,[b,d,e,g,h])}}}}}},lift6:function(a){return function(b){return function(d){return function(e){return function(g){return function(h){return function(j){return new k(a,
78−[b,d,e,g,h,j])}}}}}}},lift7:function(a){return function(b){return function(d){return function(e){return function(g){return function(h){return function(j){return function(l){return new k(a,[b,d,e,g,h,j,l])}}}}}}}},lift8:function(a){return function(b){return function(d){return function(e){return function(g){return function(h){return function(j){return function(l){return function(m){return new k(a,[b,d,e,g,h,j,l,m])}}}}}}}}},foldp:function(a){return function(d){return function(e){return new b(a,d,!1,
79−e)}}},foldp_:function(a){return function(d){return function(e){return new b(a,d,!0,e)}}},foldp1:function(a){return function(d){return new b(a,function(a){return a},!0,d)}},delay:function(a){return function(b){var d=new e(b.value),g=!0;b=new m(d,new k(function(a){return function(){return a}},[d,new k(function(b){g||setTimeout(function(){Dispatcher.notify(d.id,b)},a)},[b])]));g=!1;return b}},merge:function(a){return function(b){return new g(a,b)}},merges:function(a){return Elm.List.foldl1(function(a){return function(b){return new g(a,
80−b)}})(a)},average:function(a){return function(b){for(var d=Array(a),e=a;e--;)d[e]=0;var e=0,g=!1,h=0;return new k(function(b){h+=b-d[e];d[e]=b;b=h/Math.max(1,g?a:e);++e==a&&(g=!0,e=0);return b},[b])}},count:function(a){return new b(function(){return function(a){return a+1}},0,!1,a)},countIf:function(a){return function(d){return new b(function(b){return function(d){return a(b)?d+1:d}},0,!1,d)}},keepIf:function(a){return function(b){return function(e){return new d(function(b){return!a(b)},b,e)}}},dropIf:function(a){return function(b){return function(e){return new d(a,
81−b,e)}}},keepWhen:function(a){return h(new k(function(a){return!a},[a]))},dropWhen:h,dropRepeats:function(a){return new j(a)},sampleOn:function(a){return function(b){return new m(a,b)}},timestamp:function(b){return new a(!0,b)},timeOf:function(b){return new a(!1,b)}}}();
82−var Dispatcher=function(){function e(b){if(!b.hasOwnProperty("defaultNumberOfKids"))return!0;var a=b.kids.length;if(0==a)return!1;if(a>b.defaultNumberOfKids)return!0;for(var d=!1;a--;)d=d||e(b.kids[a]);return d}var k=null,b=[],d=null;return{initialize:function(){k=Elm.main();k.hasOwnProperty("recv")||(k=Elm.Signal.constant(k));d=k.value;for(var j=[],a=b.length;a--;)e(b[a])&&j.push(b[a]);b=j;document.getElementById("content").appendChild(Render.render(d));j=document.getElementById("widthChecker").offsetWidth;
83−j!==window.innerWidth&&Dispatcher.notify(Elm.Window.dimensions.id,Value.Tuple(j,window.innerHeight));k=Elm.Signal.lift(function(a){var b=document.getElementById("content");Render.update(b.firstChild,d,a);return d=a})(k)},notify:function(d,a){for(var e=(new window.Date).getTime(),g=!1,k=b.length;k--;)g=b[k].recv(e,d,a)||g;return g},inputs:b}}();
84−Elm.HTTP=function(){function e(b){return function(d){return function(e){return function(c){return{"0":"Request",length:1,verb:a.castStringToJSString(b),url:a.castStringToJSString(d),data:null===e?null:a.castStringToJSString(e),headers:c}}}}}function k(a){return e("GET")(a)(null)(["Nil"])}function b(b,e){return function(h){if(""!==h.url){var c={value:["Waiting"]};b.push(c);var f=null;window.ActiveXObject&&(f=new ActiveXObject("Microsoft.XMLHTTP"));window.XMLHttpRequest&&(f=new XMLHttpRequest);f.onreadystatechange=
85−function(){4===f.readyState&&(c.value=200===f.status?["Success",m(f.responseText)]:["Failure",f.status,m(f.statusText)],setTimeout(function(){d(b,e)},0))};f.open(h.verb,h.url,!0);Elm.List.map(function(b){f.setRequestHeader(a.castStringToJSString(b[1]),a.castStringToJSString(b[2]))})(h.headers);f.send(h.data)}}}function d(a,b){0<a.length&&(Dispatcher.notify(b.id,a[0].value),"Waiting"!==a[0].value[0]&&(a.shift(),setTimeout(function(){d(a,b)},0)))}function j(a){var d=Elm.Signal.constant(["Waiting"]);
86−a=Elm.Signal.lift(b([],d))(a);return Elm.Signal.lift2(function(a){return function(){return a}})(d)(a)}var a=Elm.JavaScript,m=Elm.JavaScript.castJSStringToString;return{get:k,post:function(a){return function(b){return e("POST")(a)(b)(["Nil"])}},request:e,send:j,sendGet:function(a){return j(Elm.Signal.lift(k)(a))}}}();
87−Elm.Input=function(){var e=Elm.JavaScript,k=Elm.JavaScript.castJSStringToString,b=function(a,b){a.placeholder=e.castStringToJSString(b);var d=Elm.Signal.constant(["Nil"]);Value.addListener(a,"keyup",function(){Dispatcher.notify(d.id,k(a.value));a.focus()});a.style.padding="1px";return Value.Tuple(Value.wrap(a),d)},d=function(a){a=document.createElement(a);a.style.padding="0";a.style.margin="0";return a},j=function(a){for(var b=d("select"),e=[];"Cons"===a[0];){var j=d("option"),h=Value.toText(a[1][1]);
88−j.value=h;j.innerHTML=h;b.appendChild(j);e.push(a[1][2]);a=a[2]}var c=Elm.Signal.constant(e[0]);Value.addListener(b,"change",function(){Dispatcher.notify(c.id,e[b.selectedIndex])});return Value.Tuple(Value.wrap(b),c)};return{textArea:function(a){return function(e){var g=d("textarea");g.rows=e;g.cols=a;return b(g,"")}},textField:function(a){var e=d("input");e.type="text";return b(e,a)},password:function(a){var e=d("input");e.type="password";return b(e,a)},checkbox:function(a){var b=d("input");b.type=
89−"checkbox";b.checked=a;var e=Elm.Signal.constant(a);Value.addListener(b,"change",function(){Dispatcher.notify(e.id,b.checked)});return Value.Tuple(Value.wrap(b),e)},dropDown:j,stringDropDown:function(a){return j(Elm.List.map(function(a){return Value.Tuple(a,a)})(a))},button:function(a){var b=d("input");b.type="button";b.value=e.castStringToJSString(a);var g=Elm.Signal.constant(!1);Value.addListener(b,"click",function(){Dispatcher.notify(g.id,!0);Dispatcher.notify(g.id,!1)});return Value.Tuple(Value.wrap(b),
90−g)}}}();
91−Elm.Keyboard={Raw:function(){function e(b,j){return"Nil"===j[0]?j:j[1]===b?j[2]:["Cons",j[1],e(b,j[2])]}var k=Elm.Signal.constant(["Nil"]),b=Elm.Signal.constant(["Nothing"]);Value.addListener(document,"keydown",function(b){var e;a:{for(e=k.value;"Nil"!==e[0];){if(e[1]===b.keyCode){e=!0;break a}e=e[2]}e=!1}e||Dispatcher.notify(k.id,["Cons",b.keyCode,k.value])||this.removeEventListener("keydown",arguments.callee,!1)});Value.addListener(document,"keyup",function(b){var j=e(b.keyCode,k.value);Dispatcher.notify(k.id,
92−j)||this.removeEventListener("keyup",arguments.callee,!1)});Value.addListener(window,"blur",function(b){Dispatcher.notify(k.id,["Nil"])||this.removeEventListener("blur",arguments.callee,!1)});Value.addListener(document,"keypress",function(d){var e=Dispatcher.notify(b.id,["Just",d.charCode||d.keyCode]);Dispatcher.notify(b.id,["Nothing"]);e||this.removeEventListener("keypress",arguments.callee,!1)});return{keysDown:k,charPressed:b}}()};
93−Elm.Mouse=function(){function e(a){var b=0,d=0;a||(a=window.event);if(a.pageX||a.pageY)b=a.pageX,d=a.pageY;else if(a.clientX||a.clientY)b=a.clientX+document.body.scrollLeft+document.documentElement.scrollLeft,d=a.clientY+document.body.scrollTop+document.documentElement.scrollTop;return Value.Tuple(b,d)}var k=Elm.Signal.constant(Value.Tuple(0,0));k.defaultNumberOfKids=2;var b=Elm.Signal.lift(function(a){return a[1]})(k);b.defaultNumberOfKids=0;var d=Elm.Signal.lift(function(a){return a[2]})(k);d.defaultNumberOfKids=
94−0;var j=Elm.Signal.constant(!1),a=Elm.Signal.constant(!1),m=Elm.Signal.constant(Value.Tuple());Value.addListener(document,"click",function(b){var d=Dispatcher.notify(a.id,!0),e=Dispatcher.notify(m.id,Value.Tuple());Dispatcher.notify(a.id,!1);!d&&!e&&this.removeEventListener("click",arguments.callee,!1)});Value.addListener(document,"mousedown",function(a){Dispatcher.notify(j.id,!0)||this.removeEventListener("mousedown",arguments.callee,!1)});Value.addListener(document,"mouseup",function(a){Dispatcher.notify(j.id,
95−!1)||this.removeEventListener("mouseup",arguments.callee,!1)});Value.addListener(document,"mousemove",function(a){Dispatcher.notify(k.id,e(a))||this.removeEventListener("mousemove",arguments.callee,!1)});return{position:k,x:b,y:d,isClicked:a,isDown:j,clicks:m,isClickedOn:function(a){a=Render.render(a);var b=Elm.Signal.constant(!1);Value.addListener(a,"click",function(){Dispatcher.notify(b.id,!0);Dispatcher.notify(b.id,!1)});return Value.Tuple(Value.wrap(a),b)}}}();
96−Elm.Random=function(){return{inRange:function(e){return function(k){return Elm.Signal.constant(Math.floor(Math.random()*(k-e+1))+e)}},randomize:function(e){return function(k){return function(b){return Elm.Signal.lift(function(){return Math.floor(Math.random()*(k-e+1))+e})(b)}}}}}();
97−Elm.Time=function(){function e(){return(new window.Date).getTime()}function k(b){return function(d){var j=1E3/b,a=e(),k=a,g=0,l=!0,h=Elm.Signal.constant(g),c=0;return Elm.Signal.lift2(function(b){return function(d){if(b){var n=!l&&b;c=setTimeout(function(){k=e();g=n?0:k-a;a=k;Dispatcher.notify(h.id,g)},j)}else l&&clearTimeout(c);l=b;return d}})(d)(h)}}Elm.Signal.constant(!0);return{fpsWhen:k,fps:function(b){return k(b)(Elm.Signal.constant(!0))},every:function(b){var d=Elm.Signal.constant(e());setInterval(function(){Dispatcher.notify(d.id,
98−e())},b);return d},delay:Elm.Signal.delay,since:function(b){return function(d){var e=Elm.Signal.count(Elm.Signal.delay(b)(d));return Elm.Signal.lift2(function(a){return function(b){return!Value.eq(a,b)}})(Elm.Signal.count(d))(e)}},after:function(b){b*=1E3;var d=Elm.Signal.constant(!1);setTimeout(function(){Dispatcher.notify(d.id,!0)},b);return d},before:function(b){b*=1E3;var d=Elm.Signal.constant(!0);setTimeout(function(){Dispatcher.notify(d.id,!1)},b);return d},hour:36E5,minute:6E4,second:1E3,ms:1,
99−inHours:function(b){return b/36E5},inMinutes:function(b){return b/6E4},inSeconds:function(b){return b/1E3},inMss:function(b){return b},toDate:function(b){return new window.Date(b)},read:function(b){b=window.Date.parse(b);return isNaN(b)?["Nothing"]:["Just",b]}}}();
100−Elm.Window=function(){var e=Elm.Signal.constant(Value.Tuple(window.innerWidth,window.innerHeight));e.defaultNumberOfKids=2;var k=Elm.Signal.lift(function(b){return b[1]})(e);k.defaultNumberOfKids=0;var b=Elm.Signal.lift(function(b){return b[2]})(e);b.defaultNumberOfKids=0;Value.addListener(window,"resize",function(b){var j=document.getElementById("widthChecker").offsetWidth;Dispatcher.notify(e.id,Value.Tuple(j,window.innerHeight))||this.removeEventListener("resize",arguments.callee,!1)});return{dimensions:e,
101−width:k,height:b}}();
102−Elm.Date=function(){var e="Sun Mon Tue Wed Thu Fri Sat".split(" "),k="Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec".split(" ");return{read:function(b){b=new window.Date(Elm.JavaScript.castStringToJSString(b));return isNaN(b.getTime())?["Nothing"]:["Just",b]},year:function(b){return b.getFullYear()},month:function(b){return[k[b.getMonth()]]},day:function(b){return b.getDate()},hour:function(b){return b.getHours()},minute:function(b){return b.getMinutes()},second:function(b){return b.getSeconds()},dayOfWeek:function(b){return[e[b.getDay()]]},
103−toTime:function(b){return b.getTime()},Mon:["Mon"],Tue:["Tue"],Wed:["Wed"],Thu:["Thu"],Fri:["Fri"],Sat:["Sat"],Sun:["Sun"],Jan:["Jan"],Feb:["Feb"],Mar:["Mar"],Apr:["Apr"],May:["May"],Jun:["Jun"],Jul:["Jul"],Aug:["Aug"],Sep:["Sep"],Oct:["Oct"],Nov:["Nov"],Dec:["Dec"]}}();Value.addListener(document,"elm_log",function(e){console.log(e.value)});Value.addListener(document,"elm_title",function(e){document.title=e.value});
104−Value.addListener(document,"elm_redirect",function(e){0<e.value.length&&(window.location=e.value)});
105−Elm.Prelude=function(){function e(b){return function(d){if(b instanceof Array&&d instanceof Array){var j=b.length;if(j==d.length){for(var a=1;a<j;++a){var k=e(b[a])(d[a]);if("EQ"!==k[0])return k}return["EQ"]}return[1==d.length?"GT":"LT"]}return[b===d?"EQ":b<d?"LT":"GT"]}}var k=function(b){return function(d){var e=b%d,e=0==b?0:0<d?0<=b?e:e+d:-k(-b)(-d);return e==d?0:e}};return{eq:Value.eq,id:function(b){return b},not:function(b){return!b},fst:function(b){return b[1]},snd:function(b){return b[2]},rem:function(b){return function(d){return b%
106−d}},div:function(b){return function(d){return~~(b/d)}},otherwise:!0,compare:e,toFloat:function(b){return b},round:function(b){return Math.round(b)},floor:function(b){return Math.floor(b)},ceiling:function(b){return Math.ceil(b)},truncate:function(b){return~~b},readInt:function(b){b=Elm.JavaScript.castStringToJSString(b);var d=b.length;if(0===d)return["Nothing"];var e=0;if("-"==b[0]){if(1===d)return["Nothing"];e=1}for(;e<d;++e)if(!Elm.Char.isDigit(b[e]))return["Nothing"];return["Just",parseInt(b)]},
107−readFloat:function(b){b=Elm.JavaScript.castStringToJSString(b);var d=b.length;if(0===d)return["Nothing"];var e=0;if("-"==b[0]){if(1===d)return["Nothing"];e=1}for(var a=0;e<d;++e)if(!Elm.Char.isDigit(b[e])){if("."===b[e]&&(a+=1,1>=a))continue;return["Nothing"]}return["Just",parseFloat(b)]},sqrt:Math.sqrt,abs:Math.abs,pi:Math.PI,e:Math.E,sin:Math.sin,cos:Math.cos,tan:Math.tan,asin:Math.asin,acos:Math.acos,atan:Math.atan,atan2:function(b){return function(d){return Math.atan2(b,d)}},mod:k,min:function(b){return function(d){return Math.min(b,
108−d)}},max:function(b){return function(d){return Math.max(b,d)}},flip:function(b){return function(d){return function(e){return b(e)(d)}}},clamp:function(b){return function(d){return function(e){return Math.min(d,Math.max(b,e))}}},curry:function(b){return function(d){return function(e){return b(["Tuple2",d,e])}}},uncurry:function(b){return function(d){if("Tuple2"!==d[0])throw"Function was uncurry'd but was not given a pair.";return b(d[1])(d[2])}},logBase:function(b){return function(d){return Math.log(d)/
109−Math.log(b)}},Just:Elm.Maybe.Just,Nothing:Elm.Maybe.Nothing,maybe:Elm.Maybe.maybe,map:Elm.List.map,zip:Elm.List.zip,zipWith:Elm.List.zipWith,filter:Elm.List.filter,head:Elm.List.head,tail:Elm.List.tail,last:Elm.List.last,length:Elm.List.length,reverse:Elm.List.reverse,foldr:Elm.List.foldr,foldr1:Elm.List.foldr1,foldl:Elm.List.foldl,foldl1:Elm.List.foldl1,and:Elm.List.and,or:Elm.List.or,all:Elm.List.all,any:Elm.List.any,sum:Elm.List.sum,product:Elm.List.product,concat:Elm.List.concat,concatMap:Elm.List.concatMap,
110−maximum:Elm.List.maximum,minimum:Elm.List.minimum,scanl:Elm.List.scanl,scanl1:Elm.List.scanl1,take:Elm.List.take,drop:Elm.List.drop,zip:Elm.List.zip,unzip:Elm.List.unzip,lift:Elm.Signal.lift,lift2:Elm.Signal.lift2,lift3:Elm.Signal.lift3,lift4:Elm.Signal.lift4,lift5:Elm.Signal.lift5,lift6:Elm.Signal.lift6,lift7:Elm.Signal.lift7,lift8:Elm.Signal.lift8,foldp:Elm.Signal.foldp,foldp1:Elm.Signal.foldp1,foldp_:Elm.Signal.foldp_,constant:Elm.Signal.constant,merge:Elm.Signal.merge,count:Elm.Signal.count,countIf:Elm.Signal.countIf,
111−average:Elm.Signal.average,keepIf:Elm.Signal.keepIf,dropIf:Elm.Signal.dropIf,keepWhen:Elm.Signal.keepWhen,dropWhen:Elm.Signal.dropWhen,dropRepeats:Elm.Signal.dropRepeats,sampleOn:Elm.Signal.sampleOn,timestamp:Elm.Signal.timestamp,timeOf:Elm.Signal.timeOf}}();(function(){var e=function(e){for(var b in e)Elm.Prelude[b]=e[b]};e(Elm.Color);e(Elm.Text);e(Elm.Graphics);e(Elm.Time);show=Value.show})();
112−Elm.Dict=function(){function e(a){return function(b){return function(c){return function(e){return function(d){return["RBNode",a,b,c,e,d]}}}}}function k(a){a:{switch(a[0]){case "RBEmpty":throw"(min RBEmpty) is not defined";case "RBNode":switch(a[4][0]){case "RBEmpty":a=["Tuple2",a[2],a[3]];break a}a=k(a[4]);break a}throw"Non-exhaustive pattern match in case";}return a}function b(a){return function(c){var e;a:{switch(c[0]){case "RBEmpty":e=w;break a;case "RBNode":e=function(){switch(q(a)(c[2])[0]){case "EQ":return A(c[3]);
113−case "GT":return b(a)(c[5]);case "LT":return b(a)(c[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";}return e}}function d(a){return function(b){return function(c){var e;a:{switch(c[0]){case "RBEmpty":e=a;break a;case "RBNode":e=function(){switch(q(b)(c[2])[0]){case "EQ":return c[3];case "GT":return d(a)(b)(c[5]);case "LT":return d(a)(b)(c[4])}throw"Non-exhaustive pattern match in case";}();break a}throw"Non-exhaustive pattern match in case";
114−}return e}}}function j(a){return function(c){return F(b(a)(c))}}function a(a){a:{switch(a[0]){case "RBNode":switch(a[5][0]){case "RBNode":a=e(a[1])(a[5][2])(a[5][3])(e(B)(a[2])(a[3])(a[4])(a[5][4]))(a[5][5]);break a}}throw"rotateLeft of a node without enough children";}return a}function m(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":a=e(a[1])(a[4][2])(a[4][3])(a[4][4])(e(B)(a[2])(a[3])(a[4][5])(a[5]));break a}}throw"rotateRight of a node without enough children";}return a}function g(a){a:{switch(a[0]){case "Black":a=
115−B;break a;case "Red":a=E;break a}throw"Non-exhaustive pattern match in case";}return a}function l(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[5][0]){case "RBNode":a=e(g(a[1]))(a[2])(a[3])(e(g(a[4][1]))(a[4][2])(a[4][3])(a[4][4])(a[4][5]))(e(g(a[5][1]))(a[5][2])(a[5][3])(a[5][4])(a[5][5]));break a}}}throw"color_flip called on a RBEmpty or RBNode with a RBEmpty child";}return a}function h(b){a:switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":b=
116−a(b);break a}}}a:switch(b[0]){case "RBNode":switch(b[4][0]){case "RBNode":switch(b[4][1][0]){case "Red":switch(b[4][4][0]){case "RBNode":switch(b[4][4][1][0]){case "Red":b=m(b);break a}}}}}a:switch(b[0]){case "RBNode":switch(b[4][0]){case "RBNode":switch(b[4][1][0]){case "Red":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":b=l(b);break a}}}}}return b}function c(a){a:switch(a[0]){case "RBNode":switch(a[1][0]){case "Red":a=e(E)(a[2])(a[3])(a[4])(a[5]);break a}}return a}function f(a){return function(b){return function(d){var f=
117−function(c){var d;a:{switch(c[0]){case "RBEmpty":d=e(B)(a)(b)(z)(z);break a;case "RBNode":d=function(){switch(q(a)(c[2])[0]){case "EQ":return e(c[1])(c[2])(b)(c[4])(c[5]);case "GT":return e(c[1])(c[2])(c[3])(c[4])(f(c[5]));case "LT":return e(c[1])(c[2])(c[3])(f(c[4]))(c[5])}throw"Non-exhaustive pattern match in case";}();d=h(d);break a}throw"Non-exhaustive pattern match in case";}return d};return c(f(d))}}}function v(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][1][0]){case "Red":a=
118−!0;break a}}}a=!1}return a}function n(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBNode":switch(a[4][4][0]){case "RBNode":switch(a[4][4][1][0]){case "Red":a=!0;break a}}}}a=!1}return a}function p(b){if(x(v(b))&&x(n(b))){b=l(b);a:switch(b[0]){case "RBNode":b:switch(b[5][0]){case "RBNode":switch(b[5][4][0]){case "RBNode":switch(b[5][4][1][0]){case "Red":b=l(a(e(b[1])(b[2])(b[3])(b[4])(m(b[5]))));break b}}}break a}}return b}function r(a){return function(b){var d=function(b){a:{switch(b[0]){case "RBEmpty":b=
119−z;break a;case "RBNode":if("LT"===q(a)(b[2])[0])b:{b=p(b);switch(b[0]){case "RBEmpty":throw"delLT on RBEmpty";case "RBNode":b=h(e(b[1])(b[2])(b[3])(d(b[4]))(b[5]));break b}break}else{var f=v(b)?m(b):b,g;b:{switch(f[0]){case "RBNode":switch(f[5][0]){case "RBEmpty":g=D(a,f[2]);break b}}g=!1}if(g)b=f[4];else{f=x;b:{switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][1][0]){case "Red":g=!0;break b}}}g=!1}if(f=f(g)){f=x;b:{switch(b[0]){case "RBNode":switch(b[5][0]){case "RBNode":switch(b[5][4][0]){case "RBNode":switch(b[5][4][1][0]){case "Red":g=
120−!0;break b}}}}g=!1}f=f(g)}f&&(b=l(b),b=n(b)?l(m(b)):b);b:{switch(b[0]){case "RBNode":f=D(a,b[2]);break b}f=!1}if(f)b:{switch(b[0]){case "RBEmpty":throw"delEQ called on a RBEmpty";case "RBNode":g=k(b[5]);c:{switch(g[0]){case "Tuple2":f=g[1];break c}break}c:{switch(g[0]){case "Tuple2":g=g[2];break c}break}var f=e(b[1])(f)(g)(b[4]),j=function(a){a:{switch(a[0]){case "RBNode":switch(a[4][0]){case "RBEmpty":a=z;break a}}b:{a=p(a);switch(a[0]){case "RBEmpty":a=z;break b;case "RBNode":a=h(e(a[1])(a[2])(a[3])(j(a[4]))(a[5]));
121−break b}throw"Non-exhaustive pattern match in case";}}return a};b=c(j(b[5]));b=h(f(b));break b}break}else b:{switch(b[0]){case "RBEmpty":throw"delGT called on a RBEmpty";case "RBNode":b=h(e(b[1])(b[2])(b[3])(b[4])(d(b[5])));break b}break}}}break a}throw"Non-exhaustive pattern match in case";}return b};return j(a)(b)?c(d(b)):b}}function y(a){return function(b){a:{switch(b[0]){case "RBEmpty":b=z;break a;case "RBNode":b=e(b[1])(b[2])(a(b[3]))(y(a)(b[4]))(y(a)(b[5]));break a}throw"Non-exhaustive pattern match in case";
122−}return b}}function s(a){return function(b){return function(c){a:{switch(c[0]){case "RBEmpty":c=b;break a;case "RBNode":c=s(a)(a(c[2])(c[3])(s(a)(b)(c[4])))(c[5]);break a}throw"Non-exhaustive pattern match in case";}return c}}}function u(a){return function(b){return function(c){a:{switch(c[0]){case "RBEmpty":c=b;break a;case "RBNode":c=u(a)(a(c[2])(c[3])(u(a)(b)(c[5])))(c[4]);break a}throw"Non-exhaustive pattern match in case";}return c}}}var q=Elm.Prelude.compare,t=Elm.Prelude.uncurry,w=Elm.Prelude.Nothing,
123−A=Elm.Prelude.Just,x=Elm.Prelude.not,D=Elm.Prelude.eq,F=Elm.Maybe.isJust,B=["Red"],E=["Black"],z=["RBEmpty"],C=z;return{$op:{},empty:C,lookup:b,findWithDefault:d,member:j,insert:f,singleton:function(a){return function(b){return f(a)(b)(z)}},remove:r,map:y,foldl:s,foldr:u,union:function(a){return function(b){return s(f)(b)(a)}},intersect:function(a){return function(b){return s(function(a){return function(c){return function(d){return j(a)(b)?f(a)(c)(d):d}}})(C)(a)}},diff:function(a){return function(b){return s(function(a){return function(){return function(b){return r(a)(b)}}})(a)(b)}},
124−keys:function(a){return u(function(a){return function(){return function(b){return["Cons",a,b]}}})(["Nil"])(a)},values:function(a){return u(function(){return function(a){return function(b){return["Cons",a,b]}}})(["Nil"])(a)},toList:function(a){return u(function(a){return function(b){return function(c){return["Cons",["Tuple2",a,b],c]}}})(["Nil"])(a)},fromList:function(a){return Elm.List.foldl(t(f))(C)(a)}}}();
125−Elm.Set=function(){var e=Elm.Dict.empty,k=Elm.Dict.remove,b=Elm.Dict.member,d=Elm.Dict.union,j=Elm.Dict.intersect,a=Elm.Dict.diff,m=Elm.Dict.keys,g=Elm.List.foldl(function(a){return function(b){return Elm.Dict.insert(a)(["Tuple0"])(b)}})(e);return{empty:e,singleton:function(a){return Elm.Dict.singleton(a)(["Tuple0"])},insert:function(a){return Elm.Dict.insert(a)(["Tuple0"])},remove:k,member:b,union:d,intersect:j,diff:a,toList:m,fromList:g,foldl:function(a){return Elm.Dict.foldl(function(b){return function(){return function(c){return a(b)(c)}}})},
126−foldr:function(a){return Elm.Dict.foldr(function(b){return function(){return function(c){return a(b)(c)}}})},map:function(a){return function(b){b=m(b);return g(Elm.List.map(a)(b))}}}}();
127−(function(){try{var e={};for(this.i in Elm)eval("var "+this.i+"=Elm[this.i];");if(Elm.Automaton)throw"Module name collision, 'Automaton' is already defined.";Elm.Automaton=function(){function b(a){return["Automaton",a]}function d(a){return b(function(b){var c=unzip(map(function(a){a:{switch(a[0]){case "Automaton":a=a[1](b);break a}throw"Non-exhaustive pattern match in case";}return a})(a)),e;a:{switch(c[0]){case "Tuple2":e=c[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(c[0]){case "Tuple2":c=
128−c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",e,d(c)]})}function j(a){return b(function(b){return["Tuple2",a(b),j(a)]})}function a(c){return function(d){return b(function(b){b=d(b)(c);return["Tuple2",b,a(b)(d)]})}}function k(a){return function(c){return b(function(b){var d=c(b)(a);a:{switch(d[0]){case "Tuple2":b=d[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(d[0]){case "Tuple2":d=d[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",
129−b,k(d)(c)]})}}function g(a){return function(b){a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":b=["Tuple2",a[1]-b[1],a[2]-b[2]];break b}break}break a}throw"Non-exhaustive pattern match in case";}return b}}function l(a){return function(b){var c;a:{switch(a[0]){case "Tuple2":b:{switch(b[0]){case "Tuple2":var d=function(a){return["Tuple2",b[2],["Tuple2",a,b[2]]]};c=function(){switch(b[1][0]){case "DragFrom":var c;a[1]?c=["Tuple2",uncurry(move)(g(a[2])(b[1][1]))(b[2]),["Tuple2",["DragFrom",
130−b[1][1]],b[2]]]:(c=uncurry(move)(g(a[2])(b[1][1]))(b[2]),c=["Tuple2",c,["Tuple2",f,c]]);return c;case "Ignore":return d(a[1]?v:f);case "Listen":return d(not(a[1])?f:isWithin(a[2])(b[2])?["DragFrom",a[2]]:v)}throw"Non-exhaustive pattern match in case";}();break b}break}break a}throw"Non-exhaustive pattern match in case";}return c}}try{if(!(Elm.Prelude instanceof Object))throw"module not found";}catch(h){throw"Module 'Prelude' is missing. Compile with --make flag or load missing module in a separate JavaScript file.";
131−}var c={};for(this.i in Elm.Prelude)c[this.i]||eval("var "+this.i+" = Elm.Prelude[this.i];");var f=["Listen"],v=["Ignore"];e[">>>"]=function(a){return function(c){var d;a:{switch(a[0]){case "Automaton":d=a[1];break a}throw"Non-exhaustive pattern match in case";}var f;a:{switch(c[0]){case "Automaton":f=c[1];break a}throw"Non-exhaustive pattern match in case";}return b(function(a){a=d(a);var b;a:{switch(a[0]){case "Tuple2":b=a[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(a[0]){case "Tuple2":a=
132−a[2];break a}throw"Non-exhaustive pattern match in case";}var c=f(b);a:{switch(c[0]){case "Tuple2":b=c[1];break a}throw"Non-exhaustive pattern match in case";}a:{switch(c[0]){case "Tuple2":c=c[2];break a}throw"Non-exhaustive pattern match in case";}return["Tuple2",b,e[">>>"](a)(c)]})}};e["<<<"]=function(a){return function(b){return e[">>>"](b)(a)}};e["^>>"]=function(a){return function(b){return e[">>>"](j(a))(b)}};e[">>^"]=function(a){return function(b){return e[">>>"](a)(j(b))}};e["^<<"]=function(a){return function(b){return e[">>>"](b)(j(a))}};
133−e["<<^"]=function(a){return function(b){return e[">>>"](j(b))(a)}};c=a(0)(function(){return function(a){return 1+a}});return{$op:{">>>":e[">>>"],"<<<":e["<<<"],"^>>":e["^>>"],">>^":e[">>^"],"^<<":e["^<<"],"<<^":e["<<^"]},run:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=lift(fst)(foldp_(function(a){return function(b){a:{switch(b[0]){case "Tuple2":switch(b[2][0]){case "Automaton":b=b[2][1](a);break a}}throw"Non-exhaustive pattern match in case";}return b}})(a[1])(b));break a}throw"Non-exhaustive pattern match in case";
134−}return b}},step:function(a){return function(b){a:{switch(a[0]){case "Automaton":b=a[1](b);break a}throw"Non-exhaustive pattern match in case";}return b}},combine:d,pure:j,init:a,init_:k,count:c,draggable:function(a){return k(["Tuple2",f,a])(l)}}}();Elm.main=function(){return Elm.Automaton.main}}catch(k){Elm.main=function(){document.body.innerHTML=Elm.Text.monospace('<br/><h2>Your browser may not be supported. Are you using a modern browser?</h2><br/><span style="color:grey">Runtime Error in Automaton module:<br/>'+
135−k+"</span>");throw k;}}})();
elm/src/Gen/CompileToJS.hsdeleted−323
@@ -1,323 +0,0 @@
1−module CompileToJS (showErr, jsModule) where
2−
3−import Ast
4−import Context
5−import Control.Arrow (first,second)
6−import Control.Monad (liftM,(<=<),join,ap)
7−import Data.Char (isAlpha,isDigit)
8−import Data.List (intercalate,sortBy,inits,foldl')
9−import qualified Data.Map as Map
10−import Data.Either (partitionEithers)
11−import qualified Text.Pandoc as Pan
12−
13−import Initialize
14−import Rename (derename)
15−import Cases
16−import Guid
17−import Parse.Library (isOp)
18−import Rename (deprime)
19−
20−showErr :: String -> String
21−showErr err = mainEquals $ "Elm.Graphics.text(Elm.Text.monospace(" ++ msg ++ "))"
22− where msg = show . concatMap (++"<br>") . lines $ err
23−
24−indent = concatMap f
25− where f '\n' = "\n "
26− f c = [c]
27−
28−parens s = "(" ++ s ++ ")"
29−braces s = "{" ++ s ++ "}"
30−jsList ss = "["++ intercalate "," ss ++"]"
31−jsFunc args body = "function(" ++ args ++ "){" ++ indent body ++ "}"
32−assign x e = "\nvar " ++ x ++ "=" ++ e ++ ";"
33−ret e = "\nreturn "++ e ++";"
34−iff a b c = a ++ "?" ++ b ++ ":" ++ c
35−quoted s = "'" ++ concatMap f s ++ "'"
36− where f '\n' = "\\n"
37− f '\'' = "\\'"
38− f '\t' = "\\t"
39− f '\"' = "\\\""
40− f '\\' = "\\\\"
41− f c = [c]
42−
43−mainEquals s = globalAssign "Elm.main" (jsFunc "" (ret s))
44−globalAssign m s = "\n" ++ m ++ "=" ++ s ++ ";"
45−
46−tryBlock escapees names e =
47− concat [ "\ntry{\n" ++ e ++ "\n} catch (e) {"
48− , "\nElm.main=function() {"
49− , "\nvar msg = ('<br/><h2>Your browser may not be supported. " ++
50− "Are you using a modern browser?</h2>' +" ++
51− " '<br/><span style=\"color:grey\">Runtime Error in " ++
52− intercalate "." names ++ " module:<br/>' + e + '" ++ msg ++ "</span>');"
53− , "\ndocument.body.innerHTML = Elm.Text.monospace(msg);"
54− , "throw e;"
55− , "};}"
56− ]
57− where msg | escapees /= [] = concat [ "<br/><br/>The problem may stem from an improper usage of:<br/>"
58− , intercalate ", " $ map (concatMap escape) escapees ]
59− | otherwise = ""
60− escape '\'' = "\\'"
61− escape '"' = "\\\""
62− escape c = [c]
63−
64−
65−jsModule (escapees, Module names exports imports stmts) =
66− tryBlock escapees (tail modNames) $ concat
67− [ concatMap (\n -> globalAssign n $ n ++ " || {}") .
68− map (intercalate ".") . drop 2 . inits $
69− take (length modNames - 1) modNames
70− , "\nif (" ++ modName ++ ") throw new Error(\"Module name collision, '" ++
71− intercalate "." (tail modNames) ++ "' is already defined.\"); "
72− , globalAssign modName $ jsFunc "" (defs ++ includes ++ body ++ export) ++ "()"
73− , mainEquals $ modName ++ ".main" ]
74− where modNames = if null names then ["Elm", "Main"]
75− else "Elm" : names
76− modName = intercalate "." modNames
77− includes = concatMap jsImport $ map (first ("Elm."++)) imports
78− body = stmtsToJS stmts
79− export = getExports exports stmts
80− exps = if null exports then ["main"] else exports
81− defs = concat [ assign "$op" "{}"
82− , "\nfor(Elm['i'] in Elm){eval('var '+Elm['i']+'=Elm[Elm.i];');}" ]
83−
84−getExports names stmts = ret . braces $ intercalate ",\n" (op : map fnPair fns)
85− where exNames n = either derename id n `elem` names
86− exports | null names = concatMap get stmts
87− | otherwise = filter exNames (concatMap get stmts)
88−
89− (fns,ops) = partitionEithers exports
90−
91− opPair op = "'" ++ op ++ "' : $op['" ++ op ++ "']"
92− fnPair fn = let fn' = derename fn in fn' ++ ":" ++ fn
93−
94− op = ("$op : "++) . braces . intercalate ", " $ map opPair ops
95−
96− get' (FnDef x _ _) = Left x
97− get' (OpDef op _ _ _) = Right op
98− get s = case s of Definition d -> [ get' d ]
99− Datatype _ _ tcs -> map (Left . fst) tcs
100− ImportEvent _ _ x _ -> [ Left x ]
101− ExportEvent _ _ _ -> []
102− TypeAlias _ _ _ -> []
103− TypeAnnotation _ _ -> []
104−
105−
106−jsImport (modul, how) =
107− concat [ "\ntry{\n if (!(" ++ modul ++ " instanceof Object)) throw new Error('module not found');\n} catch(e) {\n throw new Error(\"Module '"
108− , drop 1 (dropWhile (/='.') modul)
109− , "' is missing. Compile with --make flag or load missing "
110− , "module in a separate JavaScript file.\");\n}" ] ++
111− jsImport' (modul, how)
112−
113−jsImport' (modul, As name) = assign name modul
114−jsImport' (modul, Importing vs) = concatMap def vs
115− where def [] = []
116− def (o:p) | isOp o = let v = "$op['" ++ o:p ++ "']" in
117− "\n" ++ v ++ " = " ++ modul ++ "." ++ v ++ ";"
118− | otherwise = let v = deprime (o:p) in
119− assign v $ modul ++ "." ++ v
120−
121−jsImport' (modul, Hiding vs) =
122− concat [ assign "hiddenVars" . ("{"++) . (++"}") . intercalate "," $
123− map (\v -> v ++ ":true") (map deprime vs)
124− , "\nfor (Elm['i'] in " ++ modul ++ ") "
125− , braces . indent . concat $
126− [ "\nif (hiddenVars[Elm['i']]) continue;"
127− , "\neval('var ' + Elm['i'] + ' = "
128− , modul, "[Elm.i];');" ]
129− ]
130−
131−stmtsToJS :: [Statement] -> String
132−stmtsToJS stmts = run (concat `liftM` mapM toJS (sortBy cmpStmt stmts))
133− where cmpStmt s1 s2 = compare (valueOf s1) (valueOf s2)
134− valueOf s = case s of
135− Datatype _ _ _ -> 1
136− ImportEvent _ _ _ _ -> 2
137− Definition (FnDef f [] _) ->
138− if derename f == "main" then 5 else 4
139− Definition _ -> 3
140− ExportEvent _ _ _ -> 6
141− TypeAlias _ _ _ -> 0
142− TypeAnnotation _ _ -> 0
143−
144−class ToJS a where
145− toJS :: a -> GuidCounter String
146−
147−instance ToJS Def where
148− toJS (FnDef x [] e) = assign x `liftM` toJS' e
149− toJS (FnDef f (a:as) e) =
150− do body <- toJS' (foldr (\x e -> noContext (Lambda x e)) e as)
151− return $ concat ["\nfunction ",f,parens a, braces . indent $ ret body]
152− toJS (OpDef op a1 a2 e) =
153− do body <- toJS' (foldr (\x e -> noContext (Lambda x e)) e [a1,a2])
154− return $ concat [ "\n$op['", op, "'] = ", body, ";" ]
155−
156−instance ToJS Statement where
157− toJS (Definition d) = toJS d
158− toJS (Datatype _ _ tcs) = concat `liftM` mapM (toJS . toDef) tcs
159− where toDef (name,args) = Definition . FnDef name vars . noContext $
160− Data (derename name) (map (noContext . Var) vars)
161− where vars = map (('a':) . show) [1..length args]
162− toJS (ImportEvent js base elm _) =
163− do v <- toJS' base
164− return $ concat [ "\nvar " ++ elm ++ "=Elm.Signal.constant(" ++ v ++ ");"
165− , "\nValue.addListener(document, '" ++ js
166− , "', function(e) { Dispatcher.notify(" ++ elm
167− , ".id, e.value); });" ]
168− toJS (ExportEvent js elm _) =
169− return $ concat [ "\nlift(function(v) { "
170− , "var e = document.createEvent('Event');"
171− , "e.initEvent('", js, "', true, true);"
172− , "e.value = v;"
173− , "document.dispatchEvent(e); return v; })(", elm, ");" ]
174− toJS (TypeAnnotation _ _) = return ""
175− toJS (TypeAlias _ _ _) = return ""
176−
177−toJS' :: CExpr -> GuidCounter String
178−toJS' (C txt span expr) =
179− case expr of
180− MultiIf ps -> multiIfToJS span ps
181− Case e cases -> caseToJS span e cases
182− _ -> toJS expr
183−
184−remove x e = "elmRecordRemove('" ++ x ++ "', " ++ e ++ ")"
185−addField x v e = "elmRecordInsert('" ++ x ++ "', " ++ v ++ ", " ++ e ++ ")"
186−setField fs e = "elmRecordReplace(" ++ jsList (map f fs) ++ ", " ++ e ++ ")"
187− where f (x,v) = "['" ++ x ++ "'," ++ v ++ "]"
188−access x e = parens e ++ "." ++ x
189−makeRecord kvs = record `liftM` collect kvs
190− where
191− combine r (k,v) = Map.insertWith (++) k v r
192− collect = liftM (foldl' combine Map.empty) . mapM prep
193− prep (k, as, e@(C t s _)) =
194− do v <- toJS' (foldr (\x e -> C t s $ Lambda x e) e as)
195− return (k,[v])
196− fields fs =
197− braces ("\n "++intercalate ",\n " (map (\(k,v) -> k++":"++v) fs))
198− hidden = fields . map (second jsList) .
199− filter (not . null . snd) . Map.toList . Map.map tail
200− record kvs = fields . (("_", hidden kvs) :) . Map.toList . Map.map head $ kvs
201−
202−
203−instance ToJS Expr where
204− toJS expr =
205− case expr of
206− IntNum n -> return $ show n
207− FloatNum n -> return $ show n
208− Var x -> return $ x
209− Chr c -> return $ quoted [c]
210− Str s -> return $ "Value.str" ++ parens (quoted s)
211− Boolean b -> return $ if b then "true" else "false"
212− Range lo hi -> jsRange `liftM` toJS' lo `ap` toJS' hi
213− Access e x -> access x `liftM` toJS' e
214− Remove e x -> remove x `liftM` toJS' e
215− Insert e x v -> addField x `liftM` toJS' v `ap` toJS' e
216− Modify e fs -> do fs' <- (mapM (\(x,v) -> (,) x `liftM` toJS' v) fs)
217− setField fs' `liftM` toJS' e
218− Record fs -> makeRecord fs
219− Binop op e1 e2 -> binop op `liftM` toJS' e1 `ap` toJS' e2
220−
221− If eb et ef ->
222− parens `liftM` (iff `liftM` toJS' eb `ap` toJS' et `ap` toJS' ef)
223−
224− Lambda v e -> liftM (jsFunc v . ret) (toJS' e)
225−
226− App (C _ _ (Var "toText")) (C _ _ (Str s)) ->
227− return $ "toText" ++ parens (quoted s)
228−
229− App (C _ _ (Var "link")) (C _ _ (Str s)) ->
230− return $ "link(" ++ quoted s ++ ")"
231−
232− App (C _ _ (Var "plainText")) (C _ _ (Str s)) ->
233− return $ "plainText(" ++ quoted s ++ ")"
234−
235− App e1 e2 -> (++) `liftM` (toJS' e1) `ap` (parens `liftM` toJS' e2)
236− Let defs e -> jsLet defs e
237− Data name es -> (\ss -> jsList $ quoted name : ss) `liftM` mapM toJS' es
238−
239− Markdown doc -> return $ "text('" ++ pad ++ md ++ pad ++ "')"
240− where pad = "<div style=\"height:0;width:0;\">&nbsp;</div>"
241− md = formatMarkdown $ Pan.writeHtmlString Pan.def doc
242−
243−formatMarkdown = concatMap f
244− where f '\'' = "\\'"
245− f '\n' = "\\n"
246− f '"' = "\""
247− f c = [c]
248−
249−multiIfToJS span ps = format `liftM` mapM f ps
250− where format cs = foldr (\c e -> parens $ c ++ " : " ++ e) err cs
251− err = concat [ "(function(){throw new Error(\"Non-exhaustive "
252− , "multi-way-if expression (", show span, ")\");}())" ]
253− f (b,e) = do b' <- toJS' b
254− e' <- toJS' e
255− return (b' ++ " ? " ++ e')
256−
257−jsLet defs e' = do
258− body <- (++) `liftM` jsDefs defs `ap` (ret `liftM` toJS' e')
259− return $ jsFunc "" body ++ "()"
260−
261−jsDefs defs = concat `liftM` mapM toJS (sortBy f defs)
262− where f a b = compare (valueOf a) (valueOf b)
263− valueOf (FnDef _ args _) = min 1 (length args)
264− valueOf (OpDef _ _ _ _) = 1
265−
266−caseToJS span e ps = do
267− match <- caseToMatch ps
268− e' <- toJS' e
269− (match',stmt) <- case (match,e) of
270− (Match name _ _, C _ _ (Var x)) -> return (matchSubst [(name,x)] match, "")
271− (Match name _ _, _) -> return (match, assign name e')
272− _ -> liftM (\n -> (match, e')) guid
273− matches <- matchToJS span match'
274− return $ concat [ "function(){", stmt, matches, "}()" ]
275−
276−matchToJS span (Match name clauses def) = do
277− cases <- concat `liftM` mapM (clauseToJS span name) clauses
278− finally <- matchToJS span def
279− return $ concat [ "\nswitch(", name, "[0]){", indent cases, "\n}", finally ]
280−matchToJS span Fail = return ("\nthrow new Error(\"Non-exhaustive pattern match " ++
281− "in case expression (" ++ show span ++ ")\");")
282−matchToJS span Break = return "break;"
283−matchToJS span (Other e) = ret `liftM` toJS' e
284−matchToJS span (Seq ms) = concat `liftM` mapM (matchToJS span) ms
285−
286−clauseToJS span var (Clause name vars e) = do
287− let vars' = map (\n -> var ++ "[" ++ show n ++ "]") [ 1 .. length vars ]
288− s <- matchToJS span $ matchSubst (zip vars vars') e
289− return $ concat [ "\ncase ", quoted name, ":", s ]
290−
291−jsNil = "[\"Nil\"]"
292−jsCons e1 e2 = jsList [ quoted "Cons", e1, e2 ]
293−jsRange e1 e2 = (++"()") . jsFunc "" $
294− assign "lo" e1 ++ assign "hi" e2 ++ assign "lst" jsNil ++
295− "if(lo<=hi){do{lst=" ++ (jsCons "hi" "lst") ++ "}while(hi-->lo)}" ++
296− ret "lst"
297−
298−binop (o:p) e1 e2
299− | isAlpha o || '_' == o = (o:p) ++ parens e1 ++ parens e2
300− | otherwise =
301− let ops = ["+","-","*","/","&&","||"] in
302− case o:p of
303− "::" -> jsCons e1 e2
304− "++" -> append e1 e2
305− "$" -> e1 ++ parens e2
306− "." -> jsFunc "x" . ret $ e1 ++ parens (e2 ++ parens "x")
307− "^" -> "Math.pow(" ++ e1 ++ "," ++ e2 ++ ")"
308− "==" -> "eq(" ++ e1 ++ "," ++ e2 ++ ")"
309− "/=" -> "not(eq(" ++ e1 ++ "," ++ e2 ++ "))"
310− "<" -> "(compare(" ++ e1 ++ ")(" ++ e2 ++ ")[0] === 'LT')"
311− ">" -> "(compare(" ++ e1 ++ ")(" ++ e2 ++ ")[0] === 'GT')"
312− "<=" -> "function() { var ord = compare(" ++ e1 ++ ")(" ++
313− e2 ++ ")[0]; return ord==='LT' || ord==='EQ'; }()"
314− ">=" -> "function() { var ord = compare(" ++ e1 ++ ")(" ++
315− e2 ++ ")[0]; return ord==='GT' || ord==='EQ'; }()"
316− "<~" -> "lift" ++ parens e1 ++ parens e2
317− "~" -> "lift2(function(f){return function(x){return f(x);};})" ++
318− parens e1 ++ parens e2
319− _ | elem (o:p) ops -> parens (e1 ++ (o:p) ++ e2)
320− | otherwise -> concat [ "$op['", o:p, "']"
321− , parens e1, parens e2 ]
322−
323−append e1 e2 = "Value.append" ++ parens (e1 ++ "," ++ e2)
elm/src/Gen/GenerateHtml.hsdeleted−89
@@ -1,89 +0,0 @@
1−{-# LANGUAGE OverloadedStrings #-}
2−module GenerateHtml (generateHtml,
3− body, css, widgetBody,
4− modulesToHtml, linkedHtml,
5− JSStyle (..)
6− ) where
7−
8−import Data.List (intercalate)
9−import Text.Blaze (preEscapedToMarkup)
10−import Text.Blaze.Html (Html)
11−import qualified Text.Blaze.Html5 as H
12−import Text.Blaze.Html5 ((!))
13−import qualified Text.Blaze.Html5.Attributes as A
14−
15−import Text.Jasmine (minify)
16−import qualified Data.ByteString.Lazy.Char8 as BS
17−
18−import Ast
19−import Initialize
20−import CompileToJS
21−import ExtractNoscript
22−
23−css = H.style ! A.type_ "text/css" $ preEscapedToMarkup
24− ("html,head,body { padding:0; margin:0; }\
25− \body { font-family: helvetica, arial, sans-serif; }" :: String)
26−
27−data JSStyle = Minified | Readable
28−
29−makeScript :: JSStyle -> Either String String -> H.Html
30−makeScript _ (Left s) =
31− H.script ! A.type_ "text/javascript" ! A.src (H.toValue s) $ ""
32−makeScript jsStyle (Right s) =
33− H.script ! A.type_ "text/javascript" $ preEscapedToMarkup content
34− where content = case jsStyle of
35− Minified -> BS.unpack . minify . BS.pack $ s
36− Readable -> s
37−
38−-- |This function compiles Elm code into simple HTML.
39−--
40−-- Usage example:
41−--
42−-- > generateHtml "/elm-min.js" "Some title" [elmFile|elm-source/somePage.elm|]
43−generateHtml :: String -- ^ Location of elm-min.js as expected by the browser
44− -> String -- ^ The page title
45− -> String -- ^ The elm source code.
46− -> Html
47−generateHtml libLoc title source =
48− case buildFromSource source of
49− Left err -> createHtml Readable libLoc title (Right $ showErr err) (H.noscript "")
50− Right (escs, modul) -> modulesToHtml Readable title libLoc [] True [(escs,modul)]
51−
52−
53−modulesToHtml jsStyle title libLoc jss nscrpt pairs =
54− createHtml jsStyle libLoc title' js noscript
55− where modules = map snd pairs
56− js = Right $ jss ++ concatMap jsModule pairs
57− noscript = if nscrpt then extractNoscript $ last modules else ""
58− title' = if null title then altTitle else title
59− altTitle = (\(Module names _ _ _) -> intercalate "." names) $
60− last modules
61−
62−
63−linkedHtml rtLoc jsLoc modules =
64− createHtml Readable rtLoc title (Left jsLoc) (H.noscript "")
65− where title = (\(Module names _ _ _) -> intercalate "." names) $
66− snd (last modules)
67−
68−
69−createHtml jsStyle libLoc title js noscript =
70− H.docTypeHtml $ do
71− H.head $ do
72− H.meta ! A.charset "UTF-8"
73− H.title . H.toHtml $ title
74− css
75− H.body $ do
76− makeScript Readable (Left libLoc)
77− makeScript jsStyle js
78− body noscript
79−
80−body noscript = do
81− H.div ! A.id "widthChecker" ! A.style "width:100%; height:1px; position:absolute; top:-1px;" $ ""
82− H.div ! A.id "content" $ ""
83− H.script ! A.type_ "text/javascript" $ "Dispatcher.initialize()"
84− H.noscript $ preEscapedToMarkup noscript
85−
86−widgetBody noscript = do
87− H.div ! A.id "widthChecker" ! A.style "width:100%; height:1px; position:absolute; top:-1px;" $ ""
88− H.div ! A.id "content" $ ""
89− H.noscript $ preEscapedToMarkup noscript
elm/src/Initialize.hsdeleted−95
@@ -1,95 +0,0 @@
1−module Initialize (build,buildFromSource) where
2−
3−import Control.Applicative ((<$>))
4−import Control.Monad.Error
5−import Data.List (lookup)
6−
7−import Ast
8−import Data.Either (lefts,rights)
9−import Data.List (intercalate,partition)
10−import Parse.Parser (parseProgram)
11−import Rename
12−import Types.Types ((-:))
13−import Types.Hints (hints)
14−import Types.Unify
15−import Types.Alias
16−import Optimize
17−
18−checkMistakes :: Module -> Either String Module
19−checkMistakes modul@(Module name ex im stmts) =
20− case mistakes stmts of
21− m:ms -> Left (unlines (m:ms))
22− [] -> return modul
23−
24−checkTypes :: Module -> Either String ([String], Module)
25−checkTypes (Module name ex im stmts) =
26− let stmts' = dealias stmts
27− modul = Module name ex im stmts'
28− in do (escapees, subs) <- unify hints modul
29− let im' | any ((=="Prelude") . fst) im = im
30− | otherwise = ("Prelude", Hiding []) : im
31− modul' = optimize . renameModule $ Module name ex im' stmts'
32− subs `seq` return (escapees, modul')
33−
34−check :: Module -> Either String ([String], Module)
35−check = checkMistakes >=> checkTypes
36−
37−buildFromSource :: String -> Either String ([String],Module)
38−buildFromSource = parseProgram >=> check
39−
40−build :: Bool -> FilePath -> IO (Either String ([String],[Module]))
41−build make root = do
42− proj <- parse make root
43− return $ do
44− ms <- proj
45− (escapeess, modules) <- unzip `liftM` mapM check ms
46− sortedModules <- (if make then sort else return) modules
47− return (concat escapeess, sortedModules)
48−
49−parse :: Bool -> FilePath -> IO (Either String [Module])
50−parse make root = parseProject [] make root
51−
52−parseProject :: [FilePath] -> Bool -> FilePath -> IO (Either String [Module])
53−parseProject seen make root = do
54− txt <- readFile root
55− case parseProgram txt of
56− Left err -> return (Left err)
57− Right modul@(Module names exs ims stmts) ->
58− let allDeps = map toFilePath (getDeps modul)
59− newDeps = if make then filter (`notElem` seen) allDeps else []
60− name = intercalate "." names
61− in do ps <- mapM (parseProject (name : seen ++ newDeps) make) newDeps
62− return $ case unlines (lefts ps) of
63− c:cs -> Left (c:cs)
64− _ -> Right (modul : concat (rights ps))
65−
66−toFilePath :: String -> FilePath
67−toFilePath modul = map (\c -> if c == '.' then '/' else c) modul ++ ".elm"
68−
69−getDeps :: Module -> [String]
70−getDeps (Module _ _ is _) = filter (`notElem` builtInModules) (map fst is)
71− where
72− builtInModules =
73− ["List","Char","Either","Maybe","Dict","Set","Automaton","Date",
74− "Signal","Mouse","Keyboard.Raw","Keyboard","Touch",
75− "WebSocket","Window","Time","HTTP","Input","Random",
76− "Graphics","Text","Color","JavaScript",
77− "JavaScript.Experimental","Prelude","JSON"]
78−
79−
80−sort :: [Module] -> Either String [Module]
81−sort = go []
82− where
83− msg = "A cyclical or missing module dependency or was detected in: "
84− getName (Module names _ _ _) = intercalate "." names
85−
86− has name modul = name == getName modul
87− within ms name = any (has name) ms
88−
89− go :: [Module] -> [Module] -> Either String [Module]
90− go sorted [] = Right sorted
91− go sorted unsorted =
92− case partition (all (within sorted) . getDeps) unsorted of
93− ([],m:ms) -> Left (msg ++ intercalate ", " (map getName (m:ms)))
94− (srtd,unsrtd) -> go (sorted ++ srtd) unsrtd
95−
elm/src/Language/Elm.hsdeleted−82
@@ -1,82 +0,0 @@
1−{-# LANGUAGE TypeSynonymInstances, FlexibleInstances #-}
2−{- | This module exports the functions necessary for compiling Elm code into the
3− respective HTML, JS and CSS code.
4−
5− The type class @'ElmSource'@ requires an instance for all types that the Elm compiler
6− understands. The provided instances for String, Text and QuasiQuoted Elm source code
7− should be sufficient.
8−
9− The documentation for the Elm language is available at <http://elm-lang.org/Documentation.elm>,
10− and many interactive examples are available at <http://elm-lang.org/Examples.elm>
11−
12− Example implementations using Yesod and Happstack are available at <https://github.com/tazjin/Elm/tree/master/Examples>
13−-}
14−module Language.Elm (
15− ElmSource (..),
16− runtimeLocation
17− ) where
18−
19−import Data.Version (showVersion)
20−import CompileToJS
21−import ExtractNoscript
22−import GenerateHtml
23−import Initialize
24−import Text.Blaze.Html (Html)
25−import Language.Elm.Quasi
26−import Paths_Elm
27−
28−import qualified Data.Text as TS
29−import qualified Data.Text.Lazy as TL
30−
31−-- |The absolute path to Elm's runtime system.
32−runtimeLocation :: IO FilePath
33−runtimeLocation =
34− getDataFileName ("elm-runtime-" ++ showVersion version ++ ".js")
35−
36−class ElmSource a where
37− -- |This function compiles Elm code to three separate parts: HTML, CSS,
38− -- and JavaScript. The HTML is only the contents of the body, so the three
39− -- parts must be combined in a basic HTML skeleton.
40− toParts :: a -> (Html, Html, String)
41−
42− -- |This function compiles Elm code into a full HTML page.
43− toHtml :: String -- ^ Location of elm-min.js as expected by the browser
44− -> String -- ^ The page title
45− -> a -- ^ The elm source code
46− -> Html
47−
48−instance ElmSource String where
49− toParts = toPartsHelper
50− toHtml = generateHtml
51−
52−instance ElmSource Elm where
53− toParts = toPartsHelper . TL.unpack . renderElm
54− toHtml elmL title = generateHtml elmL title . TL.unpack . renderElm
55−
56−-- |Strict text
57−instance ElmSource TS.Text where
58− toParts = toPartsHelper . TS.unpack
59− toHtml elmL title = generateHtml elmL title . TS.unpack
60−
61−-- |Lazy text
62−instance ElmSource TL.Text where
63− toParts = toPartsHelper . TL.unpack
64− toHtml elmL title = generateHtml elmL title . TL.unpack
65−
66−-- | (urlRenderFn, urlRenderFn -> Elm)
67−instance ElmSource (t, t -> Elm) where
68− toParts (f, s) = toPartsHelper $ TL.unpack $ renderElm $ s f
69− toHtml elmL title (f, s) = generateHtml elmL title $ TL.unpack $ renderElm $ s f
70−
71−-- | to be used without URL interpolation
72−instance ElmSource (t -> Elm) where
73− toParts s = toPartsHelper $ TL.unpack $ renderElm $ s undefined
74− toHtml l t s = generateHtml l t $ TL.unpack $ renderElm $ s undefined
75−
76−
77−-- build helper to avoid boilerplate repetition
78−toPartsHelper :: String -> (Html, Html, String)
79−toPartsHelper source = (html, css, js)
80− where modul = buildFromSource source
81− js = either showErr jsModule modul
82− html = widgetBody $ either id (extractNoscript . snd) modul
elm/src/Types/Hints.hsdeleted−446
@@ -1,446 +0,0 @@
1−module Types.Hints (hints) where
2−
3−import Context
4−import Control.Arrow (first)
5−import Control.Monad (liftM,mapM)
6−import Types.Types
7−import Types.Substitutions (rescheme)
8−
9−ctx str = C (Just str) NoSpan
10−prefix pre xs = map (first (\x -> pre ++ "." ++ x)) xs
11−hasType t = map (-: t)
12−
13−
14−-------- Text and Elements --------
15−
16−textToText = [ "header", "italic", "bold", "underline"
17− , "overline", "strikeThrough", "monospace" ]
18−
19−textAttrs = [ "toText" -: string ==> text
20− , "Text.typeface" -: string ==> text ==> text
21− , "Text.link" -:: string ==> text ==> text
22− , numScheme (\t -> t ==> text ==> text) "Text.height"
23− ] ++ prefix "Text" (hasType (text ==> text) textToText)
24−
25−elements =
26− let iee = int ==> element ==> element in
27− [ "plainText" -: string ==> element
28− , "link" -:: string ==> element ==> element
29− , "flow" -: direction ==> listOf element ==> element
30− , "layers" -: listOf element ==> element
31− , "text" -: text ==> element
32− , "image" -: int ==> int ==> string ==> element
33− , "video" -: int ==> int ==> string ==> element
34− , "opacity" -: float ==> element ==> element
35− , "width" -: iee
36− , "height" -: iee
37− , "size" -: int ==> iee
38− , "widthOf" -: element ==> int
39− , "heightOf"-: element ==> int
40− , "sizeOf" -: element ==> pairOf int
41− , "color" -: color ==> element ==> element
42− , "container" -: int ==> int ==> position ==> element ==> element
43− , "spacer" -: int ==> int ==> element
44− , "rightedText" -: text ==> element
45− , "centeredText" -: text ==> element
46− , "justifiedText" -: text ==> element
47− , "asText" -:: a ==> element
48− , "collage" -: int ==> int ==> listOf form ==> element
49− , "fittedImage" -: int ==> int ==> string ==> element
50− ]
51−
52−directions = hasType direction ["up","down","left","right","inward","outward"]
53−positions =
54− hasType position ["topLeft","midLeft","bottomLeft","midTop","middle"
55− ,"midBottom","topRight","midRight","bottomRight"] ++
56− hasType (location ==> location ==> position)
57− ["topLeftAt","bottomLeftAt","middleAt","topRightAt","bottomRightAt"] ++
58− [ "absolute" -: int ==> location, "relative" -: float ==> location ]
59−
60−lineTypes = [ numScheme (\n -> listOf (pairOf n) ==> line) "line"
61− , numScheme (\n -> pairOf n ==> pairOf n ==> line) "segment"
62− , "customLine" -: listOf int ==> color ==> line ==> form
63− ] ++ hasType (color ==> line ==> form) ["solid","dashed","dotted"]
64−
65−shapes = [ twoNums (\n m -> listOf (pairOf n) ==> pairOf m ==> shape) "polygon"
66− , "filled" -: color ==> shape ==> form
67− , "outlined" -: color ==> shape ==> form
68− , "textured" -: string ==> shape ==> form
69− , "customOutline" -: listOf int ==> color ==> shape ==> form
70− ] ++ map (twoNums (\n m -> n ==> n ==> pairOf m ==> shape)) [ "ngon"
71− , "rect"
72− , "oval" ]
73−
74−collages = [ numScheme (\n -> pairOf n ==> element ==> form) "toForm"
75− , numScheme (\n -> string ==> n ==> n ==> pairOf n ==> form) "sprite"
76− , numScheme (\n -> n ==> n ==> form ==> form) "move"
77− , numScheme (\n -> n ==> form ==> form) "rotate"
78− , numScheme (\n -> n ==> form ==> form) "scale"
79− , numScheme (\n -> pairOf n ==> form ==> bool) "isWithin"
80− ]
81−
82−graphicsElement = prefix "Graphics"
83− (concat [elements,directions,positions,lineTypes,shapes,collages])
84−graphicsColor = prefix "Color" clrs
85− where clrs = [ numScheme (\n -> n ==> n ==> n ==> color) "rgb"
86− , numScheme (\n -> n ==> n ==> n ==> n ==> color) "rgba"
87− , "complement" -: color ==> color
88− ] ++ hasType color ["red","green","blue","black","white"
89− ,"yellow","cyan","magenta","grey","gray"]
90−
91−
92−-------- Foreign --------
93−
94−casts =
95− [ "castJSBoolToBool" -: jsBool ==> bool
96− , "castBoolToJSBool" -: bool ==> jsBool
97− , "castJSNumberToInt" -: jsNumber ==> int
98− , "castIntToJSNumber" -: int ==> jsNumber
99− , "castJSElementToElement" -: int ==> int ==> jsElement ==> element
100− , "castElementToJSElement" -: element ==> jsElement
101− , "castJSStringToString" -: jsString ==> string
102− , "castStringToJSString" -: string ==> jsString
103− , "castJSNumberToFloat" -: jsNumber ==> float
104− , "castFloatToJSNumber" -: float ==> jsNumber
105− ]
106−
107−castToTuple n = (,) name $ Forall [1..n] [] (jsTuple vs ==> tupleOf vs)
108− where vs = map VarT [1..n]
109− name = "castJSTupleToTuple" ++ show n
110−castToJSTuple n = (,) name $ Forall [1..n] [] (tupleOf vs ==> jsTuple vs)
111− where vs = map VarT [1..n]
112− name = "castTupleToJSTuple" ++ show n
113−
114−polyCasts =
115− map castToTuple [2..5] ++ map castToJSTuple [2..5] ++
116− [ "castJSArrayToList" -:: jsArray a ==> listOf a
117− , "castListToJSArray" -:: listOf a ==> jsArray a
118− ]
119−
120−javascript = prefix "JavaScript" (concat [casts,polyCasts])
121−
122−json = prefix "JSON"
123− [ "JsonString" -: string ==> jsonValue
124− , "JsonBool" -: bool ==> jsonValue
125− , "JsonNull" -: jsonValue
126− , "JsonArray" -: listOf jsonValue ==> jsonValue
127− , "JsonObject" -: jsonObject ==> jsonValue
128− , numScheme (\n -> n ==> jsonValue) "JsonNumber"
129− , "toString" -: jsonObject ==> string
130− , "fromString" -: string ==> maybeOf jsonObject
131− , "lookup" -: string ==> jsonObject ==> maybeOf jsonValue
132− , "findObject" -: string ==> jsonObject ==> jsonObject
133− , "findArray" -: string ==> jsonObject ==> listOf jsonValue
134− , "findString" -: string ==> jsonObject ==> string
135− , "findNumber" -: float ==> jsonObject ==> float
136− , "findWithDefault" -:: jsonValue ==> string ==> jsonObject ==> jsonValue
137− , "toPrettyString" -: string ==> jsonObject ==> string
138− , "toPrettyJSString" -: string ==> jsonObject ==> jsString
139− , "toList" -: jsonObject ==> listOf (tupleOf [string,jsonValue])
140− , "fromList" -: listOf (tupleOf [string,jsonValue]) ==> jsonObject
141− , "toJSString" -: jsonObject ==> jsString
142− , "fromJSString" -: jsString ==> jsonObject
143− ]
144−
145−
146−-------- Signals --------
147−
148−lyft n = sig (n+1) ("lift" ++ show n)
149−sig n name = (,) name $ Forall [1..n] [] (fn ts ==> fn (map signalOf ts))
150− where fn = foldr1 (==>)
151− ts = map VarT [1..n]
152−
153−signals = prefix "Signal"
154− [ sig 1 "constant"
155− , sig 2 "lift"
156− ] ++ map lyft [2..8] ++ [
157− "<~" -:: (a ==> b) ==> signalOf a ==> signalOf b
158− , "~" -:: signalOf (a ==> b) ==> signalOf a ==> signalOf b
159− , "foldp" -:: (a ==> b ==> b) ==> b ==> signalOf a ==> signalOf b
160− , "foldp1" -:: (a ==> a ==> a) ==> signalOf a ==> signalOf a
161− , "foldp'" -:: (a ==> b ==> b) ==> (a ==> b) ==> signalOf a ==> signalOf b
162− , "count" -:: signalOf a ==> signalOf int
163− , "countIf" -:: (a ==> bool) ==> signalOf a ==> signalOf int
164− , "keepIf" -:: (a ==> bool) ==> a ==> signalOf a ==> signalOf a
165− , "dropIf" -:: (a ==> bool) ==> a ==> signalOf a ==> signalOf a
166− , "keepWhen" -:: signalOf bool ==> a ==> signalOf a ==> signalOf a
167− , "dropWhen" -:: signalOf bool ==> a ==> signalOf a ==> signalOf a
168− , "dropRepeats" -:: signalOf a ==> signalOf a
169− , "sampleOn" -:: signalOf a ==> signalOf b ==> signalOf b
170− , "timestamp" -:: signalOf a ==> signalOf (tupleOf [time,a])
171− , "timeOf" -:: signalOf a ==> signalOf time
172− , "merge" -:: signalOf a ==> signalOf a ==> signalOf a
173− , "merges" -:: listOf (signalOf a) ==> signalOf a
174− , "mergeEither" -:: signalOf a ==> signalOf b ==> signalOf (eitherOf a b)
175− , numScheme (\n -> int ==> signalOf n ==> signalOf float) "average"
176− ]
177−
178−http = prefix "HTTP"
179− [ "send" -:: signalOf (request a) ==> signalOf (response string)
180− , "sendGet" -:: signalOf string ==> signalOf (response string)
181− , "get" -: string ==> request string
182− , "post" -: string ==> string ==> request string
183− , "request" -: string ==> string ==> string ==> listOf (pairOf string) ==> request string
184− , "Waiting" -:: response a
185− , "Failure" -:: int ==> string ==> response a
186− , "Success" -:: a ==> response a ]
187− where request t = ADT "Request" [t]
188− response t = ADT "Response" [t]
189−
190−concreteSignals =
191− [ "Random.inRange" -: int ==> int ==> signalOf int
192− , "Random.randomize" -:: int ==> int ==> signalOf a ==> signalOf int
193− , "Window.dimensions" -: signalOf point
194− , "Window.width" -: signalOf int
195− , "Window.height" -: signalOf int
196− , "Mouse.position" -: signalOf point
197− , "Mouse.x" -: signalOf int
198− , "Mouse.y" -: signalOf int
199− , "Mouse.isDown" -: signalOf bool
200− , "Mouse.isClicked" -: signalOf bool
201− , "Mouse.clicks" -: signalOf (tupleOf [])
202− , "Input.textField" -: string ==> tupleOf [element, signalOf string]
203− , "Input.password" -: string ==> tupleOf [element, signalOf string]
204− , "Input.textArea" -: int ==> int ==> tupleOf [element, signalOf string]
205− , "Input.checkBox" -: bool ==> tupleOf [element, signalOf bool]
206− , "Input.button" -: string ==> tupleOf [element, signalOf bool]
207− , "Input.stringDropDown" -: listOf string ==> tupleOf [element, signalOf string]
208− , "Input.dropDown" -:: listOf (tupleOf [string,a]) ==> tupleOf [element, signalOf a]
209− ]
210−
211−keyboards = prefix "Keyboard"
212− [ "Raw.keysDown" -: signalOf (listOf int)
213− , "Raw.charPressed" -: signalOf (maybeOf int)
214− , "arrows" -: signalOf (recordOf [("x",int),("y",int)])
215− , "wasd" -: signalOf (recordOf [("x",int),("y",int)])
216− , "ctrl" -: signalOf bool
217− , "space" -: signalOf bool
218− , "shift" -: signalOf bool
219− ]
220−
221−touches = prefix "Touch"
222− [ "touches" -: signalOf (listOf (recordOf [("x" ,int) ,("y" ,int)
223− ,("x0",int) ,("y0",int)
224− ,("t0",time),("id",int)]))
225− , "taps" -: signalOf (recordOf [("x",int),("y",int)])
226− ]
227−
228−times = prefix "Time"
229− [ numScheme (\n -> n ==> signalOf time) "fps"
230− , numScheme (\n -> n ==> signalOf bool ==> signalOf time) "fpsWhen"
231− , "every" -: time ==> signalOf time
232− , "delay" -:: time ==> signalOf a ==> signalOf a
233− , "since" -:: time ==> signalOf a ==> signalOf bool
234− , "hour" -: time
235− , "minute" -: time
236− , "second" -: time
237− , "ms" -: time
238− , "inHours" -: time ==> float
239− , "inMinutes" -: time ==> float
240− , "inSeconds" -: time ==> float
241− , "inMss" -: time ==> float
242− , "toDate" -: time ==> date
243− , "read" -: string ==> maybeOf time
244− ]
245−
246−dates =
247− let days = map (-: day) ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"]
248− months = map (-: month) [ "Jan", "Feb", "Mar", "Apr", "May", "Jun"
249− , "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" ]
250− in prefix "Date"
251− ([ "read" -: string ==> maybeOf date
252− , "year" -: date ==> int
253− , "month" -: date ==> month
254− , "day" -: date ==> int
255− , "hour" -: date ==> int
256− , "minute" -: date ==> int
257− , "second" -: date ==> int
258− , "dayOfWeek" -: date ==> day
259− , "toTime" -: date ==> time
260− ] ++ days ++ months)
261−
262−-------- Math and Binops --------
263−
264−binop t = t ==> t ==> t
265−scheme1 super t name =
266− (name, Forall [0] [ ctx name $ VarT 0 :<: super
267− ] (t (VarT 0)))
268−scheme2 s1 s2 t name =
269− (name, Forall [0,1] [ ctx name $ VarT 0 :<: s1
270− , ctx name $ VarT 1 :<: s2
271− ] (t (VarT 0) (VarT 1)))
272−numScheme t name = scheme1 number t name
273−twoNums f name = scheme2 number number f name
274−
275−math =
276− map (numScheme (\t -> t ==> binop t)) ["clamp"] ++
277− map (numScheme (\t -> binop t)) ["+","-","*","max","min"] ++
278− [ numScheme (\t -> t ==> t) "abs" ] ++
279− hasType (binop float) [ "/", "logBase" ] ++
280− hasType (binop int) ["rem","div","mod"] ++
281− hasType (float ==> float) ["sin","cos","tan","asin","acos","atan","sqrt"] ++
282− hasType float ["pi","e"] ++
283− hasType (int ==> float) ["toFloat","castIntToFloat"] ++
284− hasType (float ==> int) ["round","floor","ceiling","truncate"] ++
285− [ "show" -:: a ==> string
286− , "readInt" -: string ==> maybeOf int
287− , "readFloat" -: string ==> maybeOf float ]
288−
289−bools =
290− [ "not" -: bool ==> bool ] ++
291− hasType (binop bool) ["&&","||","xor"] ++
292− map (scheme1 comparable (\t -> t ==> t ==> bool)) ["<",">","<=",">="] ++
293− [ ( "compare"
294− , Forall [0,1] [ ctx "compare" $ VarT 0 :<: comparable ] (VarT 0 ==> VarT 0 ==> VarT 1) )
295− ]
296−
297−chars = prefix "Char" (classify ++ convert1 ++ convert2)
298− where classify = hasType (char ==> bool)
299− ["isDigit","isOctDigit","isHexDigit","isUpper","isLower"]
300− convert1 = hasType (char ==> char)
301− ["toUpper","toLower","toLocaleUpper","toLocaleLower"]
302− convert2 = [ "toCode" -: char ==> int, "fromCode" -: int ==> char ]
303−
304−
305−-------- Polymorphic Functions --------
306−
307−[a,b,c] = map VarT [1,2,3]
308−
309−infix 8 -::
310−name -:: tipe = (name, Forall [1,2,3] [] tipe)
311−
312−funcs =
313− [ "id" -:: a ==> a
314− , "==" -:: a ==> a ==> bool
315− , "/=" -:: a ==> a ==> bool
316− , "flip" -:: (a ==> b ==> c) ==> (b ==> a ==> c)
317− , "." -:: (b ==> c) ==> (a ==> b) ==> (a ==> c)
318− , "$" -:: (a ==> b) ==> a ==> b
319− , ":" -:: a ==> listOf a ==> listOf a
320− , (,) "++" . Forall [0,1] [ ctx "++" $ VarT 0 :<: appendable (VarT 1) ] $ VarT 0 ==> VarT 0 ==> VarT 0
321− , "Cons" -:: a ==> listOf a ==> listOf a
322− , "Nil" -:: listOf a
323− , "Just" -:: a ==> maybeOf a
324− , "Nothing" -:: maybeOf a
325− , "Left" -:: a ==> eitherOf a b
326− , "Right" -:: b ==> eitherOf a b
327− , "curry" -:: (tupleOf [a,b] ==> c) ==> a ==> b ==> c
328− , "uncurry" -:: (a ==> b ==> c) ==> tupleOf [a,b] ==> c
329− ] ++ map tuple [0..8]
330−
331−tuple n = ("Tuple" ++ show n, Forall [1..n] [] $ foldr (==>) (tupleOf vs) vs)
332− where vs = map VarT [1..n]
333−
334−lists = prefix "List"
335− [ "and" -:: listOf bool ==> bool
336− , "or" -:: listOf bool ==> bool
337− , numScheme (\n -> listOf n ==> listOf n) "sort"
338− , "head" -:: listOf a ==> a
339− , "tail" -:: listOf a ==> listOf a
340− , "length" -:: listOf a ==> int
341− , "filter" -:: (a ==> bool) ==> listOf a ==> listOf a
342− , "foldr1" -:: (a ==> a ==> a) ==> listOf a ==> a
343− , "foldl1" -:: (a ==> a ==> a) ==> listOf a ==> a
344− , "scanl1" -:: (a ==> a ==> a) ==> listOf a ==> a
345− , "all" -:: (a ==> bool) ==> listOf a ==> bool
346− , "any" -:: (a ==> bool) ==> listOf a ==> bool
347− , "reverse" -:: listOf a ==> listOf a
348− , "take" -:: int ==> listOf a ==> listOf a
349− , "drop" -:: int ==> listOf a ==> listOf a
350− , "partition" -:: (a ==> bool) ==> listOf a ==> tupleOf [listOf a,listOf a]
351− , "intersperse" -:: a ==> listOf a ==> listOf a
352− , "zip" -:: listOf a ==>listOf b ==>listOf(tupleOf [a,b])
353− , "map" -:: (a ==> b) ==> listOf a ==> listOf b
354− , "foldr" -:: (a ==> b ==> b) ==> b ==> listOf a ==> b
355− , "foldl" -:: (a ==> b ==> b) ==> b ==> listOf a ==> b
356− , "scanl" -:: (a ==> b ==> b) ==> b ==> listOf a ==> listOf b
357− , (,) "concat" . Forall [0,1] [ ctx "concat" $ VarT 0 :<: appendable (VarT 1) ] $
358− listOf (VarT 0) ==> VarT 0
359− , (,) "concatMap" . Forall [0,1,2] [ ctx "concatMap" $ VarT 0 :<: appendable (VarT 1) ] $
360− (VarT 2 ==> VarT 0) ==> listOf (VarT 2) ==> VarT 0
361− , (,) "intercalate" . Forall [0,1] [ ctx "intercalate" $ VarT 0 :<: appendable (VarT 1) ] $
362− VarT 0 ==> listOf (VarT 0) ==> VarT 0
363− , "zipWith" -:: (a ==> b ==> c) ==> listOf a ==> listOf b ==> listOf c
364− ] ++ map (numScheme (\n -> listOf n ==> n)) [ "sum", "product"
365− , "maximum", "minimum" ]
366−
367−maybeFuncs = prefix "Maybe"
368− [ "maybe" -:: b ==> (a ==> b) ==> maybeOf a ==> b
369− , "isJust" -:: maybeOf a ==> bool
370− , "isNothing" -:: maybeOf a ==> bool
371− , "cons" -:: maybeOf a ==> listOf a ==> listOf a
372− , "justs" -:: listOf (maybeOf a) ==> listOf a
373− ]
374−
375−eithers = prefix "Either"
376− [ "isLeft" -:: eitherOf a b ==> bool
377− , "isRight" -:: eitherOf a b ==> bool
378− , "either" -:: (a ==> c) ==> (b ==> c) ==> eitherOf a b ==> c
379− , "lefts" -:: listOf (eitherOf a b) ==> listOf a
380− , "rights" -:: listOf (eitherOf a b) ==> listOf b
381− , "partition" -:: listOf (eitherOf a b) ==> tupleOf [listOf a,listOf b]
382− ]
383−
384−dictionary =
385− let dict k v = ADT "Dict" [k,v] in
386− prefix "Dict"
387− [ "empty" -:: dict a b
388− , "singleton" -:: a ==> b ==> dict a b
389− , "insert" -:: a ==> b ==> dict a b ==> dict a b
390− , "remove" -:: a ==> dict a b ==> dict a b
391− , "member" -:: a ==> dict a b ==> bool
392− , "lookup" -:: a ==> dict a b ==> maybeOf b
393− , "findWithDefault" -:: b ==> a ==> dict a b ==> b
394− , "intersect" -:: dict a b ==> dict a c ==> dict a b
395− , "union" -:: dict a b ==> dict a b ==> dict a b
396− , "diff" -:: dict a b ==> dict a c ==> dict a b
397− , "map" -:: (b ==> c) ==> dict a b ==> dict a c
398− , "foldl" -:: (a ==> b ==> c ==> c) ==> c ==> dict a b ==> c
399− , "foldr" -:: (a ==> b ==> c ==> c) ==> c ==> dict a b ==> c
400− , "keys" -:: dict a b ==> listOf a
401− , "values" -:: dict a b ==> listOf b
402− , "toList" -:: dict a b ==> listOf (tupleOf [a,b])
403− , "fromList" -:: listOf (tupleOf [a,b]) ==> dict a b
404− ]
405−
406−sets =
407− let set v = ADT "Set" [v] in
408− prefix "Set"
409− [ "empty" -:: set a
410− , "singleton" -:: a ==> set a
411− , "insert" -:: a ==> set a ==> set a
412− , "remove" -:: a ==> set a ==> set a
413− , "member" -:: a ==> set a ==> bool
414− , "intersect" -:: set a ==> set a ==> set a
415− , "union" -:: set a ==> set a ==> set a
416− , "diff" -:: set a ==> set a ==> set a
417− , "map" -:: (a ==> b) ==> set a ==> set b
418− , "foldl" -:: (a ==> b ==> b) ==> b ==> set a ==> b
419− , "foldr" -:: (a ==> b ==> b) ==> b ==> set a ==> b
420− , "toList" -:: set a ==> listOf a
421− , "fromList" -:: listOf a ==> set a
422− ]
423−
424−automaton =
425− let auto a b = ADT "Automaton" [a,b] in
426− prefix "Automaton"
427− [ "pure" -:: (a ==> b) ==> auto a b
428− , "init" -:: b ==> (a ==> b ==> b) ==> auto a b
429− , "init'" -:: c ==> (a ==> c ==> tupleOf [b,c]) ==> auto a b
430− , ">>>" -:: auto a b ==> auto b c ==> auto a c
431− , "<<<" -:: auto b c ==> auto a b ==> auto a c
432− , "combine" -:: listOf (auto a b) ==> auto a (listOf b)
433− , "run" -:: auto a b ==> signalOf a ==> signalOf b
434− , "step" -:: auto a b ==> a ==> tupleOf [b,auto a b]
435− , "count" -:: auto a int
436− , "draggable" -:: form ==> auto (tupleOf [bool,point]) form
437− ]
438−
439−-------- Everything --------
440−
441−hints = mapM (\(n,s) -> (,) n `liftM` rescheme s) (concat hs)
442− where hs = [ funcs, lists, signals, math, bools, textAttrs
443− , graphicsElement, graphicsColor, eithers, keyboards, touches
444− , concreteSignals, javascript, json, maybeFuncs
445− , http, dictionary, sets, automaton, times, dates
446− ]
elm/src/Types/Types.hsdeleted−119
@@ -1,119 +0,0 @@
1−
2−module Types.Types where
3−
4−import Context
5−import Data.Char (isDigit)
6−import Data.List (intercalate,isPrefixOf)
7−import qualified Data.Set as Set
8−import qualified Data.Map as Map
9−
10−type X = Int
11−
12−data Type = LambdaT Type Type
13− | VarT X
14− | ADT String [Type]
15− | EmptyRecord
16− | RecordT (Map.Map String [Type]) Type
17− | Super (Set.Set Type)
18− deriving (Eq, Ord)
19−
20−data Scheme = Forall [X] [Context Constraint] Type deriving (Eq, Ord)
21−
22−data Constraint = Type :=: Type
23− | Type :<: Type
24− | X :<<: Scheme
25− deriving (Eq, Ord, Show)
26−
27−recordT :: [(String,Type)] -> Map.Map String [Type]
28−recordT fields =
29− foldl (\r (x,t) -> Map.insertWith (++) x [t] r) Map.empty fields
30−
31−recordOf :: [(String,Type)] -> Type
32−recordOf fields = RecordT (recordT fields) EmptyRecord
33−
34−tipe t = ADT t []
35−
36−int = tipe "Int"
37−float = tipe "Float"
38−number = Super (Set.fromList [ int, float ])
39−
40−char = tipe "Char"
41−bool = tipe "Bool"
42−
43−string = listOf char -- tipe "String"
44−text = tipe "Text"
45−
46−time = float --tipe "Time"
47−date = tipe "Date"
48−month = tipe "Month"
49−day = tipe "Day"
50−
51−element = tipe "Element"
52−direction = tipe "Direction"
53−form = tipe "Form"
54−line = tipe "Line"
55−shape = tipe "Shape"
56−color = tipe "Color"
57−position = tipe "Position"
58−location = tipe "Location"
59−
60−listOf t = ADT "List" [t]
61−signalOf t = ADT "Signal" [t]
62−tupleOf ts = ADT ("Tuple" ++ show (length ts)) ts
63−maybeOf t = ADT "Maybe" [t]
64−eitherOf a b = ADT "Either" [a,b]
65−pairOf t = tupleOf [t,t]
66−point = pairOf int
67−appendable t = Super (Set.fromList [ string, text, listOf t ])
68−comparable = Super (Set.fromList [ int, float, char, string, time, date ])
69−
70−jsBool = tipe "JSBool"
71−jsNumber = tipe "JSNumber"
72−jsString = tipe "JSString"
73−jsElement = tipe "JSElement"
74−jsArray t = ADT "JSArray" [t]
75−jsTuple ts = ADT ("JSTuple" ++ show (length ts)) ts
76−jsonValue = tipe "JsonValue"
77−jsonObject = tipe "JsonObject"
78−
79−infixr ==>
80−t1 ==> t2 = LambdaT t1 t2
81−
82−infix 8 -:
83−name -: tipe = (,) name $ Forall [] [] tipe
84−
85−parens = ("("++) . (++")")
86−
87−instance Show Type where
88− show t =
89− case t of
90− { LambdaT t1@(LambdaT _ _) t2 -> parens (show t1) ++ " -> " ++ show t2
91− ; LambdaT t1 t2 -> show t1 ++ " -> " ++ show t2
92− ; VarT x -> 't' : show x
93− ; ADT "List" [ADT "Char" []] -> "String"
94− ; ADT "List" [tipe] -> "[" ++ show tipe ++ "]"
95− ; ADT name cs ->
96− if isTupleString name
97− then parens . intercalate "," $ map show cs
98− else case cs of
99− [] -> name
100− _ -> parens $ name ++ " " ++ unwords (map show cs)
101− ; Super ts -> "{" ++ (intercalate "," . map show $ Set.toList ts) ++ "}"
102− ; EmptyRecord -> "{}"
103− ; RecordT fs t ->
104− start ++ intercalate ", " (concatMap fields $ Map.toList fs) ++ " }"
105− where field n s = n ++ " :: " ++ show s
106− fields (n,ss) = map (field n) ss
107− start = case t of
108− EmptyRecord -> "{ "
109− _ -> "{ " ++ show t ++ " | "
110− }
111−
112−instance Show Scheme where
113− show (Forall [] [] t) = show t
114− show (Forall xs cs t) =
115− concat [ "Forall ", show xs
116− , concatMap (("\n "++) . show) cs
117− , "\n ", parens (show t) ]
118−
119−isTupleString str = "Tuple" `isPrefixOf` str && all isDigit (drop 5 str)
elm/src/Types/Unify.hsdeleted−19
@@ -1,19 +0,0 @@
1−
2−module Types.Unify (unify) where
3−
4−import Control.Monad (liftM)
5−import qualified Data.Map as Map
6−
7−import Guid
8−import Types.Constrain
9−import Types.Solver
10−
11−unify hints modul = run $ do
12− constraints <- constrain hints modul
13− case constraints of
14− Left msg -> return (Left msg)
15− Right (escapees, cs) ->
16− do subs <- solver cs Map.empty
17− return $ do ss <- subs
18− return (escapees, ss)
19−
libraries/Automaton.elmnew file+96
@@ -0,0 +1,96 @@
1+-- This library is a way to package up dynamic behavior. It makes it easier to
2+-- dynamically create dynamic components. See the [original release
3+-- notes](/blog/announce/version-0.5.0.elm) on this library to get a feel for how
4+-- it can be used.
5+module Automaton where
6+
7+data Automaton a b = Step (a -> (Automaton a b, b))
8+
9+-- Run an automaton on a given signal. The automaton steps forward
10+-- whenever the input signal updates.
11+run : Automaton a b -> b -> Signal a -> Signal b
12+run (Step f) base inputs =
13+ let step a (Step f, _) = f a
14+ in lift snd $ foldp step base inputs
15+
16+-- Step an automaton forward once with a given input.
17+step : a -> Automaton a b -> (Automaton a b, b)
18+step a (Step f) = f a
19+
20+-- Compose two automatons, chaining them together.
21+(>>>) : Automaton a b -> Automaton b c -> Automaton a c
22+f >>> g =
23+ Step (\a -> let (f', b) = step a f
24+ (g', c) = step b g
25+ in (f' >>> g', c))
26+
27+-- Compose two automatons, chaining them together.
28+(<<<) : Automaton b c -> Automaton a b -> Automaton a c
29+g <<< f = f >>> g
30+
31+-- Combine a list of automatons into a single automaton that produces a list.
32+combine : [Automaton a b] -> Automaton a [b]
33+combine autos =
34+ Step (\a -> let (autos', bs) = unzip $ map (step a) autos
35+ in (combine autos', bs))
36+
37+-- Create an automaton with no memory. It just applies the given function to
38+-- every input.
39+pure : (a -> b) -> Automaton a b
40+pure f = Step (\x -> (pure f, f x))
41+
42+-- Create an automaton with state. Requires an initial state and a step
43+-- function to step the state forward. For example, an automaton that counted
44+-- how many steps it has taken would look like this:
45+--
46+-- count = Automaton a Int
47+-- count = state 0 (\\_ c -> c+1)
48+--
49+-- It is a stateful automaton. The initial state is zero, and the step function
50+-- increments the state on every step.
51+state : b -> (a -> b -> b) -> Automaton a b
52+state s f = Step (\x -> let s' = f x s
53+ in (state s' f, s'))
54+
55+-- Create an automaton with hidden state. Requires an initial state and a
56+-- step function to step the state forward and produce an output.
57+hiddenState : s -> (a -> s -> (s,b)) -> Automaton a b
58+hiddenState s f = Step (\x -> let (s',out) = f x s
59+ in (hiddenState s' f, out))
60+
61+-- Count the number of steps taken.
62+count : Automaton a Int
63+count = state 0 (\_ c -> c + 1)
64+
65+type Queue t = ([t],[t])
66+empty = ([],[])
67+enqueue x (en,de) = (x::en, de)
68+dequeue q = case q of
69+ ([],[]) -> Nothing
70+ (en,[]) -> enqueue ([], reverse en)
71+ (en,hd::tl) -> Just (hd, (en,tl))
72+
73+-- Computes the running average of the last `n` inputs.
74+average : Int -> Automaton Float Float
75+average k =
76+ let step n (ns,len,sum) =
77+ if len == k then stepFull n (ns,len,sum)
78+ else ((enqueue n ns, len+1, sum+n), (sum+n) / (len+1))
79+ stepFull n (ns,len,sum) =
80+ case dequeue ns of
81+ Nothing -> ((ns,len,sum), 0)
82+ Just (m,ns') -> let sum' = sum + n - m
83+ in ((enqueue n ns', len, sum'), sum' / len)
84+ in hiddenState (empty,0,0) step
85+
86+
87+{-- TODO(evancz): See the following papers for ideas on how to make this
88+library faster and better:
89+
90+- Functional Reactive Programming, Continued
91+- Causal commutative arrows and their optimization
92+
93+Speeding things up is a really low priority. Language features and
94+libraries with nice APIs and are way more important!
95+--}
96+
libraries/Char.elmnew file+38
@@ -0,0 +1,38 @@
1+
2+module Char where
3+
4+import Native.Char as N
5+
6+-- True for upper case letters.
7+isUpper : Char -> Bool
8+
9+-- True for lower case letters.
10+isLower : Char -> Bool
11+
12+-- True for ASCII digits (`0..9`).
13+isDigit : Char -> Bool
14+
15+-- True for ASCII octal digits (`0..7`).
16+isOctDigit : Char -> Bool
17+
18+-- True for ASCII hexadecimal digits (`0..9a..fA..F`).
19+isHexDigit : Char -> Bool
20+
21+-- Convert to upper case.
22+toUpper : Char -> Char
23+
24+-- Convert to lower case.
25+toLower : Char -> Char
26+
27+-- Convert to upper case, according to any locale-specific case mappings.
28+toLocaleUpper : Char -> Char
29+
30+-- Convert to lower case, according to any locale-specific case mappings.
31+toLocaleLower : Char -> Char
32+
33+-- Convert to unicode.
34+toCode : Char -> KeyCode
35+
36+-- Convert from unicode.
37+fromCode : KeyCode -> Char
38+
libraries/Color.elmnew file+87
@@ -0,0 +1,87 @@
1+
2+module Color where
3+
4+data Color = Color Int Int Int Float
5+
6+-- Create RGB colors with an alpha component for transparency.
7+-- The alpha component is specified with numbers between 0 and 1.
8+rgba : Int -> Int -> Int -> Float -> Color
9+rgba = Color
10+
11+-- Create RGB colors from numbers between 0 and 255 inclusive.
12+rgb : Int -> Int -> Int -> Color
13+rgb r g b = Color r g b 1
14+
15+red : Color
16+red = Color 255 0 0 1
17+lime : Color
18+lime = Color 0 255 0 1
19+blue : Color
20+blue = Color 0 0 255 1
21+
22+yellow : Color
23+yellow = Color 255 255 0 1
24+cyan : Color
25+cyan = Color 0 255 255 1
26+magenta : Color
27+magenta = Color 255 0 255 1
28+
29+black : Color
30+black = Color 0 0 0 1
31+white : Color
32+white = Color 255 255 255 1
33+
34+gray : Color
35+gray = Color 128 128 128 1
36+grey : Color
37+grey = Color 128 128 128 1
38+
39+maroon : Color
40+maroon = Color 128 0 0 1
41+navy : Color
42+navy = Color 0 0 128 1
43+green : Color
44+green = Color 0 128 0 1
45+
46+teal : Color
47+teal = Color 0 128 128 1
48+purple : Color
49+purple = Color 128 0 128 1
50+
51+violet : Color
52+violet = Color 238 130 238 1
53+forestGreen : Color
54+forestGreen = Color 34 139 34 1
55+
56+-- Produce a &ldquo;complementary color&rdquo;.
57+-- The two colors will accent each other.
58+complement : Color -> Color
59+
60+-- Create [HSV colors](http://en.wikipedia.org/wiki/HSL_and_HSV)
61+-- with an alpha component for transparency.
62+hsva : Float -> Float -> Float -> Float -> Color
63+
64+-- Create [HSV colors](http://en.wikipedia.org/wiki/HSL_and_HSV).
65+-- This is very convenient for creating colors that cycle and shift.
66+--
67+-- hsv (degrees 240) 1 1 == blue
68+hsv : Float -> Float -> Float -> Color
69+
70+data Gradient
71+ = Linear (Float,Float) (Float,Float) [(Float,Color)]
72+ | Radial (Float,Float) Float (Float,Float) Float [(Float,Color)]
73+
74+-- Create a linear gradient. Takes a start and end point and then a series
75+-- of &ldquo;color stops&rdquo; that indicate how to interpolate between
76+-- the start and end points. See [this example](/edit/examples/Elements/LinearGradient.elm) for
77+-- a more visual explanation.
78+linear : (Number a, Number a) -> (Number a, Number a) -> [(Float,Color)] -> Gradient
79+linear = Linear
80+
81+-- Create a radial gradient. First takes a start point and inner radius.
82+-- Then takes an end point and outer radius. It then takes a series
83+-- of &ldquo;color stops&rdquo; that indicate how to interpolate between
84+-- the inner and outer circles. See [this example](/edit/examples/Elements/RadialGradient.elm) for
85+-- a more visual explanation.
86+radial : (Number a,Number a) -> Number a -> (Number a,Number a) -> Number a -> [(Float,Color)] -> Gradient
87+radial = Radial
libraries/Date.elmnew file+50
@@ -0,0 +1,50 @@
1+
2+-- Library for working with dates. It is still a work in progress, so email
3+-- the mailing list if you are having issues with internationalization or
4+-- locale formatting or something.
5+module Date where
6+
7+-- Represents the days of the week.
8+data Day = Mon | Tue | Wed | Thu | Fri | Sat | Sun
9+
10+-- Represents the month of the year.
11+data Month = Jan | Feb | Mar | Apr
12+ | May | Jun | Jul | Aug
13+ | Sep | Oct | Nov | Dec
14+
15+-- Attempt to read a date from a string.
16+read : String -> Maybe Date
17+
18+-- Convert a date into a time since midnight (UTC) of 1 January 1990 (i.e.
19+-- [UNIX time](http://en.wikipedia.org/wiki/Unix_time)). Given the date 23 June
20+-- 1990 at 11:45AM this returns the corresponding time.
21+toTime : Date -> Time
22+
23+-- Extract the year of a given date. Given the date 23 June 1990 at 11:45AM
24+-- this returns the integer `1990`.
25+year : Date -> Int
26+
27+-- Extract the month of a given date. Given the date 23 June 1990 at 11:45AM
28+-- this returns the Month `Jun` as defined below.
29+month : Date -> Month
30+
31+
32+-- Extract the day of a given date. Given the date 23 June 1990 at 11:45AM
33+-- this returns the integer `23`.
34+day : Date -> Int
35+
36+-- Extract the day of the week for a given date. Given the date 23 June
37+-- 1990 at 11:45AM this returns the Day `Thu` as defined below.
38+dayOfWeek : Date -> Day
39+
40+-- Extract the hour of a given date. Given the date 23 June 1990 at 11:45AM
41+-- this returns the integer `11`.
42+hour : Date -> Int
43+
44+-- Extract the minute of a given date. Given the date 23 June 1990 at 11:45AM
45+-- this returns the integer `45`.
46+minute : Date -> Int
47+
48+-- Extract the second of a given date. Given the date 23 June 1990 at 11:45AM
49+-- this returns the integer `0`.
50+second : Date -> Int
core/Dict.elm → libraries/Dict.elmrenamed+116−89
@@ -8,40 +8,41 @@ module Dict (empty,singleton,insert
8 ,toList,fromList
8 ,toList,fromList
9 ) where
9 ) where
10
10
11−import Maybe (isJust)
11+import Maybe as Maybe
12+import Native.Error as Error
13+import List as List
14+import Native.Utils (compare)
12
15
13data NColor = Red | Black
16data NColor = Red | Black
14
17
15−data RBTree k v = RBNode NColor k v (RBTree k v) (RBTree k v) | RBEmpty
18+data Dict k v = RBNode NColor k v (Dict k v) (Dict k v) | RBEmpty
16
19
20+-- Create an empty dictionary.
17−empty : RBTree k v
21+empty : Dict (Comparable k) v
18empty = RBEmpty
22empty = RBEmpty
19
23
20−raise err = throw (JavaScript.castStringToJSString err)
21−
22{-- Helpers for checking invariants
24{-- Helpers for checking invariants
23
25
24-- Check that the tree has an equal number of black nodes on each path
26-- Check that the tree has an equal number of black nodes on each path
25−equal_pathLen t =
27+equal_pathLen t =
26 let path_numBlacks t =
28 let path_numBlacks t =
27 case t of
29 case t of
28− { RBEmpty -> 1
30+ RBEmpty -> 1
29− ; RBNode col _ _ l r ->
31+ RBNode col _ _ l r ->
30 let { bl = path_numBlacks l ; br = path_numBlacks r } in
32 let { bl = path_numBlacks l ; br = path_numBlacks r } in
31 if bl /= br || bl == 0-1 || br == 0-1
33 if bl /= br || bl == 0-1 || br == 0-1
32 then 0-1
34 then 0-1
33 else bl + (if col == Red then 0 else 1)
35 else bl + (if col == Red then 0 else 1)
34− }
35 in 0-1 /= path_numBlacks t
36 in 0-1 /= path_numBlacks t
36
37
37−rootBlack t =
38+rootBlack t =
38 case t of
39 case t of
39− { RBEmpty -> True
40+ RBEmpty -> True
40− ; RBNode Black _ _ _ _ -> True
41+ RBNode Black _ _ _ _ -> True
41− ; _ -> False }
42+ _ -> False
42
43
43−redBlack_children t =
44+redBlack_children t =
44− case t of
45+ case t of
45 { RBNode Red _ _ (RBNode Red _ _ _ _) _ -> False
46 { RBNode Red _ _ (RBNode Red _ _ _ _) _ -> False
46 ; RBNode Red _ _ _ (RBNode Red _ _ _ _) -> False
47 ; RBNode Red _ _ _ (RBNode Red _ _ _ _) -> False
47 ; RBEmpty -> True
48 ; RBEmpty -> True
@@ -56,7 +57,7 @@ findExtreme f t =
56 { Nothing -> Just k
57 { Nothing -> Just k
57 ; Just k' -> Just k' }
58 ; Just k' -> Just k' }
58 }
59 }
59−
60+
60findminRbt t = findExtreme fst t
61findminRbt t = findExtreme fst t
61findmaxRbt t = findExtreme snd t
62findmaxRbt t = findExtreme snd t
62
63
@@ -82,7 +83,7 @@ ordered t =
82 }
83 }
83
84
84-- Check that there aren't any right red nodes in the tree *)
85-- Check that there aren't any right red nodes in the tree *)
85−leftLeaning t =
86+leftLeaning t =
86 case t of
87 case t of
87 { RBEmpty -> True
88 { RBEmpty -> True
88 ; RBNode _ _ _ (RBNode Black _ _ _ _) (RBNode Red _ _ _ _) -> False
89 ; RBNode _ _ _ (RBNode Black _ _ _ _) (RBNode Red _ _ _ _) -> False
@@ -91,40 +92,43 @@ leftLeaning t =
91 }
92 }
92
93
93invariants_hold t =
94invariants_hold t =
94− ordered t && rootBlack t && redBlack_children t &&
95+ ordered t && rootBlack t && redBlack_children t &&
95 equal_pathLen t && leftLeaning t
96 equal_pathLen t && leftLeaning t
96
97
97--** End invariant helpers *****
98--** End invariant helpers *****
98--}
99--}
99
100
100
101
101−min : RBTree k v -> (k,v)
102+min : Dict k v -> (k,v)
102min t =
103min t =
103− case t of
104+ case t of
104 RBNode _ k v RBEmpty _ -> (k,v)
105 RBNode _ k v RBEmpty _ -> (k,v)
105 RBNode _ _ _ l _ -> min l
106 RBNode _ _ _ l _ -> min l
106− RBEmpty -> raise "(min RBEmpty) is not defined"
107+ RBEmpty -> Error.raise "(min Empty) is not defined"
107
108
108{--
109{--
109max t =
110max t =
110− case t of
111+ case t of
111 { RBNode _ k v _ RBEmpty -> (k,v)
112 { RBNode _ k v _ RBEmpty -> (k,v)
112 ; RBNode _ _ _ _ r -> max r
113 ; RBNode _ _ _ _ r -> max r
113− ; RBEmpty -> raise "(max RBEmpty) is not defined"
114+ ; RBEmpty -> Error.raise "(max Empty) is not defined"
114 }
115 }
115--}
116--}
116
117
118+-- Lookup the value associated with a key.
117−lookup : k -> RBTree k v -> Maybe v
119+lookup : Comparable k -> Dict (Comparable k) v -> Maybe v
118lookup k t =
120lookup k t =
119 case t of
121 case t of
120− RBEmpty -> Nothing
122+ RBEmpty -> Maybe.Nothing
121 RBNode _ k' v l r ->
123 RBNode _ k' v l r ->
122 case compare k k' of
124 case compare k k' of
123 LT -> lookup k l
125 LT -> lookup k l
124− EQ -> Just v
126+ EQ -> Maybe.Just v
125 GT -> lookup k r
127 GT -> lookup k r
126
128
129+-- Find the value associated with a key. If the key is not found,
130+-- return the default value.
127−findWithDefault : v -> k -> RBTree k v -> v
131+findWithDefault : v -> Comparable k -> Dict (Comparable k) v -> v
128findWithDefault base k t =
132findWithDefault base k t =
129 case t of
133 case t of
130 RBEmpty -> base
134 RBEmpty -> base
@@ -135,9 +139,10 @@ findWithDefault base k t =
135 GT -> findWithDefault base k r
139 GT -> findWithDefault base k r
136
140
137{--
141{--
142+-- Find the value associated with a key. If the key is not found, there will be a runtime error.
138find k t =
143find k t =
139 case t of
144 case t of
140− { RBEmpty -> raise "Key was not found in dictionary!"
145+ { RBEmpty -> Error.raise "Key was not found in dictionary!"
141 ; RBNode _ k' v l r ->
146 ; RBNode _ k' v l r ->
142 case compare k k' of
147 case compare k k' of
143 { LT -> find k l
148 { LT -> find k l
@@ -146,64 +151,66 @@ find k t =
146 }
151 }
147--}
152--}
148
153
154+-- Determine if a key is in a dictionary.
155+member : Comparable k -> Dict (Comparable k) v -> Bool
149-- Does t contain k?
156-- Does t contain k?
150−member : k -> RBTree k v -> Bool
151−member k t = isJust $ lookup k t
157+member k t = Maybe.isJust $ lookup k t
152
158
153−rotateLeft : RBTree k v -> RBTree k v
159+rotateLeft : Dict k v -> Dict k v
154rotateLeft t =
160rotateLeft t =
155 case t of
161 case t of
156 RBNode cy ky vy a (RBNode cz kz vz b c) -> RBNode cy kz vz (RBNode Red ky vy a b) c
162 RBNode cy ky vy a (RBNode cz kz vz b c) -> RBNode cy kz vz (RBNode Red ky vy a b) c
157− _ -> raise "rotateLeft of a node without enough children"
163+ _ -> Error.raise "rotateLeft of a node without enough children"
158
164
159−-- rotateRight -- the reverse, and
165+-- rotateRight -- the reverse, and
160-- makes Y have Z's color, and makes Z Red.
166-- makes Y have Z's color, and makes Z Red.
161−rotateRight : RBTree k v -> RBTree k v
167+rotateRight : Dict k v -> Dict k v
162rotateRight t =
168rotateRight t =
163 case t of
169 case t of
164 RBNode cz kz vz (RBNode cy ky vy a b) c -> RBNode cz ky vy a (RBNode Red kz vz b c)
170 RBNode cz kz vz (RBNode cy ky vy a b) c -> RBNode cz ky vy a (RBNode Red kz vz b c)
165− _ -> raise "rotateRight of a node without enough children"
171+ _ -> Error.raise "rotateRight of a node without enough children"
166
172
167−rotateLeftIfNeeded : RBTree k v -> RBTree k v
173+rotateLeftIfNeeded : Dict k v -> Dict k v
168rotateLeftIfNeeded t =
174rotateLeftIfNeeded t =
169− case t of
175+ case t of
170 RBNode _ _ _ _ (RBNode Red _ _ _ _) -> rotateLeft t
176 RBNode _ _ _ _ (RBNode Red _ _ _ _) -> rotateLeft t
171 _ -> t
177 _ -> t
172
178
173−rotateRightIfNeeded : RBTree k v -> RBTree k v
179+rotateRightIfNeeded : Dict k v -> Dict k v
174rotateRightIfNeeded t =
180rotateRightIfNeeded t =
175− case t of
181+ case t of
176 RBNode _ _ _ (RBNode Red _ _ (RBNode Red _ _ _ _) _) _ -> rotateRight t
182 RBNode _ _ _ (RBNode Red _ _ (RBNode Red _ _ _ _) _) _ -> rotateRight t
177 _ -> t
183 _ -> t
178
184
179otherColor c = case c of { Red -> Black ; Black -> Red }
185otherColor c = case c of { Red -> Black ; Black -> Red }
180
186
181−color_flip : RBTree k v -> RBTree k v
187+color_flip : Dict k v -> Dict k v
182color_flip t =
188color_flip t =
183 case t of
189 case t of
184− RBNode c1 bk bv (RBNode c2 ak av la ra) (RBNode c3 ck cv lc rc) ->
190+ RBNode c1 bk bv (RBNode c2 ak av la ra) (RBNode c3 ck cv lc rc) ->
185 RBNode (otherColor c1) bk bv
191 RBNode (otherColor c1) bk bv
186 (RBNode (otherColor c2) ak av la ra)
192 (RBNode (otherColor c2) ak av la ra)
187 (RBNode (otherColor c3) ck cv lc rc)
193 (RBNode (otherColor c3) ck cv lc rc)
188− _ -> raise "color_flip called on a RBEmpty or RBNode with a RBEmpty child"
194+ _ -> Error.raise "color_flip called on a Empty or Node with a Empty child"
189
195
190−color_flipIfNeeded : RBTree k v -> RBTree k v
196+color_flipIfNeeded : Dict k v -> Dict k v
191−color_flipIfNeeded t =
197+color_flipIfNeeded t =
192 case t of
198 case t of
193 RBNode _ _ _ (RBNode Red _ _ _ _) (RBNode Red _ _ _ _) -> color_flip t
199 RBNode _ _ _ (RBNode Red _ _ _ _) (RBNode Red _ _ _ _) -> color_flip t
194 _ -> t
200 _ -> t
195
201
196fixUp t = color_flipIfNeeded (rotateRightIfNeeded (rotateLeftIfNeeded t))
202fixUp t = color_flipIfNeeded (rotateRightIfNeeded (rotateLeftIfNeeded t))
197
203
198−ensureBlackRoot : RBTree k v -> RBTree k v
204+ensureBlackRoot : Dict k v -> Dict k v
199−ensureBlackRoot t =
205+ensureBlackRoot t =
200 case t of
206 case t of
201 RBNode Red k v l r -> RBNode Black k v l r
207 RBNode Red k v l r -> RBNode Black k v l r
202 _ -> t
208 _ -> t
203−
209+
210+-- Insert a key-value pair into a dictionary. Replaces value when there is
211+-- a collision.
212+insert : Comparable k -> v -> Dict (Comparable k) v -> Dict (Comparable k) v
204−-- Invariant: t is a valid left-leaning rb tree *)
213+insert k v t = -- Invariant: t is a valid left-leaning rb tree
205−insert : k -> v -> RBTree k v -> RBTree k v
206−insert k v t =
207 let ins t =
214 let ins t =
208 case t of
215 case t of
209 RBEmpty -> RBNode Red k v RBEmpty RBEmpty
216 RBEmpty -> RBNode Red k v RBEmpty RBEmpty
@@ -216,48 +223,49 @@ insert k v t =
216 in ensureBlackRoot (ins t)
223 in ensureBlackRoot (ins t)
217{--
224{--
218 if not (invariants_hold t) then
225 if not (invariants_hold t) then
219− raise "invariants broken before insert"
226+ Error.raise "invariants broken before insert"
220 else (let new_t = ensureBlackRoot (ins t) in
227 else (let new_t = ensureBlackRoot (ins t) in
221 if not (invariants_hold new_t) then
228 if not (invariants_hold new_t) then
222− raise "invariants broken after insert"
229+ Error.raise "invariants broken after insert"
223 else new_t)
230 else new_t)
224--}
231--}
225
232
233+-- Create a dictionary with one key-value pair.
226−singleton : k -> v -> RBTree k v
234+singleton : Comparable k -> v -> Dict (Comparable k) v
227singleton k v = insert k v RBEmpty
235singleton k v = insert k v RBEmpty
228
236
229−isRed : RBTree k v -> Bool
237+isRed : Dict k v -> Bool
230isRed t =
238isRed t =
231 case t of
239 case t of
232 RBNode Red _ _ _ _ -> True
240 RBNode Red _ _ _ _ -> True
233 _ -> False
241 _ -> False
234
242
235−isRedLeft : RBTree k v -> Bool
243+isRedLeft : Dict k v -> Bool
236isRedLeft t =
244isRedLeft t =
237 case t of
245 case t of
238 RBNode _ _ _ (RBNode Red _ _ _ _) _ -> True
246 RBNode _ _ _ (RBNode Red _ _ _ _) _ -> True
239 _ -> False
247 _ -> False
240
248
241−isRedLeftLeft : RBTree k v -> Bool
249+isRedLeftLeft : Dict k v -> Bool
242isRedLeftLeft t =
250isRedLeftLeft t =
243 case t of
251 case t of
244 RBNode _ _ _ (RBNode _ _ _ (RBNode Red _ _ _ _) _) _ -> True
252 RBNode _ _ _ (RBNode _ _ _ (RBNode Red _ _ _ _) _) _ -> True
245 _ -> False
253 _ -> False
246
254
247−isRedRight : RBTree k v -> Bool
255+isRedRight : Dict k v -> Bool
248isRedRight t =
256isRedRight t =
249 case t of
257 case t of
250 RBNode _ _ _ _ (RBNode Red _ _ _ _) -> True
258 RBNode _ _ _ _ (RBNode Red _ _ _ _) -> True
251 _ -> False
259 _ -> False
252
260
253−isRedRightLeft : RBTree k v -> Bool
261+isRedRightLeft : Dict k v -> Bool
254isRedRightLeft t =
262isRedRightLeft t =
255 case t of
263 case t of
256 RBNode _ _ _ _ (RBNode _ _ _ (RBNode Red _ _ _ _) _) -> True
264 RBNode _ _ _ _ (RBNode _ _ _ (RBNode Red _ _ _ _) _) -> True
257 _ -> False
265 _ -> False
258
266
259−moveRedLeft : RBTree k v -> RBTree k v
267+moveRedLeft : Dict k v -> Dict k v
260−moveRedLeft t =
268+moveRedLeft t =
261 let t' = color_flip t in
269 let t' = color_flip t in
262 case t' of
270 case t' of
263 RBNode c k v l r ->
271 RBNode c k v l r ->
@@ -267,23 +275,23 @@ moveRedLeft t =
267 _ -> t'
275 _ -> t'
268 _ -> t'
276 _ -> t'
269
277
270−moveRedRight : RBTree k v -> RBTree k v
278+moveRedRight : Dict k v -> Dict k v
271moveRedRight t =
279moveRedRight t =
272 let t' = color_flip t in
280 let t' = color_flip t in
273 if isRedLeftLeft t' then color_flip (rotateRight t') else t'
281 if isRedLeftLeft t' then color_flip (rotateRight t') else t'
274
282
275−moveRedLeftIfNeeded : RBTree k v -> RBTree k v
283+moveRedLeftIfNeeded : Dict k v -> Dict k v
276moveRedLeftIfNeeded t =
284moveRedLeftIfNeeded t =
277− if not (isRedLeft t) && not (isRedLeftLeft t) then moveRedLeft t else t
285+ if isRedLeft t || isRedLeftLeft t then t else moveRedLeft t
278
286
279−moveRedRightIfNeeded : RBTree k v -> RBTree k v
287+moveRedRightIfNeeded : Dict k v -> Dict k v
280moveRedRightIfNeeded t =
288moveRedRightIfNeeded t =
281− if not (isRedRight t) && not (isRedRightLeft t) then moveRedRight t else t
289+ if isRedRight t || isRedRightLeft t then t else moveRedRight t
282
290
283−deleteMin : RBTree k v -> RBTree k v
291+deleteMin : Dict k v -> Dict k v
284−deleteMin t =
292+deleteMin t =
285 let del t =
293 let del t =
286− case t of
294+ case t of
287 RBNode _ _ _ RBEmpty _ -> RBEmpty
295 RBNode _ _ _ RBEmpty _ -> RBEmpty
288 _ -> case moveRedLeftIfNeeded t of
296 _ -> case moveRedLeftIfNeeded t of
289 RBNode c k v l r -> fixUp (RBNode c k v (del l) r)
297 RBNode c k v l r -> fixUp (RBNode c k v (del l) r)
@@ -303,22 +311,24 @@ deleteMax t =
303 in ensureBlackRoot (del t)
311 in ensureBlackRoot (del t)
304--}
312--}
305
313
306−remove : k -> RBTree k v -> RBTree k v
314+-- Remove a key-value pair from a dictionary. If the key is not found,
315+-- no changes are made.
316+remove : Comparable k -> Dict (Comparable k) v -> Dict (Comparable k) v
307−remove k t =
317+remove k t =
308 let eq_and_noRightNode t =
318 let eq_and_noRightNode t =
309 case t of { RBNode _ k' _ _ RBEmpty -> k == k' ; _ -> False }
319 case t of { RBNode _ k' _ _ RBEmpty -> k == k' ; _ -> False }
310 eq t = case t of { RBNode _ k' _ _ _ -> k == k' ; _ -> False }
320 eq t = case t of { RBNode _ k' _ _ _ -> k == k' ; _ -> False }
311− delLT t = case moveRedLeftIfNeeded t of
321+ delLT t = case moveRedLeftIfNeeded t of
312 RBNode c k' v l r -> fixUp (RBNode c k' v (del l) r)
322 RBNode c k' v l r -> fixUp (RBNode c k' v (del l) r)
313− RBEmpty -> raise "delLT on RBEmpty"
323+ RBEmpty -> Error.raise "delLT on Empty"
314 delEQ t = case t of -- Replace with successor
324 delEQ t = case t of -- Replace with successor
315 RBNode c _ _ l r -> let (k',v') = min r in
325 RBNode c _ _ l r -> let (k',v') = min r in
316 fixUp (RBNode c k' v' l (deleteMin r))
326 fixUp (RBNode c k' v' l (deleteMin r))
317− RBEmpty -> raise "delEQ called on a RBEmpty"
327+ RBEmpty -> Error.raise "delEQ called on a Empty"
318 delGT t = case t of
328 delGT t = case t of
319 RBNode c k' v l r -> fixUp (RBNode c k' v l (del r))
329 RBNode c k' v l r -> fixUp (RBNode c k' v l (del r))
320− RBEmpty -> raise "delGT called on a RBEmpty"
330+ RBEmpty -> Error.raise "delGT called on a Empty"
321− del t = case t of
331+ del t = case t of
322 RBEmpty -> RBEmpty
332 RBEmpty -> RBEmpty
323 RBNode _ k' _ _ _ ->
333 RBNode _ k' _ _ _ ->
324 if k < k' then delLT t else
334 if k < k' then delLT t else
@@ -329,47 +339,64 @@ remove k t =
329 in if member k t then ensureBlackRoot (del t) else t
339 in if member k t then ensureBlackRoot (del t) else t
330{--
340{--
331 if not (invariants_hold t) then
341 if not (invariants_hold t) then
332− raise "invariants broken before remove"
342+ Error.raise "invariants broken before remove"
333 else (let t' = ensureBlackRoot (del t) in
343 else (let t' = ensureBlackRoot (del t) in
334 if invariants_hold t' then t' else
344 if invariants_hold t' then t' else
335− raise "invariants broken after remove")
345+ Error.raise "invariants broken after remove")
336--}
346--}
337
347
338−map : (a -> b) -> RBTree k a -> RBTree k b
348+-- Apply a function to all values in a dictionary.
349+map : (a -> b) -> Dict (Comparable k) a -> Dict (Comparable k) b
339map f t =
350map f t =
340 case t of
351 case t of
341 RBEmpty -> RBEmpty
352 RBEmpty -> RBEmpty
342 RBNode c k v l r -> RBNode c k (f v) (map f l) (map f r)
353 RBNode c k v l r -> RBNode c k (f v) (map f l) (map f r)
343
354
355+-- Fold over the key-value pairs in a dictionary, in order from lowest
356+-- key to highest key.
344−foldl : (k -> v -> b -> b) -> b -> RBTree k v -> b
357+foldl : (Comparable k -> v -> b -> b) -> b -> Dict (Comparable k) v -> b
345foldl f acc t =
358foldl f acc t =
346 case t of
359 case t of
347 RBEmpty -> acc
360 RBEmpty -> acc
348 RBNode _ k v l r -> foldl f (f k v (foldl f acc l)) r
361 RBNode _ k v l r -> foldl f (f k v (foldl f acc l)) r
349
362
363+-- Fold over the key-value pairs in a dictionary, in order from highest
364+-- key to lowest key.
350−foldr : (k -> v -> b -> b) -> b -> RBTree k v -> b
365+foldr : (Comparable k -> v -> b -> b) -> b -> Dict (Comparable k) v -> b
351foldr f acc t =
366foldr f acc t =
352 case t of
367 case t of
353 RBEmpty -> acc
368 RBEmpty -> acc
354 RBNode _ k v l r -> foldr f (f k v (foldr f acc r)) l
369 RBNode _ k v l r -> foldr f (f k v (foldr f acc r)) l
355
370
356−union : RBTree k v -> RBTree k v -> RBTree k v
371+-- Combine two dictionaries. If there is a collision, preference is given
372+-- to the first dictionary.
373+union : Dict (Comparable k) v -> Dict (Comparable k) v -> Dict (Comparable k) v
357union t1 t2 = foldl insert t2 t1
374union t1 t2 = foldl insert t2 t1
358
375
359−intersect : RBTree k v -> RBTree k v -> RBTree k v
376+-- Keep a key-value pair when its key appears in the second dictionary.
377+-- Preference is given to values in the first dictionary.
378+intersect : Dict (Comparable k) v -> Dict (Comparable k) v -> Dict (Comparable k) v
379+intersect t1 t2 =
360−intersect t1 t2 = foldl (\k v t -> if k `member` t2 then insert k v t else t) empty t1
380+ let combine k v t = if k `member` t2 then insert k v t else t
381+ in foldl combine empty t1
361
382
362−diff : RBTree k v -> RBTree k v -> RBTree k v
383+-- Keep a key-value pair when its key does not appear in the second dictionary.
384+-- Preference is given to the first dictionary.
385+diff : Dict (Comparable k) v -> Dict (Comparable k) v -> Dict (Comparable k) v
363diff t1 t2 = foldl (\k v t -> remove k t) t1 t2
386diff t1 t2 = foldl (\k v t -> remove k t) t1 t2
364
387
365−keys : RBTree k v -> [k]
388+-- Get all of the keys in a dictionary.
389+keys : Dict (Comparable k) v -> [Comparable k]
366keys t = foldr (\k v acc -> k :: acc) [] t
390keys t = foldr (\k v acc -> k :: acc) [] t
367
391
392+-- Get all of the values in a dictionary.
368−values : RBTree k v -> [v]
393+values : Dict (Comparable k) v -> [v]
369values t = foldr (\k v acc -> v :: acc) [] t
394values t = foldr (\k v acc -> v :: acc) [] t
370
395
396+-- Convert a dictionary into an association list of key-value pairs.
371−toList : RBTree k v -> [(k,v)]
397+toList : Dict (Comparable k) v -> [(Comparable k,v)]
372toList t = foldr (\k v acc -> (k,v) :: acc) [] t
398toList t = foldr (\k v acc -> (k,v) :: acc) [] t
373
399
400+-- Convert an association list into a dictionary.
374−fromList : [(k,v)] -> RBTree k v
401+fromList : [(Comparable k,v)] -> Dict (Comparable k) v
375−fromList assocs = Elm.List.foldl (uncurry insert) empty assocs
402+fromList assocs = List.foldl (\(k,v) d -> insert k v d) empty assocs
libraries/Either.elmnew file+51
@@ -0,0 +1,51 @@
1+
2+module Either where
3+
4+import List
5+
6+-- Represents any data that can take two different types.
7+--
8+-- This can also be used for error handling `(Either String a)` where error
9+-- messages are stored on the left, and the correct values (&ldquo;right&rdquo; values) are stored on the right.
10+data Either a b = Left a | Right b
11+
12+-- Apply the first function to a `Left` and the second function to a `Right`.
13+-- This allows the extraction of a value from an `Either`.
14+either : (a -> c) -> (b -> c) -> Either a b -> c
15+either f g e = case e of { Left x -> f x ; Right y -> g y }
16+
17+-- True if the value is a `Left`.
18+isLeft : Either a b -> Bool
19+isLeft e = case e of { Left _ -> True ; _ -> False }
20+
21+-- True if the value is a `Right`.
22+isRight : Either a b -> Bool
23+isRight e = case e of { Right _ -> True ; _ -> False }
24+
25+-- Keep only the values held in `Left` values.
26+lefts : [Either a b] -> [a]
27+lefts es = List.foldr consLeft [] es
28+
29+-- Keep only the values held in `Right` values.
30+rights : [Either a b] -> [b]
31+rights es = List.foldr consRight [] es
32+
33+-- Split into two lists, lefts on the left and rights on the right. So we
34+-- have the equivalence: `(partition es == (lefts es, rights es))`
35+partition : [Either a b] -> ([a],[b])
36+partition es = List.foldr consEither ([],[]) es
37+
38+consLeft e vs =
39+ case e of
40+ Left v -> v::vs
41+ Right _ -> vs
42+
43+consRight e vs =
44+ case e of
45+ Left _ -> vs
46+ Right v -> v::vs
47+
48+consEither e (ls,rs) =
49+ case e of
50+ Left l -> (l::ls,rs)
51+ Right r -> (ls,r::rs)
libraries/Graphics/Collage.elmnew file+205
@@ -0,0 +1,205 @@
1+
2+module Graphics.Collage where
3+
4+import List
5+import Native.Utils (toFloat)
6+import Either
7+import Native.Matrix2D as Matrix
8+import Native.Graphics.Collage as N
9+import Graphics.Element
10+import Color
11+
12+type Form = {
13+ theta : Float,
14+ scale : Float,
15+ x : Float,
16+ y : Float,
17+ form : BasicForm
18+ }
19+
20+data FillStyle
21+ = Solid Color
22+ | Texture String
23+ | Gradient Gradient
24+
25+-- The shape of the ends of a line.
26+data LineCap = Flat | Round | Padded
27+
28+-- The shape of the &ldquo;joints&rdquo; of a line, where each line segment
29+-- meets. `Sharp` takes an argument to limit the length of the joint. This
30+-- defaults to 10.
31+data LineJoin = Smooth | Sharp Float | Clipped
32+
33+-- All of the attributes of a line style. This lets you build up a line style
34+-- however you want. You can also update existing line styles with record updates.
35+type LineStyle = {
36+ color : Color,
37+ width : Float,
38+ cap : LineCap,
39+ join : LineJoin,
40+ dashing : [Int],
41+ dashOffset : Int
42+ }
43+
44+-- The default line style, which is solid black with flat caps and sharp joints.
45+-- You can use record updates to build the line style you
46+-- want. For example, to make a thicker line, you could say:
47+--
48+-- { defaultLine | width <- 10 }
49+defaultLine : LineStyle
50+defaultLine = {
51+ color = Color.black,
52+ width = 1,
53+ cap = Flat,
54+ join = Sharp 10,
55+ dashing = [],
56+ dashOffset = 0
57+ }
58+
59+-- Create a solid line style with a given color.
60+solid : Color -> LineStyle
61+solid clr = { defaultLine | color <- clr }
62+
63+-- Create a dashed line style with a given color. Dashing equals `[8,4]`.
64+dashed : Color -> LineStyle
65+dashed clr = { defaultLine | color <- clr, dashing <- [8,4] }
66+
67+-- Create a dotted line style with a given color. Dashing equals `[3,3]`.
68+dotted : Color -> LineStyle
69+dotted clr = { defaultLine | color <- clr, dashing <- [3,3] }
70+
71+data BasicForm
72+ = FPath LineStyle Path
73+ | FShape (Either LineStyle FillStyle) Shape
74+ | FImage Int Int (Int,Int) String
75+ | FElement Element
76+ | FGroup Matrix2D [Form]
77+
78+form f = { theta = 0, scale = 1, x = 0, y = 0, form = f }
79+
80+fill style shape = form (FShape (Either.Right style) shape)
81+
82+-- Create a filled in shape.
83+filled : Color -> Shape -> Form
84+filled color shape = fill (Solid color) shape
85+
86+-- Create a textured shape. The texture is described by some url and is
87+-- tiled to fill the entire shape.
88+textured : String -> Shape -> Form
89+textured src shape = fill (Texture src) shape
90+
91+-- Fill a shape with a [gradient](/docs/Color.elm#linear).
92+gradient : Gradient -> Shape -> Form
93+gradient grad shape = fill (Gradient grad) shape
94+
95+-- Outline a shape with a given line style.
96+outlined : LineStyle -> Shape -> Form
97+outlined style shape = form (FShape (Either.Left style) shape)
98+
99+-- Trace a path with a given line style.
100+traced : LineStyle -> Path -> Form
101+traced style path = form (FPath style path)
102+
103+-- Create a sprite from a sprite sheet. It cuts out a rectangle
104+-- at a given position.
105+sprite : Int -> Int -> (Int,Int) -> String -> Form
106+sprite w h pos src = form (FImage w h pos src)
107+
108+-- Turn any `Element` into a `Form`. This lets you use text, gifs, and video
109+-- in your collage. This means you can move, rotate, and scale
110+-- an `Element` however you want.
111+toForm : Element -> Form
112+toForm e = form (FElement e)
113+
114+-- Flatten many forms into a single `Form`. This lets you move and rotate them
115+-- as a single unit, making it possible to build small, modular components.
116+group : [Form] -> Form
117+group fs = form (FGroup Matrix.identity fs)
118+
119+-- Flatten many forms into a single `Form` and then apply a matrix
120+-- transformation.
121+groupTransform : Matrix2D -> [Form] -> Form
122+groupTransform matrix fs = form (FGroup matrix fs)
123+
124+-- Rotate a form by a given angle. Rotate takes standard Elm angles (radians)
125+-- and turns things counterclockwise. So to turn `form` 30&deg; to the left
126+-- you would say, `(rotate (degrees 30) form)`.
127+rotate : Float -> Form -> Form
128+rotate t f = { f | theta <- f.theta + t }
129+
130+-- Scale a form by a given factor. Scaling by 2 doubles the size.
131+scale : Float -> Form -> Form
132+scale s f = { f | scale <- f.scale * s }
133+
134+-- Move a form by the given amount. This is a relative translation so
135+-- `(move (10,10) form)` would move `form` ten pixels up and ten pixels to the
136+-- right.
137+move : (Float,Float) -> Form -> Form
138+move (x,y) f = { f | x <- f.x + x, y <- f.y + y }
139+
140+-- Move a shape in the x direction. This is relative so `(moveX 10 form)` moves
141+-- `form` 10 pixels to the right.
142+moveX : Float -> Form -> Form
143+moveX x f = { f | x <- f.x + x }
144+
145+-- Move a shape in the y direction. This is relative so `(moveY 10 form)` moves
146+-- `form` upwards by 10 pixels.
147+moveY : Float -> Form -> Form
148+moveY y f = { f | y <- f.y + y }
149+
150+-- A collage is a collection of 2D forms. There are no strict positioning
151+-- relationships between forms, so you are free to do all kinds of 2D graphics.
152+collage : Int -> Int -> [Form] -> Element
153+
154+
155+type Path = [(Float,Float)]
156+
157+-- Create a path that follows a sequence of points.
158+path : [(Number a,Number a)] -> Path
159+path ps = ps
160+
161+-- Create a path along a given line segment.
162+segment : (Number a,Number a) -> (Number a,Number a) -> Path
163+segment p1 p2 = [p1,p2]
164+
165+type Shape = [(Float,Float)]
166+
167+-- Create an arbitrary polygon by specifying its corners in order.
168+-- `polygon` will automatically close all shapes, so the given list
169+-- of points does not need to start and end with the same position.
170+polygon : [(Number a,Number a)] -> Shape
171+polygon points = points
172+
173+-- A rectangle with a given width and height.
174+rect : Number a -> Number a -> Shape
175+rect w h = [ (0-w/2,0-h/2), (0-w/2,h/2), (w/2,h/2), (w/2,0-h/2) ]
176+
177+-- A square with a given edge length.
178+square : Number a -> Shape
179+square n = rect w h
180+
181+-- An oval with a given width and height.
182+oval : Number a -> Number a -> Shape
183+oval w h =
184+ let n = 50
185+ t = 2 * Math.PI / n
186+ hw = w/2
187+ hh = h/2
188+ f i = (hw * Math.cos (t*i), hh * Math.sin (t*i))
189+ in List.map f [0..n-1]
190+
191+-- A circle with a given radius.
192+circle : Number a -> Shape
193+circle r = oval (2*r) (2*r)
194+
195+-- A regular polygon with N sides. The first argument specifies the number
196+-- of sides and the second is the radius. So to create a pentagon with radius
197+-- 30 you would say:
198+--
199+-- ngon 5 30
200+ngon : Int -> Number a -> Shape
201+ngon n r =
202+ let m = toFloat n
203+ t = 2 * Math.PI / m
204+ f i = ( r * Math.cos (t*i), r * Math.sin (t*i) )
205+ in List.map f [0..n-1]
libraries/Graphics/Element.elmnew file+255
@@ -0,0 +1,255 @@
1+
2+module Graphics.Element (widthOf, heightOf, sizeOf,
3+ width, height, opacity, color, tag, link,
4+ image, fittedImage, croppedImage,
5+ flow, up, down, left, right, inward, outward,
6+ above, below, beside, layers,
7+ container, absolute, relative,
8+ middle, topLeft, topRight, bottomLeft, bottomRight,
9+ midLeft, midRight, midTop, midBottom, middleAt,
10+ topLeftAt, topRightAt, bottomLeftAt, bottomRightAt,
11+ midLeftAt, midRightAt, midTopAt, midBottomAt,
12+ spacer, newElement
13+ ) where
14+
15+import Native.Utils (guid, max, htmlHeight)
16+import JavaScript as JS
17+import List as List
18+import Color
19+import Maybe (Just, Nothing)
20+
21+type Properties = {
22+ id : Int,
23+ width : Int,
24+ height : Int,
25+ opacity : Float,
26+ color : Maybe Color,
27+ href : JSString,
28+ tag : JSString
29+ }
30+
31+type Element = { props : Properties, element : ElementPrim }
32+
33+-- Get the width of an Element
34+widthOf : Element -> Int
35+widthOf e = e.props.width
36+
37+-- Get the height of an Element
38+heightOf : Element -> Int
39+heightOf e = e.props.height
40+
41+-- Get the width and height of an Element
42+sizeOf : Element -> (Int,Int)
43+sizeOf e = (e.props.width, e.props.height)
44+
45+-- Create an `Element` with a given width.
46+width : Int -> Element -> Element
47+width nw e = let p = e.props
48+ props = case e.element of
49+ Image _ w h _ -> {p| height <- h/w*nw }
50+ RawHtml html -> {p| height <- let (w,h) = htmlHeight nw html in h}
51+ _ -> p
52+ in { element=e.element, props={props| width <- nw} }
53+
54+-- Create an `Element` with a given height.
55+height : Int -> Element -> Element
56+height nh e = let p = e.props
57+ props = case e.element of
58+ Image _ w h _ -> {p| width <- w/h*nh }
59+ _ -> p
60+ in { element=e.element, props={p| height <- nh} }
61+
62+-- Create an `Element` with a given opacity. Opacity is a number between 0 and 1
63+-- where 0 means totally clear.
64+opacity : Float -> Element -> Element
65+opacity o e = let p = e.props in { element=e.element, props={p| opacity <- o} }
66+
67+-- Create an `Element` with a given background color.
68+color : Color -> Element -> Element
69+color c e = let p = e.props in
70+ { element=e.element, props={p| color <- Just c} }
71+
72+-- Create an `Element` with a tag. This lets you link directly to it.
73+-- The element `(tag "all-about-badgers" thirdParagraph)` can be reached
74+-- with a link lik this: `/facts-about-animals.elm#all-about-badgers`
75+tag : String -> Element -> Element
76+tag name e = let p = e.props in
77+ { element=e.element, props={p| tag <- JS.fromString name} }
78+
79+-- Create an `Element` that is a hyper-link.
80+link : String -> Element -> Element
81+link href e = let p = e.props in
82+ { element=e.element, props={p| href <- JS.fromString href} }
83+
84+emptyStr = JS.fromString ""
85+newElement w h e =
86+ { props = Properties (guid ()) w h 1 Nothing emptyStr emptyStr, element = e }
87+
88+data ElementPrim
89+ = Image ImageStyle Int Int JSString
90+ | Container Position Element
91+ | Flow Direction [Element]
92+ | Spacer
93+ | RawHtml JSString
94+ | Custom -- for custom Elements implemented in JS, see collage for example
95+
96+data ImageStyle = Plain | Fitted | Cropped (Int,Int)
97+
98+-- Create an image given a width, height, and image source.
99+image : Int -> Int -> String -> Element
100+image w h src = newElement w h (Image Plain w h (JS.fromString src))
101+
102+-- Create a fitted image given a width, height, and image source.
103+-- This will crop the picture to best fill the given dimensions.
104+fittedImage : Int -> Int -> String -> Element
105+fittedImage w h src = newElement w h (Image Fitted w h (JS.fromString src))
106+
107+-- Create a cropped image. Take a rectangle out of the picture starting
108+-- at the given top left coordinate. If you have a 140-by-140 image,
109+-- the following will cut a 100-by-100 square out of the middle of it.
110+--
111+-- croppedImage 100 100 (20,20) "yogi.jpg"
112+croppedImage : Int -> Int -> (Int,Int) -> String -> Element
113+croppedImage w h pos src =
114+ newElement w h (Image (Cropped pos) w h (JS.fromString src))
115+
116+data Three = P | Z | N
117+data Pos = Absolute Int | Relative Float
118+type Position = { horizontal : Three, vertical : Three, x : Pos, y : Pos }
119+
120+-- Put an element in a container. This lets you position the element really
121+-- easily, and there are tons of ways to set the `Position`.
122+-- To center `element` exactly in a 300-by-300 square you would say:
123+--
124+-- container 300 300 middle element
125+--
126+-- By setting the color of the container, you can create borders.
127+container : Int -> Int -> Position -> Element -> Element
128+container w h pos e = newElement w h (Container pos e)
129+
130+-- Create an empty box. This is useful for getting your spacing right and
131+-- for making borders.
132+spacer : Int -> Int -> Element
133+spacer w h = newElement w h Spacer
134+
135+data Direction = DUp | DDown | DLeft | DRight | DIn | DOut
136+
137+-- Have a list of elements flow in a particular direction.
138+-- The `Direction` starts from the first element in the list.
139+--
140+-- flow right [a,b,c]
141+--
142+-- +---+---+---+
143+-- | a | b | c |
144+-- +---+---+---+
145+flow : Direction -> [Element] -> Element
146+flow dir es =
147+ let ws = List.map widthOf es
148+ hs = List.map heightOf es
149+ newFlow w h = newElement w h (Flow dir es)
150+ in
151+ if es == [] then spacer 0 0 else
152+ case dir of
153+ DUp -> newFlow (List.maximum ws) (List.sum hs)
154+ DDown -> newFlow (List.maximum ws) (List.sum hs)
155+ DLeft -> newFlow (List.sum ws) (List.maximum hs)
156+ DRight -> newFlow (List.sum ws) (List.maximum hs)
157+ DIn -> newFlow (List.maximum ws) (List.maximum hs)
158+ DOut -> newFlow (List.maximum ws) (List.maximum hs)
159+
160+-- Stack elements vertically. To put `a` above `b` you would say:
161+--
162+-- a `above` b
163+above : Element -> Element -> Element
164+above hi lo =
165+ newElement (max (widthOf hi) (widthOf lo))
166+ (heightOf hi + heightOf lo)
167+ (Flow DDown [hi,lo])
168+
169+-- Stack elements vertically. To put `a` below `b` you would say:
170+--
171+-- a `below` b
172+below : Element -> Element -> Element
173+below lo hi =
174+ newElement (max (widthOf hi) (widthOf lo))
175+ (heightOf hi + heightOf lo)
176+ (Flow DDown [hi,lo])
177+
178+-- Put elements beside each other horizontally.
179+beside : Element -> Element -> Element
180+beside lft rht =
181+ newElement (widthOf lft + widthOf rht)
182+ (max (heightOf lft) (heightOf rht))
183+ (Flow right [lft,rht])
184+
185+-- Layer elements on top of each other, starting from the bottom.
186+-- `(layers == flow outward)`
187+layers : [Element] -> Element
188+layers es =
189+ let ws = List.map widthOf es
190+ hs = List.map heightOf es
191+ in newElement (List.maximum ws) (List.maximum hs) (Flow DOut es)
192+
193+
194+-- Repetitive things --
195+
196+absolute : Int -> Pos
197+absolute = Absolute
198+relative : Float -> Pos
199+relative = Relative
200+
201+middle : Position
202+middle = { horizontal=Z, vertical=Z, x=Relative 0.5, y=Relative 0.5 }
203+topLeft : Position
204+topLeft = { horizontal=N, vertical=P, x=Absolute 0, y=Absolute 0 }
205+topRight : Position
206+topRight = { topLeft | horizontal <- P }
207+bottomLeft : Position
208+bottomLeft = { topLeft | vertical <- N }
209+bottomRight : Position
210+bottomRight = { bottomLeft | horizontal <- P }
211+midLeft : Position
212+midLeft = { middle | horizontal <- N, x <- Absolute 0 }
213+midRight : Position
214+midRight = { midLeft | horizontal <- P }
215+midTop : Position
216+midTop = { middle | vertical <- P, y <- Absolute 0 }
217+midBottom : Position
218+midBottom = { midTop | vertical <- N }
219+
220+middleAt : Pos -> Pos -> Position
221+middleAt x y = { horizontal = Z, vertical = Z, x = x, y = y }
222+topLeftAt : Pos -> Pos -> Position
223+topLeftAt x y = { horizontal = N, vertical = P, x = x, y = y }
224+topRightAt : Pos -> Pos -> Position
225+topRightAt x y = { horizontal = P, vertical = P, x = x, y = y }
226+bottomLeftAt : Pos -> Pos -> Position
227+bottomLeftAt x y = { horizontal = N, vertical = N, x = x, y = y }
228+bottomRightAt : Pos -> Pos -> Position
229+bottomRightAt x y = { horizontal = P, vertical = N, x = x, y = y }
230+midLeftAt : Pos -> Pos -> Position
231+midLeftAt x y = { horizontal = N, vertical = Z, x = x, y = y }
232+midRightAt : Pos -> Pos -> Position
233+midRightAt x y = { horizontal = P, vertical = Z, x = x, y = y }
234+midTopAt : Pos -> Pos -> Position
235+midTopAt x y = { horizontal = Z, vertical = P, x = x, y = y }
236+midBottomAt : Pos -> Pos -> Position
237+midBottomAt x y = { horizontal = Z, vertical = N, x = x, y = y }
238+
239+up : Direction
240+up = DUp
241+
242+down : Direction
243+down = DDown
244+
245+left : Direction
246+left = DLeft
247+
248+right : Direction
249+right = DRight
250+
251+inward : Direction
252+inward = DIn
253+
254+outward : Direction
255+outward = DOut
libraries/Graphics/Input.elmnew file+119
@@ -0,0 +1,119 @@
1+
2+module Graphics.Input where
3+
4+import Signal (lift)
5+import Native.Graphics.Input as N
6+
7+id x = x
8+
9+-- Create a group of buttons.
10+--
11+-- * The first argument is the default value of the `events` signal.
12+-- * The `events` signal represents all of the activity in this group
13+-- of buttons.
14+-- * The `button` function creates a button
15+-- with the given name, like &ldquo;Submit&rdquo; or &ldquo;Cancel&rdquo;.
16+-- The `a` value is sent to `events` whenever the button is pressed.
17+buttons : a -> { events : Signal a,
18+ button : a -> String -> Element }
19+
20+-- Create a button with a given label. The result is an `Element` and
21+-- a signal of units. This signal triggers whenever the button is pressed.
22+button : String -> (Element, Signal ())
23+button txt =
24+ let pool = N.buttons ()
25+ in (pool.button () txt, pool.events)
26+
27+-- Create a group of custom buttons.
28+--
29+-- * The first argument is the default value of the `events` signal.
30+-- * The `events` signal represents all of the activity in this group
31+-- of custom buttons.
32+-- * The `customButton` function creates a button with three different visual
33+-- states, one for up, hovering, and down. The resulting button has dimensions
34+-- large enough to fit all three possible `Elements`.
35+-- The `a` value is sent to `events` whenever the button is pressed.
36+customButtons : a -> { events : Signal a,
37+ customButton : a -> Element -> Element -> Element -> Element }
38+
39+-- Create a button with custom states for up, hovering, and down
40+-- (given in that order). The result is an `Element` and
41+-- a signal of units. This signal triggers whenever the button is pressed.
42+customButton : Element -> Element -> Element -> (Element, Signal ())
43+customButton up hover down =
44+ let pool = N.customButtons ()
45+ in (pool.button () up hover down, pool.events)
46+
47+-- Create a group of checkboxes.
48+--
49+-- * The first argument is the default value of the `events` signal.
50+-- * The `events` signal represents all of the activity in this group
51+-- of checkboxes.
52+-- * The `checkbox` function creates a
53+-- checkbox with a given state. The `(Bool -> a)` function is used
54+-- when the checkbox is modified. It takes the new state and turns
55+-- it into a value that can be sent to `events`. For example, this
56+-- lets you add an ID to distinguish between checkboxes.
57+checkboxes : a -> { events : Signal a,
58+ checkbox : (Bool -> a) -> Bool -> Element }
59+
60+-- Create a checkbox with a given start state. Unlike `button`, this result
61+-- is a *signal* of elements. That is because a checkbox has state that
62+-- updates based on user input.
63+-- The boolean signal represents the current state of the checkbox.
64+checkbox : Bool -> (Signal Element, Signal Bool)
65+checkbox b =
66+ let cbs = N.checkboxes b
67+ in (lift (cbs.box id) cbs.events, cbs.events)
68+
69+-- Represents the current state of a text field. The `string` represents the
70+-- characters filling the text field. The `selectionStart` and `selectionEnd`
71+-- values represent what the user has selected with their mouse or keyboard.
72+-- For example:
73+--
74+-- { string="She sells sea shells", selectionStart=3, selectionEnd=0 }
75+--
76+-- This means the user highlighted the substring `"She"` backwards.
77+type FieldState = { string:String, selectionStart:Int, selectionEnd:Int }
78+
79+-- Create a group of text input fields.
80+--
81+-- * The first argument is the default value of the `events` signal.
82+-- * The `events` signal represents all of the activity in this group
83+-- of text fields.
84+-- * The `field` function creates a
85+-- field with the given ghost text and initial field state.
86+-- When the field is modified, the `(FieldState -> a)` function
87+-- takes the new state and turns
88+-- it into a value that can be sent to `events`. For example, this
89+-- lets you add an ID to distinguish between input fields.
90+fields : a -> { events : Signal a,
91+ field : (FieldState -> a) -> String -> FieldState -> Element }
92+
93+-- The empty field state:
94+--
95+-- { string="", selectionStart=0, selectionEnd=0 }
96+emptyFieldState : FieldState
97+emptyFieldState = { string="", selectionStart=0, selectionEnd=0 }
98+
99+-- Create a field with the given default text. The output is an element that
100+-- updates to match the user input and a signal of strings representing the
101+-- content of the field.
102+field : String -> (Signal Element, Signal String)
103+field placeHolder =
104+ let tfs = N.fields emptyFieldState
105+ in (lift (tfs.field id placeHolder) tfs.events, lift .string tfs.events)
106+
107+-- Same as `field` but the UI element blocks out each characters.
108+password : String -> (Signal Element, Signal String)
109+password placeHolder =
110+ let tfs = N.passwords emptyFieldState
111+ in (lift (tfs.field id placeHolder) tfs.events, lift .string tfs.events)
112+
113+-- Same as `field` but it adds an annotation that this field is for email
114+-- addresses. This is helpful for auto-complete and for mobile users who may
115+-- get a custom keyboard with an `@` and `.com` button.
116+email : String -> (Signal Element, Signal String)
117+email placeHolder =
118+ let tfs = N.emails emptyFieldState
119+ in (lift (tfs.field id placeHolder) tfs.events, lift .string tfs.events)
libraries/Http.elmnew file+43
@@ -0,0 +1,43 @@
1+-- A library for asynchronous HTTP requests (AJAX). See the
2+-- [WebSocket](http://elm-lang.org/docs/WebSocket.elm) library if
3+-- you have very strict latency requirements.
4+
5+module Http where
6+
7+import Native.Http (send)
8+import Signal (lift)
9+
10+-- The datatype for responses. Success contains only the returned message.
11+-- Failures contain both an error code and an error message.
12+data Response a = Success a | Waiting | Failure Int String
13+
14+type Request a = {
15+ verb : String,
16+ url : String,
17+ body : a,
18+ headers : [(String,String)]
19+ }
20+
21+-- Create a customized request. Arguments are request type (get, post, put,
22+-- delete, etc.), target url, data, and a list of additional headers.
23+request : String -> String -> String -> [(String,String)] -> Request String
24+request = Request
25+
26+-- Create a GET request to the given url.
27+get : String -> Request String
28+get url = Request "GET" url "" []
29+
30+-- Create a POST request to the given url, carrying the given data.
31+post : String -> String -> Request String
32+post url body = Request "POST" url body []
33+
34+
35+-- Performs an HTTP request with the given requests. Produces a signal
36+-- that carries the responses.
37+send : Signal (Request a) -> Signal (Response String)
38+
39+-- Performs an HTTP GET request with the given urls. Produces a signal
40+-- that carries the responses.
41+sendGet : Signal String -> Signal (Response String)
42+sendGet reqs = send (lift get reqs)
43+
libraries/JavaScript.elmnew file+26
@@ -0,0 +1,26 @@
1+
2+module JavaScript where
3+
4+
5+-- Requires that the input array be uniform (all members have the same type)
6+toList : JSArray a -> [a]
7+toInt : JSNumber -> Int
8+toFloat : JSNumber -> Float
9+toBool : JSBool -> Bool
10+toString : JSString -> String
11+
12+
13+-- Produces a uniform JavaScript array with all members of the same type.
14+fromList : [a] -> JSArray a
15+fromInt : Int -> JSNumber
16+fromFloat : Float -> JSNumber
17+fromBool : Bool -> JSBool
18+fromString : String -> JSString
19+
20+
21+-- Turn an `Element` into a plain old DOM node.
22+fromElement : Element -> JSDomNode
23+
24+-- Turn a DOM node into an `Element`. You can resize the node
25+-- using the normal `width` and `height` functions.
26+toElement : Int -> Int -> JSDomNode -> Element
libraries/JavaScript/Experimental.elmnew file+31
@@ -0,0 +1,31 @@
1+
2+module JavaScript.Experimental where
3+
4+import JavaScript as JS
5+
6+-- Turn arbitrary JavaScript objects into Elm records.
7+-- Arrays are converted into lists, nested objects are allowed.
8+-- No `null` values or non-homogeneous arrays.
9+--
10+-- -- OK objects
11+-- { student:"Steve", scores:[83,94,99,72] }
12+-- { errorLevel:10, critical:true }
13+--
14+-- -- BAD objects
15+-- { answer:null }
16+-- { info:[true,42,'what'] }
17+toRecord : JSObject -> a
18+toRecord = JS.toRecord
19+
20+-- Turn arbitrary Elm records into JavaScript objects.
21+-- Lists become arrays, nested records are allowed. No ADTs.
22+--
23+-- -- OK records
24+-- { student="Steve", scores=[83,94,99,72] }
25+-- { errorLevel=10, critical=True }
26+--
27+-- -- BAD records
28+-- { answer = Nothing }
29+-- { result = Left "An error occurred" }
30+fromRecord : a -> JSObject
31+fromRecord = JS.fromRecord
libraries/Json.elmnew file+112
@@ -0,0 +1,112 @@
1+
2+-- TOOD: Evan please review texts
3+
4+module Json where
5+
6+import Dict as Dict
7+import JavaScript as JS
8+import Native.Json as Native
9+
10+-- This datatype can represent all valid values that can be held in a JSON
11+-- object. In Elm, a proper JSON object is represented as a (Dict String JsonValue)
12+-- which is a mapping from strings to Json Values.
13+data JsonValue
14+ = String String
15+ | Number Float
16+ | Boolean Bool
17+ | Null
18+ | Array [JsonValue]
19+ | Object (Dict String JsonValue)
20+
21+
22+-- String Converters
23+
24+-- Convert a `JsonValue` into a prettified string.
25+-- The first argument is a separator token (e.g. \" \", \"\\n\", etc.) that will
26+-- be used for indentation in the prettified string version of the JSON.
27+toString : String -> JsonValue -> String
28+toString sep v = JS.toString (Native.toJSString sep v)
29+
30+-- Convert a proper JSON object into a JavaScript string.
31+-- Note that the type JSString seen here is not the same as the type constructor
32+-- JsonString used elsewhere in this module.
33+toJSString : String -> JsonValue -> JSString
34+
35+-- Parse a string representation of a proper JSON object into
36+-- its Elm representation.
37+fromString : String -> Maybe JsonValue
38+fromString s = Native.fromJSString (JS.fromString s)
39+
40+-- Parse a JavaScript string representation of a proper JSON object into
41+-- its Elm representation.
42+fromJSString : JSString -> Maybe JsonValue
43+
44+-- Convert a JS object into a `JsonValue`.
45+fromJSObject : JSObject -> JsonValue
46+
47+-- Convert a `JsonValue` into a `JSObject`. Paired with the
48+-- [`JavaScript.Experimental` library](/docs/JavaScript/Experimental.elm),
49+-- This lets you convert strings into Elm records:
50+--
51+-- import JavaScript.Experimental as JS
52+--
53+-- stringToRecord str =
54+-- case fromString str of
55+-- Just jsonValue -> Just (JS.toRecord (toJSObject jsonValue))
56+-- Nothing -> Nothing
57+toJSObject : JsonValue -> JSObject
58+
59+ {-- Extract Elm values from Json values
60+
61+ string : JsonValue -> String
62+ string v = case v of { String s -> s ; _ -> "" }
63+
64+ number : JsonValue -> Float
65+ number v = case v of { Number n -> n ; _ -> 0 }
66+
67+ boolean : JsonValue -> Bool
68+ boolean v = case v of { Boolean b -> b ; _ -> False }
69+
70+ array : JsonValue -> [JsonValue]
71+ array v = case v of { Array a -> a ; _ -> [] }
72+
73+ object : JsonValue -> Dict String JsonValue
74+ object v = case v of { Object o -> o ; _ -> Dict.empty }
75+
76+
77+ -- Extract Elm values from dictionaries of Json values
78+
79+ -- Find a value in a Json Object using the passed get function. If the key is
80+ -- not found, this returns the given default/base value.
81+ find get base =
82+ let f key dict =
83+ case Dict.lookup key dict of
84+ Nothing -> base
85+ Just v -> get v
86+ in f
87+
88+ -- Find a string value in an Elm Json object. If the key is not found or the
89+ -- value found is not a string, this returns the empty string.
90+ findString : String -> Object -> String
91+ findString = find string ""
92+
93+ -- Find a number value in an Elm Json object. If the key is not found or the
94+ -- value found is not a number, this returns 0
95+ findNumber : String -> Object -> Float
96+ findNumber = find number 0
97+
98+ -- Find a boolean value in an Elm Json object. If the key is not found or the
99+ -- value found is not a boolean, this returns the False.
100+ findBoolean : String -> Object -> Bool
101+ findBoolean = find boolean False
102+
103+ -- Find an array value in an Elm Json object. If the key is not found or the
104+ -- value found is not an array, this returns an empty list.
105+ findArray : String -> Object -> [JsonValue]
106+ findArray = find array []
107+
108+ -- Find an object value in an Elm Json object. If the key is not found or the
109+ -- value found is not an object, this returns an empty object.
110+ findObject : String -> Object -> Object
111+ findObject = find object Dict.empty
112+ --}
libraries/Keyboard.elmnew file+52
@@ -0,0 +1,52 @@
1+module Keyboard where
2+
3+import Native.Keyboard as N
4+
5+-- Type alias to make it clearer what integers are supposed to represent
6+-- in this library. Use [`Char.toCode`](docs/Char.elm#toCode) and
7+-- [`Char.fromCode`](/docs/Char.elm#fromCode) to convert key codes to characters.
8+type KeyCode = Int
9+
10+-- A signal of records indicating which arrow keys are pressed.
11+--
12+-- `{ x = 0, y = 0 }` when pressing no arrows.<br>
13+-- `{ x =-1, y = 0 }` when pressing the left arrow.<br>
14+-- `{ x = 1, y = 1 }` when pressing the up and right arrows.<br>
15+-- `{ x = 0, y =-1 }` when pressing the down, left, and right arrows.
16+arrows : Signal { x:Int, y:Int }
17+arrows = N.directions 38 40 37 39
18+
19+-- Just like the arrows signal, but this uses keys w, a, s, and d,
20+-- which are common controls for many computer games.
21+wasd : Signal { x:Int, y:Int }
22+wasd = N.directions 87 83 65 68
23+
24+-- Custom key directions so that you can support different locales.
25+-- The plan is to have a locale independent version of this function
26+-- that uses the physical location of keys, but I don't know how to do it.
27+directions : KeyCode -> KeyCode -> KeyCode -> KeyCode -> Signal { x:Int, y:Int }
28+
29+-- Whether an arbitrary key is pressed.
30+isDown : KeyCode -> Signal Bool
31+
32+-- Whether the shift key is pressed.
33+shift : Signal Bool
34+shift = N.isDown 16
35+
36+-- Whether the control key is pressed.
37+ctrl : Signal Bool
38+ctrl = N.isDown 17
39+
40+-- Whether the space key is pressed.
41+space : Signal Bool
42+space = N.isDown 32
43+
44+-- Whether the enter key is pressed.
45+enter : Signal Bool
46+enter = N.isDown 13
47+
48+-- List of keys that are currently down.
49+keysDown : Signal [KeyCode]
50+
51+-- The latest key that has been pressed.
52+lastPressed : Signal KeyCode
libraries/List.elmnew file+155
@@ -0,0 +1,155 @@
1+
2+module List where
3+
4+import Native.Utils (min, max)
5+import Native.List as L
6+
7+-- Add an element to the front of a list `(1 :: [2,3] == [1,2,3])`
8+(::) : a -> [a] -> [a]
9+
10+-- Puts two appendable things together:
11+--
12+-- [1,1] ++ [2,3] == [1,1,2,3]
13+-- "abc" ++ "123" == "abc123"
14+(++) : Appendable a -> Appendable a -> Appendable a
15+
16+-- Extract the first element of a list. List must be non-empty.
17+-- `(head [1,2,3] == 1)`
18+head : [a] -> a
19+
20+-- Extract the elements after the head of the list. List must be non-empty.
21+-- `(tail [1,2,3] == [2,3])`
22+tail : [a] -> [a]
23+
24+-- Extract the last element of a list. List must be non-empty.
25+-- `(last [1,2,3] == 3)`
26+last : [a] -> a
27+
28+-- Apply a function to every element of a list: `(map sqrt [1,4,9] == [1,2,3])`
29+map : (a -> b) -> [a] -> [b]
30+
31+-- Reduce a list from the left: `(foldl (::) [] "gateman" == "nametag")`
32+foldl : (a -> b -> b) -> b -> [a] -> b
33+
34+-- Reduce a list from the right: `(foldr (+) 0 [1,2,3] == 6)`
35+foldr : (a -> b -> b) -> b -> [a] -> b
36+
37+-- Reduce a list from the left without a base case. List must be non-empty.
38+foldl1 : (a -> a -> a) -> [a] -> a
39+
40+-- Reduce a list from the right without a base case. List must be non-empty.
41+foldr1 : (a -> a -> a) -> [a] -> a
42+
43+-- Reduce a list from the left, building up all of the intermediate results into a list.
44+--
45+-- scanl (+) 0 [1,2,3,4] == [0,1,3,6,10]
46+scanl : (a -> b -> b) -> b -> [a] -> [b]
47+
48+-- Same as scanl but it doesn't require a base case. List must be non-empty.
49+--
50+-- scanl1 (+) [1,2,3,4] == [1,3,6,10]
51+scanl1 : (a -> a -> a) -> [a] -> [a]
52+
53+-- Filter out elements which do not satisfy the predicate: `(filter isLower "AaBbCc" == "abc")`
54+filter : (a -> Bool) -> [a] -> [a]
55+
56+-- Determine the length of a list: `(length "innumerable" == 11)`
57+length : [a] -> Int
58+
59+-- Reverse a list. `(reverse [1..4] == [4,3,2,1])`
60+reverse : [a] -> [a]
61+
62+-- Check to see if all elements satisfy the predicate.
63+all : (a -> Bool) -> [a] -> Bool
64+
65+-- Check to see if any elements satisfy the predicate.
66+any : (a -> Bool) -> [a] -> Bool
67+
68+-- Check to see if all elements are True.
69+and : [Bool] -> Bool
70+
71+-- Check to see if any elements are True.
72+or : [Bool] -> Bool
73+
74+-- Concatenate a list of appendable things:
75+--
76+-- concat ["tree","house"] == "treehouse"
77+concat : [Appendable a] -> Appendable a
78+
79+-- Map a given function onto a list and flatten the resulting lists.
80+--
81+-- concatMap f xs == concat (map f xs)
82+concatMap : (a -> Appendable b) -> [a] -> Appendable b
83+concatMap f = L.concat . L.map f
84+
85+-- Get the sum of the list elements. `(sum [1..4] == 10)`
86+sum : [Number a] -> Number a
87+sum = L.foldl (+) 0
88+
89+-- Get the product of the list elements. `(product [1..4] == 24)`
90+product : [Number a] -> Number a
91+product = L.foldl (*) 1
92+
93+-- Find the highest number in a non-empty list.
94+maximum : [Number a] -> Number a
95+maximum = L.foldl1 max
96+
97+-- Find the lowest number in a non-empty list.
98+minimum : [Number a] -> Number a
99+minimum = L.foldl1 min
100+
101+-- Split a list based on the predicate.
102+partition : (a -> Bool) -> [a] -> ([a],[a])
103+partition pred lst =
104+ case lst of
105+ [] -> ([],[])
106+ x::xs -> let (bs,cs) = partition pred xs in
107+ if pred x then (x::bs,cs) else (bs,x::cs)
108+
109+-- Combine two lists, combining them into tuples pairwise.
110+-- If one list is longer, the extra elements are dropped.
111+--
112+-- zip [1,2,3] [6,7] == [(1,6),(2,7)]
113+-- zip == zipWith (,)
114+zip : [a] -> [b] -> [(a,b)]
115+
116+-- Combine two lists, combining them with the given function.
117+-- If one list is longer, the extra elements are dropped.
118+--
119+-- zipWith (+) [1,2,3] [1,2,3,4] == [2,4,6]
120+zipWith : (a -> b -> c) -> [a] -> [b] -> [c]
121+
122+-- Decompose a list of tuples.
123+unzip : [(a,b)] -> ([a],[b])
124+unzip pairs =
125+ case pairs of
126+ [] -> ([],[])
127+ (x,y)::ps -> let (xs,ys) = (unzip ps) in (x::xs,y::ys)
128+
129+-- Split a list with a given seperator.
130+--
131+-- split "," "hello,there,friend" == ["hello", "there", "friend"]
132+split : [a] -> [a] -> [[a]]
133+
134+-- Places the given value between all of the lists in the second argument
135+-- and concatenates the result.
136+--
137+-- join "a" ["H","w","ii","n"] == "Hawaiian"
138+join : Appendable a -> [Appendable a] -> Appendable a
139+
140+-- Places the given value between all members of the given list.
141+--
142+-- intersperse ' ' "INCEPTION" == "I N C E P T I O N"
143+intersperse : a -> [a] -> [a]
144+intersperse sep xs =
145+ case xs of
146+ a::b::cs -> a :: sep :: intersperse sep (b::cs)
147+ [a] -> [a]
148+ [] -> []
149+
150+-- Take the first n members of a list: `(take 2 [1,2,3,4] == [1,2])`
151+take : Int -> [a] -> [a]
152+
153+-- Drop the first n members of a list: `(drop 2 [1,2,3,4] == [3,4])`
154+drop : Int -> [a] -> [a]
155+
libraries/Matrix2D.elmnew file+36
@@ -0,0 +1,36 @@
1+
2+module Matrix2D where
3+
4+import Native.Matrix2D as M
5+
6+-- Create an identity matrix.
7+--
8+-- / 1 0 \\
9+-- \\ 0 1 /
10+identity : Matrix2D
11+
12+-- Creates an arbitrary matrix. This lets you create scales, shears, reflections,
13+-- translations, or any other 2D transform.
14+--
15+-- matrix a b c d dx dy
16+--
17+-- / a b \\
18+-- \\ c d /
19+--
20+-- And `dx` and `dy` are the translation values.
21+matrix : Float -> Float -> Float -> Float -> Float -> Float -> Matrix2D
22+
23+-- Creates a [rotation matrix](http://en.wikipedia.org/wiki/Rotation_matrix).
24+-- Given an angle t, it creates a counterclockwise rotation matrix:
25+--
26+-- / cos t -sin t \\
27+-- \\ sin t cos t /
28+rotation : Float -> Matrix2D
29+
30+-- Multiplies two matrices together:
31+--
32+-- multiply a b
33+--
34+-- / a11 a12 \\ . / b11 b12 \\
35+-- \\ a21 a22 / \\ b21 b22 /
36+multiply : Matrix2D -> Matrix2D -> Matrix2D
libraries/Maybe.elmnew file+33
@@ -0,0 +1,33 @@
1+
2+module Maybe where
3+
4+import List as List
5+
6+-- The Maybe datatype. Useful when a computation may or may not
7+-- result in a value (e.g. logarithm is defined only for positive numbers).
8+data Maybe a = Just a | Nothing
9+
10+-- Apply a function to the contents of a `Maybe`.
11+-- Return default when given `Nothing`.
12+maybe : b -> (a -> b) -> Maybe a -> b
13+maybe b f m = case m of
14+ Just v -> f v
15+ Nothing -> b
16+
17+-- Check if constructed with `Just`.
18+isJust : Maybe a -> Bool
19+isJust = maybe False (\_ -> True)
20+
21+-- Check if constructed with `Nothing`.
22+isNothing : Maybe a -> Bool
23+isNothing = not . isJust
24+
25+
26+-- If `Just`, adds the value to the front of the list.
27+-- If `Nothing`, list is unchanged.
28+cons : Maybe a -> [a] -> [a]
29+cons mx xs = maybe xs (\x -> x :: xs) mx
30+
31+-- Filters out Nothings and extracts the remaining values.
32+justs : [Maybe a] -> [a]
33+justs = List.foldr cons []
libraries/Mouse.elmnew file+24
@@ -0,0 +1,24 @@
1+
2+module Mouse where
3+
4+import Native.Mouse as M
5+
6+-- The current mouse position.
7+position : Signal (Int,Int)
8+
9+-- The current x-coordinate of the mouse.
10+x : Signal Int
11+
12+-- The current y-coordinate of the mouse.
13+y : Signal Int
14+
15+-- The current state of the left mouse-button.
16+-- True when the button is down, and false otherwise.
17+isDown : Signal Bool
18+
19+-- True immediately after the left mouse-button has been clicked,
20+-- and false otherwise.
21+isClicked : Signal Bool
22+
23+-- Always equal to unit. Event triggers on every mouse click.
24+clicks : Signal ()
libraries/Native/Char.jsnew file+31
@@ -0,0 +1,31 @@
1+
2+Elm.Native.Char = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Char) return elm.Native.Char;
7+
8+ function isBetween(lo,hi) { return function(chr) {
9+ var c = chr.charCodeAt(0);
10+ return lo <= c && c <= hi;
11+ };
12+ }
13+ var isDigit = isBetween('0'.charCodeAt(0),'9'.charCodeAt(0));
14+ var chk1 = isBetween('a'.charCodeAt(0),'f'.charCodeAt(0));
15+ var chk2 = isBetween('A'.charCodeAt(0),'F'.charCodeAt(0));
16+
17+ return elm.Native.Char = {
18+ fromCode : function(c) { return String.fromCharCode(c); },
19+ toCode : function(c) { return c.charCodeAt(0); },
20+ toUpper : function(c) { return c.toUpperCase(); },
21+ toLower : function(c) { return c.toLowerCase(); },
22+ toLocaleUpper : function(c) { return c.toLocaleUpperCase(); },
23+ toLocaleLower : function(c) { return c.toLocaleLowerCase(); },
24+ isLower : isBetween('a'.charCodeAt(0),'z'.charCodeAt(0)),
25+ isUpper : isBetween('A'.charCodeAt(0),'Z'.charCodeAt(0)),
26+ isDigit : isDigit,
27+ isOctDigit : isBetween('0'.charCodeAt(0),'7'.charCodeAt(0)),
28+ isHexDigit : function(c) { return isDigit(c) || chk1(c) || chk2(c); }
29+ };
30+
31+};
libraries/Native/Color.jsnew file+71
@@ -0,0 +1,71 @@
1+
2+
3+Elm.Native.Color = function(elm) {
4+ "use strict";
5+
6+ elm.Native = elm.Native || {};
7+ if (elm.Native.Color) return elm.Native.Color;
8+
9+ var Utils = Elm.Native.Utils(elm);
10+
11+ function complement(rgb) {
12+ var hsv = toHSV(rgb);
13+ hsv.hue = (hsv.hue + 180) % 360;
14+ return toRGB(hsv);
15+ }
16+
17+ function hsva(h,s,v,a) {
18+ var degree = A2(Utils.mod, h * 180 / Math.PI, 360);
19+ var clr = toRGB({hue:degree, saturation:s, value:v});
20+ clr._3 = a;
21+ return clr;
22+ }
23+
24+ function hsv(h,s,v) {
25+ var degree = A2(Utils.mod, h * 180 / Math.PI, 360);
26+ return toRGB({hue:degree, saturation:s, value:v});
27+ }
28+
29+ function toHSV(rgb) {
30+ var hsv = {};
31+ var r = rgb._0 / 255.0, g = rgb._1 / 255.0, b = rgb._2 / 255.0;
32+ var M = Math.max(r,g,b);
33+ var m = Math.min(r,g,b);
34+ var c = M - m;
35+
36+ var h = 0;
37+ if (c === 0) { h = 0; }
38+ else if (M === r) { h = ((g - b) / c) % 6; }
39+ else if (M === g) { h = ((b - r) / c) + 2; }
40+ else if (M === b) { h = ((r - g) / c) + 4; }
41+ h *= 60;
42+
43+ return { value : M, hue : h, saturation : (M === 0 ? 0 : c / M) };
44+ }
45+
46+ function between(lo,hi,x) { return lo <= x && x < hi; }
47+ function norm(n) { return Math.round(n*255); }
48+
49+ function toRGB(hsv) {
50+ var c = hsv.value * hsv.saturation;
51+ var hue = hsv.hue / 60;
52+ var x = c * (1 - Math.abs((hue % 2) - 1));
53+ var r = 0, g = 0, b = 0;
54+ if (between(0,1,hue)) { r = c; g = x; b = 0; }
55+ else if (between(1,2,hue)) { r = x; g = c; b = 0; }
56+ else if (between(2,3,hue)) { r = 0; g = c; b = x; }
57+ else if (between(3,4,hue)) { r = 0; g = x; b = c; }
58+ else if (between(4,5,hue)) { r = x; g = 0; b = c; }
59+ else if (between(5,6,hue)) { r = c; g = 0; b = x; }
60+
61+ var m = hsv.value - c;
62+ return { ctor:"Color", _0:norm(r+m), _1:norm(g+m), _2:norm(b+m), _3:1 };
63+ }
64+
65+ return elm.Native.Color = {
66+ hsva:F4(hsva),
67+ hsv:F3(hsv),
68+ complement:complement
69+ };
70+
71+};
libraries/Native/Date.jsnew file+34
@@ -0,0 +1,34 @@
1+
2+Elm.Native.Date = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Date) return elm.Native.Date;
7+
8+ var JS = Elm.JavaScript(elm);
9+ var Maybe = Elm.Maybe(elm);
10+
11+ function dateNow() { return new window.Date; }
12+ function readDate(str) {
13+ var d = new window.Date(JS.fromString(str));
14+ if (isNaN(d.getTime())) return Maybe.Nothing;
15+ return Maybe.Just(d);
16+ }
17+
18+ var dayTable = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
19+ var monthTable = ["Jan", "Feb", "Mar", "Apr", "May", "Jun",
20+ "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"];
21+
22+ return elm.Native.Date = {
23+ read : readDate,
24+ year : function(d) { return d.getFullYear(); },
25+ month : function(d) { return { ctor:monthTable[d.getMonth()] }; },
26+ day : function(d) { return d.getDate(); },
27+ hour : function(d) { return d.getHours(); },
28+ minute : function(d) { return d.getMinutes(); },
29+ second : function(d) { return d.getSeconds(); },
30+ toTime : function(d) { return d.getTime(); },
31+ dayOfWeek : function(d) { return { ctor:dayTable[d.getDay()] }; }
32+ };
33+
34+};
libraries/Native/Error.jsnew file+22
@@ -0,0 +1,22 @@
1+
2+Elm.Native.Error = function(elm) {
3+ 'use strict';
4+ elm.Native = elm.Native || {};
5+ if (elm.Native.Error) return elm.Native.Error;
6+
7+ var fromString = Elm.Native.JavaScript(elm).fromString;
8+
9+ function Case(span) {
10+ var msg = 'Non-exhaustive pattern match in case expression'
11+ throw new Error(msg + " (" + span + ")")
12+ }
13+
14+ function If(span) {
15+ var msg = 'Non-exhaustive pattern match in multi-way-if expression'
16+ throw new Error(msg + " (" + span + ")")
17+ }
18+
19+ function raise(str) { throw new Error(fromString(str)); }
20+
21+ return elm.Native.Error = { Case: Case, If: If, raise: raise };
22+};
libraries/Native/Function.jsnew file+101
@@ -0,0 +1,101 @@
1+
2+function F2(fun) {
3+ function wrapper(a) { return function(b) { return fun(a,b) } }
4+ wrapper.arity = 2;
5+ wrapper.func = fun;
6+ return wrapper;
7+}
8+
9+function F3(fun) {
10+ function wrapper(a) {
11+ return function(b) { return function(c) { return fun(a,b,c) }}
12+ }
13+ wrapper.arity = 3;
14+ wrapper.func = fun;
15+ return wrapper;
16+}
17+
18+function F4(fun) {
19+ function wrapper(a) { return function(b) { return function(c) {
20+ return function(d) { return fun(a,b,c,d) }}}
21+ }
22+ wrapper.arity = 4;
23+ wrapper.func = fun;
24+ return wrapper;
25+}
26+
27+function F5(fun) {
28+ function wrapper(a) { return function(b) { return function(c) {
29+ return function(d) { return function(e) { return fun(a,b,c,d,e) }}}}
30+ }
31+ wrapper.arity = 5;
32+ wrapper.func = fun;
33+ return wrapper;
34+}
35+
36+function F6(fun) {
37+ function wrapper(a) { return function(b) { return function(c) {
38+ return function(d) { return function(e) { return function(f) {
39+ return fun(a,b,c,d,e,f) }}}}}
40+ }
41+ wrapper.arity = 6;
42+ wrapper.func = fun;
43+ return wrapper;
44+}
45+
46+function F7(fun) {
47+ function wrapper(a) { return function(b) { return function(c) {
48+ return function(d) { return function(e) { return function(f) {
49+ return function(g) { return fun(a,b,c,d,e,f,g) }}}}}}
50+ }
51+ wrapper.arity = 7;
52+ wrapper.func = fun;
53+ return wrapper;
54+}
55+
56+function F8(fun) {
57+ function wrapper(a) { return function(b) { return function(c) {
58+ return function(d) { return function(e) { return function(f) {
59+ return function(g) { return function(h) {return fun(a,b,c,d,e,f,g,h)}}}}}}}
60+ }
61+ wrapper.arity = 8;
62+ wrapper.func = fun;
63+ return wrapper;
64+}
65+
66+function F9(fun) {
67+ function wrapper(a) { return function(b) { return function(c) {
68+ return function(d) { return function(e) { return function(f) {
69+ return function(g) { return function(h) { return function(i) {
70+ return fun(a,b,c,d,e,f,g,h,i) }}}}}}}}
71+ }
72+ wrapper.arity = 9;
73+ wrapper.func = fun;
74+ return wrapper;
75+}
76+
77+function A2(fun,a,b) {
78+ return fun.arity === 2 ? fun.func(a,b) : fun(a)(b);
79+}
80+function A3(fun,a,b,c) {
81+ return fun.arity === 3 ? fun.func(a,b,c) : fun(a)(b)(c);
82+}
83+function A4(fun,a,b,c,d) {
84+ return fun.arity === 4 ? fun.func(a,b,c,d) : fun(a)(b)(c)(d);
85+}
86+function A5(fun,a,b,c,d,e) {
87+ return fun.arity === 5 ? fun.func(a,b,c,d,e) : fun(a)(b)(c)(d)(e);
88+}
89+function A6(fun,a,b,c,d,e,f) {
90+ return fun.arity === 6 ? fun.func(a,b,c,d,e,f) : fun(a)(b)(c)(d)(e)(f);
91+}
92+function A7(fun,a,b,c,d,e,f,g) {
93+ return fun.arity === 7 ? fun.func(a,b,c,d,e,f,g) : fun(a)(b)(c)(d)(e)(f)(g);
94+}
95+function A8(fun,a,b,c,d,e,f,g,h) {
96+ return fun.arity === 8 ? fun.func(a,b,c,d,e,f,g,h) : fun(a)(b)(c)(d)(e)(f)(g)(h);
97+}
98+function A9(fun,a,b,c,d,e,f,g,h,i) {
99+ return fun.arity === 9 ? fun.func(a,b,c,d,e,f,g,h,i)
100+ : fun(a)(b)(c)(d)(e)(f)(g)(h)(i);
101+}
libraries/Native/Graphics/Collage.jsnew file+23
@@ -0,0 +1,23 @@
1+
2+Elm.Native.Graphics.Collage = function(elm) {
3+ "use strict";
4+
5+ elm.Native = elm.Native || {};
6+ elm.Native.Graphics = elm.Native.Graphics || {};
7+ if (elm.Native.Graphics.Collage) return elm.Native.Graphics.Collage;
8+
9+ var newElement = Elm.Graphics.Element(elm).newElement;
10+ var C = ElmRuntime.use(ElmRuntime.Render.Collage);
11+
12+ function collage(w,h,forms) {
13+ return A3(newElement, w, h, {
14+ ctor: 'Custom',
15+ type: 'Collage',
16+ render: C.render,
17+ update: C.update,
18+ model: {w:w, h:h, forms:forms}
19+ });
20+ }
21+ return elm.Native.Graphics.Collage = { collage:F3(collage) };
22+
23+};
libraries/Native/Graphics/Input.jsnew file+234
@@ -0,0 +1,234 @@
1+
2+Elm.Native.Graphics.Input = function(elm) {
3+ "use strict";
4+
5+ elm.Native = elm.Native || {};
6+ elm.Native.Graphics = elm.Native.Graphics || {};
7+ if (elm.Native.Graphics.Input) return elm.Native.Graphics.Input;
8+
9+ var Render = ElmRuntime.use(ElmRuntime.Render.Element);
10+ var Utils = ElmRuntime.use(ElmRuntime.Render.Utils);
11+ var newNode = Utils.newElement, fromString = Utils.fromString,
12+ toString = Utils.toString;
13+
14+ var Signal = Elm.Signal(elm);
15+ var newElement = Elm.Graphics.Element(elm).newElement;
16+
17+ function buttons(defaultValue) {
18+ var events = Signal.constant(defaultValue);
19+
20+ function render(model) {
21+ var b = newNode('button');
22+ b.style.display = 'block';
23+ b.elmEvent = model.event;
24+ function click() { elm.notify(events.id, b.elmEvent); }
25+ b.addEventListener('click', click);
26+ b.innerHTML = model.text;
27+ return b;
28+ }
29+
30+ function update(node, oldModel, newModel) {
31+ node.elmEvent = newModel.event;
32+ var txt = newModel.text;
33+ if (oldModel.text !== txt) node.innerHTML = txt;
34+ }
35+
36+ function button(evnt, txt) {
37+ return A3(newElement, 100, 40, {
38+ ctor: 'Custom',
39+ type: 'Button',
40+ render: render,
41+ update: update,
42+ model: { event:evnt, text:fromString(txt) }
43+ });
44+ }
45+
46+ return { _:{}, button:F2(button), events:events };
47+ }
48+
49+ function customButtons(defaultValue) {
50+ var events = Signal.constant(defaultValue);
51+
52+ function render(model) {
53+ var btn = newNode('div');
54+ btn.elmEvent = model.event;
55+
56+ btn.elmUp = Render.render(model.up);
57+ btn.elmHover = Render.render(model.hover);
58+ btn.elmDown = Render.render(model.down);
59+
60+ function replace(node) {
61+ if (node !== btn.firstChild) btn.replaceChild(node, btn.firstChild);
62+ }
63+ var overCount = 0;
64+ function over(e) {
65+ if (overCount++ > 0) return;
66+ replace(btn.elmHover);
67+ }
68+ function out(e) {
69+ if (btn.contains(e.toElement || e.relatedTarget)) return;
70+ overCount = 0;
71+ replace(btn.elmUp);
72+ }
73+ function up() {
74+ replace(btn.elmHover);
75+ elm.notify(events.id, btn.elmEvent);
76+ }
77+ function down() { replace(btn.elmDown); }
78+ btn.addEventListener('mouseover', over);
79+ btn.addEventListener('mouseout' , out);
80+ btn.addEventListener('mousedown', down);
81+ btn.addEventListener('mouseup' , up);
82+
83+ btn.appendChild(btn.elmUp);
84+ return btn;
85+ }
86+
87+ function update(node, oldModel, newModel) {
88+ node.elmEvent = newModel.event;
89+ Render.update(node.elmUp, oldModel.up, newModel.up)
90+ Render.update(node.elmHover, oldModel.hover, newModel.hover)
91+ Render.update(node.elmDown, oldModel.down, newModel.down)
92+ }
93+
94+ function button(evnt, up, hover, down) {
95+ return A3(newElement,
96+ Math.max(up.props.width, hover.props.width, down.props.width),
97+ Math.max(up.props.height, hover.props.height, down.props.height),
98+ { ctor: 'Custom',
99+ type: 'CustomButton',
100+ render: render,
101+ update: update,
102+ model: { event:evnt, up:up, hover:hover, down:down }
103+ });
104+ }
105+
106+ return { _:{}, button:F4(button), events:events };
107+ }
108+
109+
110+ function checkboxes(defaultValue) {
111+ var events = Signal.constant(defaultValue);
112+
113+ function render(model) {
114+ var b = newNode('input');
115+ b.type = 'checkbox';
116+ b.checked = model.checked;
117+ b.style.display = 'block';
118+ b.elmHandler = model.handler;
119+ function change() { elm.notify(events.id, b.elmHandler(b.checked)); }
120+ b.addEventListener('change', change);
121+ return b;
122+ }
123+
124+ function update(node, oldModel, newModel) {
125+ node.elmHandler = newModel.handler;
126+ node.checked = newModel.checked;
127+ return true;
128+ }
129+
130+ function box(handler, checked) {
131+ return A3(newElement, 13, 13, {
132+ ctor: 'Custom',
133+ type: 'CheckBox',
134+ render: render,
135+ update: update,
136+ model: { checked:checked, handler:handler }
137+ });
138+ }
139+
140+ return { _:{}, box:F2(box), events:events };
141+ }
142+
143+ function mkTextPool(type) { return function fields(defaultValue) {
144+ var events = Signal.constant(defaultValue);
145+
146+ var state = null;
147+
148+ function render(model) {
149+ var field = newNode('input');
150+ field.elmHandler = model.handler;
151+
152+ field.id = 'test';
153+ field.type = type;
154+ field.placeholder = fromString(model.placeHolder);
155+ field.value = fromString(model.state.string);
156+ field.setSelectionRange(model.state.selectionStart, model.state.selectionEnd);
157+ field.style.border = 'none';
158+ state = model.state;
159+
160+ function update() {
161+ var start = field.selectionStart,
162+ end = field.selectionEnd;
163+ if (field.selectionDirection === 'backward') {
164+ start = end;
165+ end = field.selectionStart;
166+ }
167+ state = { _:{},
168+ string:toString(field.value),
169+ selectionStart:start,
170+ selectionEnd:end };
171+ elm.notify(events.id, field.elmHandler(state));
172+ }
173+ function mousedown() {
174+ update();
175+ elm.node.addEventListener('mouseup', mouseup);
176+ }
177+ function mouseup() {
178+ update();
179+ elm.node.removeEventListener('mouseup', mouseup)
180+ }
181+ field.addEventListener('keyup', update);
182+ field.addEventListener('mousedown', mousedown);
183+
184+ return field;
185+ }
186+
187+ function update(node, oldModel, newModel) {
188+ node.elmHandler = newModel.handler;
189+ if (state === newModel.state) return;
190+ var newStr = fromString(newModel.state.string);
191+ if (node.value !== newStr) node.value = newStr;
192+
193+ var start = newModel.state.selectionStart;
194+ var end = newModel.state.selectionEnd;
195+ var direction = 'forward';
196+ if (end < start) {
197+ start = end;
198+ end = newModel.state.selectionStart;
199+ direction = 'backward';
200+ }
201+
202+ if (node.selectionStart !== start
203+ || node.selectionEnd !== end
204+ || node.selectionDirection !== direction) {
205+ node.setSelectionRange(start, end, direction);
206+ }
207+ }
208+
209+ function field(handler, placeHolder, state) {
210+ return A3(newElement, 200, 30,
211+ { ctor: 'Custom',
212+ type: type + 'Input',
213+ render: render,
214+ update: update,
215+ model: { handler:handler,
216+ placeHolder:placeHolder,
217+ state:state }
218+ });
219+ }
220+
221+ return { _:{}, field:F3(field), events:events };
222+ }
223+ }
224+
225+ return elm.Native.Graphics.Input = {
226+ buttons:buttons,
227+ customButtons:customButtons,
228+ checkboxes:checkboxes,
229+ fields:mkTextPool('text'),
230+ emails:mkTextPool('email'),
231+ passwords:mkTextPool('password')
232+ };
233+
234+};
libraries/Native/JavaScript.jsnew file+102
@@ -0,0 +1,102 @@
1+
2+Elm.Native.JavaScript = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.JavaScript) return elm.Native.JavaScript;
7+
8+ var List = Elm.Native.List(elm);
9+ var Render = ElmRuntime.use(ElmRuntime.Render.Element);
10+
11+ function fromJS(v) {
12+ var type = typeof v;
13+ if (type === 'number' ) return v;
14+ if (type === 'boolean') return v;
15+ if (type === 'string' ) return List.fromArray(v);
16+ if (v instanceof Array) {
17+ var arr = [];
18+ var len = v.length;
19+ for (var i = 0; i < len; ++i) {
20+ var x = fromJS(v[i]);
21+ if (x !== null) arr.push(x);
22+ }
23+ return List.fromArray(arr);
24+ }
25+ if (type === 'object') {
26+ var rec = { _:{} };
27+ for (var f in v) {
28+ var x = fromJS(v[f]);
29+ if (x !== null) rec[f] = x;
30+ }
31+ return rec;
32+ }
33+ return null;
34+ }
35+
36+ function toJS(v) {
37+ var type = typeof v;
38+ if (type === 'number' || type === 'boolean') return v;
39+ if (type === 'object' && '_' in v) {
40+ var obj = {};
41+ for (var k in v) {
42+ var x = v[k];
43+ if (x !== null) obj[k] = x;
44+ }
45+ return obj;
46+ }
47+ if (type === 'object' && (v.ctor === 'Cons' || v.ctor === 'Nil')) {
48+ var array = List.toArray(v);
49+ for (var i = array.length; i--; ) {
50+ array[i] = toJS(array[i]);
51+ }
52+ if (typeof array[0] === 'string') array.join('');
53+ return array;
54+ }
55+ return null;
56+ }
57+
58+ function fromRecord(r) {
59+ if (typeof r === 'object' && '_' in r) {
60+ return toJS(r);
61+ }
62+ throw new Error("'fromRecord' must be called on a record.");
63+ }
64+
65+ function id(n) { return n; }
66+
67+ function toElement(w,h,domNode) {
68+ return A3( newElement, w, h, {
69+ ctor: 'Custom',
70+ type: 'DomNode',
71+ render: function(node) { return node; },
72+ update: function(node,oldNode,newNode) {
73+ if (node === newNode) return;
74+ node.parentNode.replaceChild(newNode, node);
75+ },
76+ model: domNode
77+ });
78+ }
79+
80+ function fromElement(element) {
81+ return Render.render(element);
82+ }
83+
84+ return elm.Native.JavaScript = {
85+ toFloat : id,
86+ toBool : id,
87+ toInt : function(n) { return n|0; },
88+ toString : List.fromArray,
89+ toList : List.fromArray,
90+ fromString : function(s) { return List.toArray(s).join(''); },
91+ fromList : List.toArray,
92+ fromInt : id,
93+ fromFloat : id,
94+ fromBool : id,
95+
96+ toElement : toElement,
97+ fromElement : fromElement,
98+ toRecord : fromJS,
99+ fromRecord : fromRecord
100+ };
101+
102+};
libraries/Native/Json.jsnew file+69
@@ -0,0 +1,69 @@
1+
2+Elm.Native.Json = function(elm) {
3+ 'use strict';
4+
5+ var Maybe = Elm.Maybe(elm);
6+ var Dict = Elm.Dict(elm);
7+ var List = Elm.List(elm);
8+ var JS = Elm.JavaScript(elm);
9+ var Utils = Elm.Native.Utils(elm);
10+
11+ function fromValue(v) {
12+ switch (v.ctor) {
13+ case 'Null' : return null;
14+ case 'String' : return JS.fromString(v._0);
15+ case 'Object' :
16+ var obj = {};
17+ var array = JS.fromList(Dict.toList(v._0));
18+ for (var i = arr.length; i--; ) {
19+ obj[JS.fromString(array[i]._0)] = fromValue(array[i]._1);
20+ }
21+ return obj;
22+ case 'Array' :
23+ var array = JS.fromList(v._0);
24+ for (var i = array.length; i--; ) {
25+ array[i] = fromValue(array[i]);
26+ }
27+ return array;
28+ default :
29+ return v._0;
30+ }
31+ }
32+
33+ function toPrettyJSString(sep, obj) {
34+ return JSON.stringify(fromValue(obj), null, JS.fromString(sep));
35+ }
36+
37+ function toValue(v) {
38+ switch (typeof v) {
39+ case 'string' : return { ctor:"String", _0: JS.toString(v) };
40+ case 'number' : return { ctor:"Number", _0: JS.toFloat(v) };
41+ case 'boolean': return { ctor:"Bool" , _0: JS.toBool(v) };
42+ case 'object' :
43+ if (v === null) return { ctor:"Null" };
44+ if (v instanceof Array) {
45+ for (var i = v.length; i--; ) { v[i] = toValue(v[i]); }
46+ return { ctor:"Array", _0: JS.toList(v) };
47+ }
48+ var array = [];
49+ for (var k in v) array.push(Utils.Tuple2(JS.toString(k), toValue(v[k])));
50+ return { ctor:"Object", _0: Dict.fromList(JS.toList(array)) };
51+ }
52+ }
53+
54+ function fromJSString(str) {
55+ try {
56+ return Maybe.Just(toValue(JSON.parse(str)));
57+ } catch (e) {
58+ return Maybe.Nothing;
59+ }
60+ }
61+
62+ return elm.Native.Json = {
63+ toJSString : F2(toPrettyJSString),
64+ fromJSString : fromJSString,
65+ toJSObject : fromValue,
66+ fromJSObject : toValue
67+ };
68+
69+};
libraries/Native/List.jsnew file+347
@@ -0,0 +1,347 @@
1+Elm.Native.List = function(elm) {
2+ "use strict";
3+
4+ elm.Native = elm.Native || {};
5+ if (elm.Native.List) return elm.Native.List;
6+ if ('values' in Elm.Native.List)
7+ return elm.Native.List = Elm.Native.List.values;
8+
9+ var Utils = Elm.Native.Utils(elm);
10+
11+ // TODO: Improve Nil handling
12+ // We can change places like: if (xs.ctor === 'Nil') ... to if (xs === Nil) ...
13+ // but only if we're confident Nil can only be defined once.
14+ // Currently (27Mar2013) each module can have different instantiations, so multiple Nil objects can exist
15+ // (and if they're used interchangeably then direct object comparison fails where ctor doesn't).
16+ // So, this can only be fixed when modules initialisation is also fixed.
17+ // The performance overhead of the .ctor calls is 5-10% according to jsperf (depending on fn + list size)
18+ // (on firefox 19)
19+
20+ var Nil = { ctor:'Nil' };
21+
22+ // using freeze for every cons would be nice but is a huge (9x on firefox 19)
23+ // performance penalty
24+ function Cons(hd,tl) { return { ctor:"Cons", _0:hd, _1:tl }; }
25+
26+ function throwError(f) {
27+ throw new Error("Function '" + f + "' expects a non-empty list!");
28+ }
29+
30+ function toArray(xs) {
31+ var out = [];
32+ while (xs.ctor !== 'Nil') {
33+ out.push(xs._0);
34+ xs = xs._1;
35+ }
36+ return out;
37+ }
38+
39+ function fromArray(arr) {
40+ var out = Nil;
41+ for (var i = arr.length; i--; ) {
42+ out = Cons(arr[i], out);
43+ }
44+ return out;
45+ }
46+
47+ function range(lo,hi) {
48+ var lst = Nil;
49+ if (lo <= hi) {
50+ do { lst = Cons(hi,lst) } while (hi-->lo);
51+ }
52+ return lst
53+ }
54+
55+ function append(xs,ys) {
56+ if (typeof xs === "string") { return xs.concat(ys); }
57+ if (xs.ctor === 'Nil') { return ys; }
58+ var root = Cons(xs._0, Nil);
59+ var curr = root;
60+ xs = xs._1;
61+ while (xs.ctor !== 'Nil') {
62+ curr._1 = Cons(xs._0, Nil);
63+ xs = xs._1;
64+ curr = curr._1;
65+ }
66+ curr._1 = ys;
67+ return root;
68+ }
69+
70+ function head(v) { return v.ctor === 'Nil' ? throwError('head') : v._0; }
71+ function tail(v) { return v.ctor === 'Nil' ? throwError('tail') : v._1; }
72+
73+ function last(xs) {
74+ if (xs.ctor === 'Nil') { throwError('last'); }
75+ var out = xs._0;
76+ while (xs.ctor !== 'Nil') {
77+ out = xs._0;
78+ xs = xs._1;
79+ }
80+ return out;
81+ }
82+
83+ function map(f, xs) {
84+ var arr = [];
85+ while (xs.ctor !== 'Nil') {
86+ arr.push(f(xs._0));
87+ xs = xs._1;
88+ }
89+ return fromArray(arr);
90+ }
91+
92+ // f defined similarly for both foldl and foldr (NB: different from Haskell)
93+ // ie, foldl :: (a -> b -> b) -> b -> [a] -> b
94+ function foldl(f, b, xs) {
95+ var acc = b;
96+ while (xs.ctor !== 'Nil') {
97+ acc = A2(f, xs._0, acc);
98+ xs = xs._1;
99+ }
100+ return acc;
101+ }
102+
103+ function foldr(f, b, xs) {
104+ var arr = toArray(xs);
105+ var acc = b;
106+ for (var i = arr.length; i--; ) {
107+ acc = A2(f, arr[i], acc);
108+ }
109+ return acc;
110+ }
111+
112+ function foldl1(f, xs) {
113+ return xs.ctor === 'Nil' ? throwError('foldl1') : foldl(f, xs._0, xs._1);
114+ }
115+
116+ function foldr1(f, xs) {
117+ if (xs.ctor === 'Nil') { throwError('foldr1'); }
118+ var arr = toArray(xs);
119+ var acc = arr.pop();
120+ for (var i = arr.length; i--; ) {
121+ acc = A2(f, arr[i], acc);
122+ }
123+ return acc;
124+ }
125+
126+ function scanl(f, b, xs) {
127+ var arr = toArray(xs);
128+ arr.unshift(b);
129+ var len = arr.length;
130+ for (var i = 1; i < len; ++i) {
131+ arr[i] = A2(f, arr[i], arr[i-1]);
132+ }
133+ return fromArray(arr);
134+ }
135+
136+ function scanl1(f, xs) {
137+ return xs.ctor === 'Nil' ? throwError('scanl1') : scanl(f, xs._0, xs._1);
138+ }
139+
140+ function filter(pred, xs) {
141+ var arr = [];
142+ while (xs.ctor !== 'Nil') {
143+ if (pred(xs._0)) { arr.push(xs._0); }
144+ xs = xs._1;
145+ }
146+ return fromArray(arr);
147+ }
148+
149+ function length(xs) {
150+ var out = 0;
151+ while (xs.ctor !== 'Nil') {
152+ out += 1;
153+ xs = xs._1;
154+ }
155+ return out;
156+ }
157+
158+ function member(x, xs) {
159+ while (xs.ctor !== 'Nil') {
160+ if (Utils.eq(x,xs._0)) return true;
161+ xs = xs._1;
162+ }
163+ return false;
164+ }
165+
166+ function reverse(xs) { return fromArray(toArray(xs).reverse()); }
167+
168+ function concat(xss) {
169+ if (xss.ctor === 'Nil') return xss;
170+ var arr = toArray(xss);
171+ var xs = arr[arr.length-1];
172+ for (var i = arr.length-1; i--; ) {
173+ xs = append(arr[i], xs);
174+ }
175+ return xs;
176+ }
177+
178+ function all(pred, xs) {
179+ while (xs.ctor !== 'Nil') {
180+ if (!pred(xs._0)) return false;
181+ xs = xs._1;
182+ }
183+ return true;
184+ }
185+
186+ function any(pred, xs) {
187+ while (xs.ctor !== 'Nil') {
188+ if (pred(xs._0)) return true;
189+ xs = xs._1;
190+ }
191+ return false;
192+ }
193+
194+ function zipWith(f, xs, ys) {
195+ var arr = [];
196+ while (xs.ctor !== 'Nil' && ys.ctor !== 'Nil') {
197+ arr.push(A2(f, xs._0, ys._0));
198+ xs = xs._1;
199+ ys = ys._1;
200+ }
201+ return fromArray(arr);
202+ }
203+
204+ function zip(xs, ys) {
205+ var arr = [];
206+ while (xs.ctor !== 'Nil' && ys.ctor !== 'Nil') {
207+ arr.push(Utils.Tuple2(xs._0, ys._0));
208+ xs = xs._1;
209+ ys = ys._1;
210+ }
211+ return fromArray(arr);
212+ }
213+
214+ function sort(xs) {
215+ function cmp(a,b) {
216+ var ord = Utils.compare(a,b).ctor;
217+ return ord=== 'EQ' ? 0 : ord === 'LT' ? -1 : 1;
218+ }
219+ return fromArray(toArray(xs).sort(cmp));
220+ }
221+
222+ function take(n, xs) {
223+ var arr = [];
224+ while (xs.ctor !== 'Nil' && n > 0) {
225+ arr.push(xs._0);
226+ xs = xs._1;
227+ --n;
228+ }
229+ return fromArray(arr);
230+ }
231+
232+ function drop(n, xs) {
233+ while (xs.ctor !== 'Nil' && n > 0) {
234+ xs = xs._1;
235+ --n;
236+ }
237+ return xs;
238+ }
239+
240+ function join(sep, xss) {
241+ if (typeof sep === 'string') return toArray(xss).join(sep);
242+ if (xss.ctor === 'Nil') return Nil;
243+ var s = toArray(sep);
244+ var out = toArray(xss._0);
245+ xss = xss._1;
246+ while (xss.ctor !== 'Nil') {
247+ out = out.concat(s, toArray(xss._0));
248+ xss = xss._1;
249+ }
250+ return fromArray(out);
251+ }
252+
253+ function split(seperator, list) {
254+ var array = toArray(list);
255+ var alen = array.length;
256+ if (alen === 0) {
257+ // splitting an empty list is a list of lists: [[]]
258+ return Cons(Nil,Nil);
259+ }
260+
261+ var sep = toArray(seperator);
262+ var seplen = sep.length;
263+ if (seplen === 0) {
264+ // splitting with an empty sep is a list of all elements
265+ // Same as (map (\x -> [x]) list)
266+ var out = Nil;
267+ for (var i = alen; i--; ) {
268+ out = Cons(Cons(array[i],Nil), out);
269+ }
270+ return out;
271+ }
272+
273+ var matches = [-seplen];
274+ var sepStart = sep[0];
275+ var len = alen - seplen + 1;
276+ for (var i = 0; i < len; ++i) {
277+ if (Utils.eq(array[i], sepStart)) {
278+ var match = true;
279+ for (var j = seplen; --j; ) {
280+ if (!Utils.eq(array[i+j], sep[j])) { match = false; break; }
281+ }
282+ if (match) {
283+ matches.push(i);
284+ i += seplen - 1;
285+ }
286+ }
287+ }
288+
289+ // shortcut in case of no matches
290+ if (matches.length === 0) {
291+ return Cons(list,Nil);
292+ }
293+
294+ var out = Nil;
295+ var index = alen - 1;
296+ for (var i = matches.length; i--; ) {
297+ var temp = Nil;
298+ var stop = matches[i] + seplen - 1;
299+ for ( ; index > stop; --index ) {
300+ temp = Cons(array[index], temp);
301+ }
302+ out = Cons(temp,out);
303+ index -= seplen;
304+ }
305+ return out;
306+ }
307+
308+ Elm.Native.List.values = {
309+ Nil:Nil,
310+ Cons:Cons,
311+ toArray:toArray,
312+ fromArray:fromArray,
313+ range:range,
314+ append:append,
315+
316+ head:head,
317+ tail:tail,
318+ last:last,
319+
320+ map:F2(map),
321+ foldl:F3(foldl),
322+ foldr:F3(foldr),
323+
324+ foldl1:F2(foldl1),
325+ foldr1:F2(foldr1),
326+ scanl:F3(scanl),
327+ scanl1:F2(scanl1),
328+ filter:F2(filter),
329+ length:length,
330+ member:F2(member),
331+ reverse:reverse,
332+ concat:concat,
333+
334+ all:F2(all),
335+ any:F2(any),
336+ zipWith:F3(zipWith),
337+ zip:F2(zip),
338+ sort:sort,
339+ take:F2(take),
340+ drop:F2(drop),
341+
342+ join:F2(join),
343+ split:F2(split)
344+ };
345+ return elm.Native.List = Elm.Native.List.values;
346+
347+};
libraries/Native/Matrix2D.jsnew file+88
@@ -0,0 +1,88 @@
1+
2+Elm.Native.Matrix2D = function(elm) {
3+ "use strict";
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Matrix2D) return elm.Native.Matrix2D;
7+
8+ if (typeof Float32Array === 'undefined'){ Float32Array = Array; }
9+ var A = Float32Array;
10+
11+ // layout of matrix in an array is
12+ //
13+ // | m11 m12 dx |
14+ // | m21 m22 dy |
15+ // | 0 0 1 |
16+ //
17+ // new A([ m11, m12, dx, m21, m22, dy ])
18+
19+ var identity = new A([1,0,0,0,1,0]);
20+ function matrix(m11, m12, m21, m22, dx, dy) {
21+ return new A([m11, m12, dx, m21, m22, dy]);
22+ }
23+ function rotation(t) {
24+ var c = Math.cos(t);
25+ var s = Math.sin(t);
26+ return new A([c, -s, 0, s, c, 0]);
27+ }
28+
29+ function rotate(t,m) {
30+ var c = Math.cos(t);
31+ var s = Math.sin(t);
32+ var m11 = m[0], m12 = m[1], m21 = m[3], m22 = m[4];
33+ return new A([m11*c + m12*s, -m11*s + m12*c, m[2],
34+ m21*c + m22*s, -m21*s + m22*c, m[5]]);
35+ }
36+ /*
37+ function move(xy,m) {
38+ var x = xy._0;
39+ var y = xy._1;
40+ var m11 = m[0], m12 = m[1], m21 = m[3], m22 = m[4];
41+ return new A([m11, m12, m11*x + m12*y + m[2],
42+ m21, m22, m21*x + m22*y + m[5]]);
43+ }
44+ function scale(s,m) { return new A([m[0]*s, m[1]*s, m[2], m[3]*s, m[4]*s, m[5]]); }
45+ function scaleX(x,m) { return new A([m[0]*x, m[1], m[2], m[3]*x, m[4], m[5]]); }
46+ function scaleY(y,m) { return new A([m[0], m[1]*y, m[2], m[3], m[4]*y, m[5]]); }
47+ function reflectX(m) { return new A([-m[0], m[1], m[2], -m[3], m[4], m[5]]); }
48+ function reflectY(m) { return new A([m[0], -m[1], m[2], m[3], -m[4], m[5]]); }
49+
50+ function transform(m11, m21, m12, m22, mdx, mdy, n) {
51+ var n11 = n[0], n12 = n[1], n21 = n[3], n22 = n[4], ndx = n[2], ndy = n[5];
52+ return new A([m11*n11 + m12*n21,
53+ m11*n12 + m12*n22,
54+ m11*ndx + m12*ndy + mdx,
55+ m21*n11 + m22*n21,
56+ m21*n12 + m22*n22,
57+ m21*ndx + m22*ndy + mdy]);
58+ }
59+ */
60+ function multiply(m, n) {
61+ var m11 = m[0], m12 = m[1], m21 = m[3], m22 = m[4], mdx = m[2], mdy = m[5];
62+ var n11 = n[0], n12 = n[1], n21 = n[3], n22 = n[4], ndx = n[2], ndy = n[5];
63+ return new A([m11*n11 + m12*n21,
64+ m11*n12 + m12*n22,
65+ m11*ndx + m12*ndy + mdx,
66+ m21*n11 + m22*n21,
67+ m21*n12 + m22*n22,
68+ m21*ndx + m22*ndy + mdy]);
69+ }
70+
71+ return elm.Native.Matrix2D = {
72+ identity:identity,
73+ matrix:F6(matrix),
74+ rotation:rotation,
75+ multiply:F2(multiply)
76+ /*
77+ transform:F7(transform),
78+ rotate:F2(rotate),
79+ move:F2(move),
80+ scale:F2(scale),
81+ scaleX:F2(scaleX),
82+ scaleY:F2(scaleY),
83+ reflectX:reflectX,
84+ reflectY:reflectY
85+ */
86+ };
87+
88+};
libraries/Native/Prelude.jsnew file+123
@@ -0,0 +1,123 @@
1+
2+Elm.Native.Prelude = function(elm) {
3+ 'use strict';
4+ if (elm.Native.Prelude) return elm.Native.Prelude;
5+
6+ var JS = Elm.JavaScript(elm);
7+ var Maybe = Elm.Maybe(elm);
8+ var Utils = Elm.Native.Utils(elm);
9+ var Char = Elm.Char(elm);
10+
11+ function div(a,b) { return (a/b)|0; }
12+ function rem(a,b) { return a % b; }
13+ var mod = Utils.mod;
14+ function abs(x) { return x < 0 ? -x : x; }
15+ function logBase(base,n) { return Math.log(n) / Math.log(base); }
16+ function min(a,b) { return a < b ? a : b; }
17+ function max(a,b) { return a > b ? a : b; }
18+ function clamp(lo,hi,n) { return n < lo ? lo : n > hi ? hi : n; }
19+ function xor(a,b) { return a !== b; }
20+ function not(b) { return !b; }
21+
22+ function truncate(n) { return n|0; }
23+
24+ function id(n) { return n; }
25+ function flip(f,a,b) { return A2(f,b,a); }
26+ function curry(f,a,b) { return f(Utils.Tuple2(a,b)); }
27+ function uncurry(f,v) { return A2(f,v._0,v._1); }
28+ function fst(t) { return t._0; }
29+ function snd(t) { return t._1; }
30+
31+ function readInt(str) {
32+ var s = JS.fromString(str);
33+ var len = s.length;
34+ if (len === 0) { return Maybe.Nothing; }
35+ var start = 0;
36+ if (s[0] == '-') {
37+ if (len === 1) { return Maybe.Nothing; }
38+ start = 1;
39+ }
40+ for (var i = start; i < len; ++i) {
41+ if (!Char.isDigit(s[i])) { return Maybe.Nothing; }
42+ }
43+ return Maybe.Just(parseInt(s, 10));
44+ }
45+
46+ function readFloat(str) {
47+ var s = JS.fromString(str);
48+ var len = s.length;
49+ if (len === 0) { return Maybe.Nothing; }
50+ var start = 0;
51+ if (s[0] == '-') {
52+ if (len === 1) { return Maybe.Nothing; }
53+ start = 1;
54+ }
55+ var dotCount = 0;
56+ for (var i = start; i < len; ++i) {
57+ if (Char.isDigit(s[i])) { continue; }
58+ if (s[i] === '.') {
59+ dotCount += 1;
60+ if (dotCount <= 1) { continue; }
61+ }
62+ return Maybe.Nothing;
63+ }
64+ return Maybe.Just(parseFloat(s));
65+ }
66+
67+ var prelude = {
68+ div:F2(div),
69+ rem:F2(rem),
70+ mod:mod,
71+
72+ pi:Math.PI,
73+ e:Math.e,
74+ cos:Math.cos,
75+ sin:Math.sin,
76+ tan:Math.tan,
77+ acos:Math.acos,
78+ asin:Math.asin,
79+ atan:Math.atan,
80+ atan2:F2(Math.atan2),
81+
82+ sqrt:Math.sqrt,
83+ abs:abs,
84+ logBase:F2(logBase),
85+ min:F2(min),
86+ max:F2(max),
87+ clamp:F3(clamp),
88+ compare:Utils.compare,
89+
90+ xor:F2(xor),
91+ not:not,
92+ otherwise:true,
93+
94+ truncate:truncate,
95+ ceiling:Math.ceil,
96+ floor:Math.floor,
97+ round:Math.round,
98+ toFloat:id,
99+
100+ readInt:readInt,
101+ readFloat:readFloat,
102+
103+ id:id,
104+ flip:F3(flip),
105+ curry:F3(curry),
106+ uncurry:F2(uncurry),
107+ fst:fst,
108+ snd:snd
109+ };
110+
111+ function add(Module) {
112+ var M = Module(elm);
113+ for (var k in M) { prelude[k] = M[k]; }
114+ }
115+ add(Elm.Native.Show);
116+ add(Elm.Signal);
117+ add(Elm.List);
118+ add(Elm.Maybe);
119+ add(Elm.Time);
120+ add(Elm.Graphics.Element);
121+
122+ return elm.Native.Prelude = prelude;
123+};
libraries/Native/Show.jsnew file+99
@@ -0,0 +1,99 @@
1+
2+Elm.Native.Show = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Show) return elm.Native.Show;
7+
8+ var NList = Elm.Native.List(elm);
9+ var List = Elm.List(elm);
10+ var Maybe = Elm.Maybe(elm);
11+ var JS = Elm.JavaScript(elm);
12+ var Dict = Elm.Dict(elm);
13+ var Json = Elm.Json(elm);
14+ var Tuple2 = Elm.Native.Utils(elm).Tuple2;
15+
16+ var toString = function(v) {
17+ if (typeof v === "function") {
18+ var name = v.func ? v.func.name : v.name;
19+ return '<function' + (name === '' ? '' : ': ') + name + '>';
20+ } else if (typeof v === "boolean") {
21+ return v ? "True" : "False";
22+ } else if (typeof v === "number") {
23+ return v+"";
24+ } else if (typeof v === "string" && v.length < 2) {
25+ return "'" + showChar(v) + "'";
26+ } else if (typeof v === "object" && '_' in v) {
27+ var output = [];
28+ for (var k in v._) {
29+ for (var i = v._[k].length; i--; ) {
30+ output.push(k + " = " + toString(v._[k][i]));
31+ }
32+ }
33+ for (var k in v) {
34+ if (k === '_') continue;
35+ output.push(k + " = " + toString(v[k]));
36+ }
37+ if (output.length === 0) return "{}";
38+ return "{ " + output.join(", ") + " }";
39+ } else if (typeof v === "object" && 'ctor' in v) {
40+ if (v.ctor.substring(0,5) === "Tuple") {
41+ var output = [];
42+ for (var k in v) {
43+ if (k === 'ctor') continue;
44+ output.push(toString(v[k]));
45+ }
46+ return "(" + output.join(",") + ")";
47+ } else if (v.ctor === "Cons") {
48+ var isStr = typeof v._0 === "string",
49+ start = isStr ? '"' : "[",
50+ end = isStr ? '"' : "]",
51+ sep = isStr ? "" : ",",
52+ f = !isStr ? toString : showChar;
53+ var output = start + f(v._0);
54+ v = v._1;
55+ while (v.ctor === "Cons") {
56+ output += sep + f(v._0);
57+ v = v._1;
58+ }
59+ return output + end;
60+ } else if (v.ctor === "Nil") {
61+ return "[]";
62+ } else if (v.ctor === "RBNode" || v.ctor === "RBEmpty") {
63+ var cons = F3(function(k,v,acc){return NList.Cons(Tuple2(k,v),acc)});
64+ var list = A3(Dict.foldr, cons, NList.Nil, v);
65+ var name = "Dict";
66+ if (list.ctor === "Cons" && list._0._1.ctor === "Tuple0") {
67+ name = "Set";
68+ list = A2(List.map, function(x){return x._0}, list);
69+ }
70+ return name + ".fromList " + toString(list);
71+ } else {
72+ var output = "";
73+ for (var i in v) {
74+ if (i === 'ctor') continue;
75+ var str = toString(v[i]);
76+ var parenless = str[0] === '{' || str.indexOf(' ') < 0;
77+ output += ' ' + (parenless ? str : '(' + str + ')');
78+ }
79+ return v.ctor + output;
80+ }
81+ }
82+ return v+"";
83+ };
84+ function show(v) { return NList.fromArray(toString(v)); }
85+
86+ function showChar (c) {
87+ return c === '\n' ? '\\n' :
88+ c === '\t' ? '\\t' :
89+ c === '\b' ? '\\b' :
90+ c === '\r' ? '\\r' :
91+ c === '\v' ? '\\v' :
92+ c === '\0' ? '\\0' :
93+ c === '\'' ? "\\'" :
94+ c === '\"' ? '\\"' :
95+ c === '\\' ? '\\\\' : c;
96+ }
97+
98+ return elm.Native.Show = { show:show };
99+};
libraries/Native/Signal/Http.jsnew file+61
@@ -0,0 +1,61 @@
1+
2+Elm.Native.Http = function(elm) {
3+ 'use strict';
4+ elm.Native = elm.Native || {};
5+ if (elm.Native.Http) return elm.Native.Http;
6+
7+
8+ var JS = Elm.JavaScript(elm);
9+ var List = Elm.List(elm);
10+ var Signal = Elm.Signal(elm);
11+
12+
13+ function registerReq(queue,responses) { return function(req) {
14+ if (req.url !== "") { sendReq(queue,responses,req); }
15+ };
16+ }
17+
18+ function updateQueue(queue,responses) {
19+ if (queue.length > 0) {
20+ elm.notify(responses.id, queue[0].value);
21+ if (queue[0].value.ctor !== 'Waiting') {
22+ queue.shift();
23+ setTimeout(function() { updateQueue(queue,responses); }, 0);
24+ }
25+ }
26+ }
27+
28+ function setHeader(pair) {
29+ request.setRequestHeader( JS.fomString(pair._0), JS.fromString(pair._1) );
30+ }
31+
32+ function sendReq(queue,responses,req) {
33+ var response = { value: { ctor:'Waiting' } };
34+ queue.push(response);
35+
36+ var request = null;
37+ if (window.ActiveXObject) { request = new ActiveXObject("Microsoft.XMLHTTP"); }
38+ if (window.XMLHttpRequest) { request = new XMLHttpRequest(); }
39+ request.onreadystatechange = function(e) {
40+ if (request.readyState === 4) {
41+ response.value = (request.status === 200 ?
42+ { ctor:'Success', _0:JS.toString(request.responseText) } :
43+ { ctor:'Failure', _0:request.status, _1:JS.toString(request.statusText) });
44+ setTimeout(function() { updateQueue(queue,responses); }, 0);
45+ }
46+ };
47+ request.open(JS.fromString(req.verb), JS.fromString(req.url), true);
48+ List.map(setHeader)(req.headers);
49+ request.send(JS.fromString(req.body));
50+ }
51+
52+ function send(requests) {
53+ var responses = Signal.constant(elm.Http.Waiting);
54+ var sender = A2( Signal.lift, registerReq([],responses), requests );
55+ function f(x) { return function(y) { return x; } }
56+ return A3( Signal.lift2, f, responses, sender );
57+ }
58+
59+ return elm.Native.Http = {send:send};
60+
61+};
libraries/Native/Signal/Keyboard.jsnew file+72
@@ -0,0 +1,72 @@
1+
2+Elm.Native.Keyboard = function(elm) {
3+ 'use strict';
4+ elm.Native = elm.Native || {};
5+ if (elm.Native.Keyboard) return elm.Native.Keyboard;
6+
7+ var Signal = Elm.Signal(elm);
8+ var NList = Elm.Native.List(elm);
9+
10+ var keysDown = Signal.constant(NList.Nil);
11+ var lastKey = Signal.constant('\0');
12+
13+ function down(e) {
14+ if (NList.member(e.keyCode)(keysDown.value)) return;
15+ var list = NList.Cons(e.keyCode, keysDown.value);
16+ var hasListener = elm.notify(keysDown.id, list);
17+ if (!hasListener) document.removeEventListener('keydown', down);
18+ }
19+ function up(e) {
20+ function notEq(kc) { return kc !== e.keyCode; }
21+ var codes = NList.filter(notEq)(keysDown.value);
22+ var hasListener = elm.notify(keysDown.id, codes);
23+ if (!hasListener) document.removeEventListener('keyup', up);
24+ }
25+ function blur(e) {
26+ var hasListener = elm.notify(keysDown.id, NList.Nil);
27+ if (!hasListener) document.removeEventListener('blur', blur);
28+ }
29+ function press(e) {
30+ var hasListener = elm.notify(lastKey.id, e.charCode || e.keyCode);
31+ if (!hasListener) document.removeEventListener('keypress', press);
32+ }
33+
34+ document.addEventListener('keydown' , down );
35+ document.addEventListener('keyup' , up );
36+ document.addEventListener('blur' , blur );
37+ document.addEventListener('keypress', press);
38+
39+ function keySignal(f) {
40+ var signal = A2( Signal.lift, f, keysDown );
41+ keysDown.defaultNumberOfKids += 1;
42+ signal.defaultNumberOfKids = 0;
43+ return signal;
44+ }
45+
46+ function dir(up, down, left, right) {
47+ function f(ks) {
48+ var x = 0, y = 0;
49+ while (ks.ctor == "Cons") {
50+ switch (ks._0) {
51+ case left : --x; break;
52+ case right: ++x; break;
53+ case up : ++y; break;
54+ case down : --y; break;
55+ }
56+ ks = ks._1;
57+ }
58+ return { _:{}, x:x, y:y };
59+ }
60+ return keySignal(f);
61+ }
62+
63+ function is(key) { return keySignal(NList.member(key)); }
64+
65+ return elm.Native.Keyboard = {
66+ isDown:is,
67+ directions:F4(dir),
68+ keysDown:keysDown,
69+ lastPressed:lastKey
70+ };
71+
72+};
libraries/Native/Signal/Mouse.jsnew file+79
@@ -0,0 +1,79 @@
1+
2+Elm.Native.Mouse = function(elm) {
3+ 'use strict';
4+ elm.Native = elm.Native || {};
5+ if (elm.Native.Mouse) return elm.Native.Mouse;
6+
7+ var Signal = Elm.Signal(elm);
8+ var Utils = Elm.Native.Utils(elm);
9+
10+ var position = Signal.constant(Utils.Tuple2(0,0));
11+ position.defaultNumberOfKids = 2;
12+
13+ // do not move x and y into Elm. By setting their default number
14+ // of kids, it is possible to detatch the mouse listeners if
15+ // they are not needed.
16+ var x = A2( Signal.lift, function(p){return p._0}, position);
17+ x.defaultNumberOfKids = 0;
18+ var y = A2( Signal.lift, function(p){return p._1}, position);
19+ y.defaultNumberOfKids = 0;
20+
21+ var isDown = Signal.constant(false);
22+ var isClicked = Signal.constant(false);
23+ var clicks = Signal.constant(Utils.Tuple0);
24+
25+ function getXY(e) {
26+ var posx = 0;
27+ var posy = 0;
28+ if (!e) e = window.event;
29+ if (e.pageX || e.pageY) {
30+ posx = e.pageX;
31+ posy = e.pageY;
32+ } else if (e.clientX || e.clientY) {
33+ posx = e.clientX + document.body.scrollLeft +
34+ document.documentElement.scrollLeft;
35+ posy = e.clientY + document.body.scrollTop +
36+ document.documentElement.scrollTop;
37+ }
38+ return Utils.Tuple2(posx-elm.node.offsetX, posy-elm.node.offsetY);
39+ }
40+
41+ var node = elm.display === ElmRuntime.Display.FULLSCREEN ? document : elm.node;
42+
43+ function click(e) {
44+ var hasListener1 = elm.notify(isClicked.id, true);
45+ var hasListener2 = elm.notify(clicks.id, Utils.Tuple0);
46+ elm.notify(isClicked.id, false);
47+ if (!hasListener1 && !hasListener2)
48+ node.removeEventListener('click', click);
49+ }
50+
51+ function down(e) {
52+ var hasListener = elm.notify(isDown.id, true);
53+ if (!hasListener) node.removeEventListener('mousedown', down);
54+ }
55+
56+ function up(e) {
57+ var hasListener = elm.notify(isDown.id, false);
58+ if (!hasListener) node.removeEventListener('mouseup', up);
59+ }
60+
61+ function move(e) {
62+ var hasListener = elm.notify(position.id, getXY(e));
63+ if (!hasListener) node.removeEventListener('mousemove', move);
64+ }
65+
66+ node.addEventListener('click' , click);
67+ node.addEventListener('mousedown', down);
68+ node.addEventListener('mouseup' , up);
69+ node.addEventListener('mousemove', move);
70+
71+ return elm.Native.Mouse = {
72+ position: position,
73+ x:x,
74+ y:y,
75+ isClicked: isClicked,
76+ isDown: isDown,
77+ clicks: clicks
78+ };
79+};
libraries/Native/Signal/Random.jsnew file+21
@@ -0,0 +1,21 @@
1+
2+Elm.Native.Random = function(elm) {
3+ 'use strict';
4+ elm.Native = elm.Native || {};
5+ if (elm.Native.Random) return elm.Native.Random;
6+
7+ var Signal = Elm.Signal(elm);
8+
9+ function range(min, max, signal) {
10+ function f(x) { return Math.floor(Math.random() * (max-min+1)) + min; }
11+ return A2( Signal.lift, f, signal );
12+ }
13+
14+ function flt(signal) {
15+ function f(x) { return Math.random(); }
16+ return A2( Signal.lift, f, signal );
17+ }
18+
19+ return elm.Native.Random = { range: F3(range), float: flt };
20+
21+};
libraries/Native/Signal/Signal.jsnew file+225
@@ -0,0 +1,225 @@
1+
2+Elm.Native.Signal = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Signal) return elm.Native.Signal;
7+
8+ var Utils = Elm.Native.Utils(elm);
9+ var foldl1 = Elm.List(elm).foldl1;
10+
11+ function send(node, timestep, changed) {
12+ var kids = node.kids;
13+ for (var i = kids.length; i--; ) {
14+ kids[i].recv(timestep, changed, node.id);
15+ }
16+ }
17+
18+ function Input(base) {
19+ this.id = Utils.guid();
20+ this.value = base;
21+ this.kids = [];
22+ this.defaultNumberOfKids = 0;
23+ this.recv = function(timestep, eid, v) {
24+ var changed = eid === this.id;
25+ if (changed) { this.value = v; }
26+ send(this, timestep, changed);
27+ return changed;
28+ };
29+ elm.inputs.push(this);
30+ }
31+
32+ function LiftN(update, args) {
33+ this.id = Utils.guid();
34+ this.value = update();
35+ this.kids = [];
36+
37+ var n = args.length;
38+ var count = 0;
39+ var isChanged = false;
40+
41+ this.recv = function(timestep, changed, parentID) {
42+ ++count;
43+ if (changed) { isChanged = true; }
44+ if (count == n) {
45+ if (isChanged) { this.value = update(); }
46+ send(this, timestep, isChanged);
47+ isChanged = false;
48+ count = 0;
49+ }
50+ };
51+ for (var i = n; i--; ) { args[i].kids.push(this); }
52+ }
53+
54+ function lift(func, a) {
55+ function update() { return func(a.value); }
56+ return new LiftN(update, [a]);
57+ }
58+ function lift2(func, a, b) {
59+ function update() { return A2( func, a.value, b.value ); }
60+ return new LiftN(update, [a,b]);
61+ }
62+ function lift3(func, a, b, c) {
63+ function update() { return A3( func, a.value, b.value, c.value ); }
64+ return new LiftN(update, [a,b,c]);
65+ }
66+ function lift4(func, a, b, c, d) {
67+ function update() { return A4( func, a.value, b.value, c.value, d.value ); }
68+ return new LiftN(update, [a,b,c,d]);
69+ }
70+ function lift5(func, a, b, c, d, e) {
71+ function update() { return A5( func, a.value, b.value, c.value, d.value, e.value ); }
72+ return new LiftN(update, [a,b,c,d,e]);
73+ }
74+ function lift6(func, a, b, c, d, e, f) {
75+ function update() { return A6( func, a.value, b.value, c.value, d.value, e.value, f.value ); }
76+ return new LiftN(update, [a,b,c,d,e,f]);
77+ }
78+ function lift7(func, a, b, c, d, e, f, g) {
79+ function update() { return A7( func, a.value, b.value, c.value, d.value, e.value, f.value, g.value ); }
80+ return new LiftN(update, [a,b,c,d,e,f,g]);
81+ }
82+ function lift8(func, a, b, c, d, e, f, g, h) {
83+ function update() { return A8( func, a.value, b.value, c.value, d.value, e.value, f.value, g.value, h.value ); }
84+ return new LiftN(update, [a,b,c,d,e,f,g,h]);
85+ }
86+
87+ function foldp(func,state,input) {
88+ var first = true;
89+ function update() {
90+ first ? first = false : state = A2(func, input.value, state);
91+ return state;
92+ }
93+ return new LiftN(update, [input]);
94+ }
95+
96+ function DropIf(pred,base,input) {
97+ this.id = Utils.guid();
98+ this.value = pred(input.value) ? base : input.value;
99+ this.kids = [];
100+ this.recv = function(timestep, changed, parentID) {
101+ var chng = changed && !pred(input.value);
102+ if (chng) { this.value = input.value; }
103+ send(this, timestep, chng);
104+ };
105+ input.kids.push(this);
106+ }
107+
108+ function DropRepeats(input) {
109+ this.id = Utils.guid();
110+ this.value = input.value;
111+ this.kids = [];
112+ this.recv = function(timestep, changed, parentID) {
113+ var chng = changed && !Utils.eq(this.value,input.value);
114+ if (chng) { this.value = input.value; }
115+ send(this, timestep, chng);
116+ };
117+ input.kids.push(this);
118+ }
119+
120+ function dropWhen(s1,b,s2) {
121+ var pairs = lift2( F2(function(x,y){return {x:x,y:y};}), s1, s2 );
122+ var dropped = new DropIf(function(p){return p.x;},{x:true,y:b},pairs);
123+ return lift(function(p){return p.y;}, dropped);
124+ }
125+
126+ function timestamp(a) {
127+ function update() { return Utils.Tuple2(Date.now(), a.value); }
128+ return new LiftN(update, [a]);
129+ }
130+
131+ function SampleOn(s1,s2) {
132+ this.id = Utils.guid();
133+ this.value = s2.value;
134+ this.kids = [];
135+
136+ var count = 0;
137+ var isChanged = false;
138+
139+ this.recv = function(timestep, changed, parentID) {
140+ if (parentID === s1.id) isChanged = changed;
141+ ++count;
142+ if (count == 2) {
143+ if (isChanged) { this.value = s2.value; }
144+ send(this, timestep, isChanged);
145+ count = 0;
146+ isChanged = false;
147+ }
148+ };
149+ s1.kids.push(this);
150+ s2.kids.push(this);
151+ }
152+
153+ function sampleOn(s1,s2) { return new SampleOn(s1,s2); }
154+
155+ function delay(t,s) {
156+ var delayed = new Input(s.value);
157+ var firstEvent = true;
158+ function update(v) {
159+ if (firstEvent) { firstEvent = false; return; }
160+ setTimeout(function() { elm.notify(delayed.id, v); }, t);
161+ }
162+ function first(a,b) { return a; }
163+ return new SampleOn(delayed, lift2(F2(first), delayed, lift(update,s)));
164+ }
165+
166+ function Merge(s1,s2) {
167+ this.id = Utils.guid();
168+ this.value = s1.value;
169+ this.kids = [];
170+
171+ var next = null;
172+ var count = 0;
173+ var isChanged = false;
174+
175+ this.recv = function(timestep, changed, parentID) {
176+ ++count;
177+ if (changed) {
178+ isChanged = true;
179+ if (parentID == s2.id && next === null) { next = s2.value; }
180+ if (parentID == s1.id) { next = s1.value; }
181+ }
182+
183+ if (count == 2) {
184+ if (isChanged) { this.value = next; next = null; }
185+ send(this, timestep, isChanged);
186+ isChanged = false;
187+ count = 0;
188+ }
189+ };
190+ s1.kids.push(this);
191+ s2.kids.push(this);
192+ }
193+
194+ function merge(s1,s2) { return new Merge(s1,s2); }
195+ function merges(ss) { return A2(foldl1, F2(merge), ss); }
196+
197+ return elm.Native.Signal = {
198+ constant : function(v) { return new Input(v); },
199+ lift : F2(lift ),
200+ lift2 : F3(lift2),
201+ lift3 : F4(lift3),
202+ lift4 : F5(lift4),
203+ lift5 : F6(lift5),
204+ lift6 : F7(lift6),
205+ lift7 : F8(lift7),
206+ lift8 : F9(lift8),
207+ foldp : F3(foldp),
208+ delay : F2(delay),
209+ merge : F2(merge),
210+ merges : merges,
211+ count : function(s) { return foldp(F2(function(_,c) { return c+1; }), 0, s); },
212+ countIf : F2(function(pred,s) {
213+ return foldp(F2(function(x,c){
214+ return pred(x) ? c+1 : c; }), 0, s)}),
215+ keepIf : F3(function(pred,base,sig) {
216+ return new DropIf(function(x) {return !pred(x);},base,sig); }),
217+ dropIf : F3(function(pred,base,sig) { return new DropIf(pred,base,sig); }),
218+ keepWhen : F3(function(s1,b,s2) {
219+ return dropWhen(lift(function(b){return !b;},s1), b, s2); }),
220+ dropWhen : F3(dropWhen),
221+ dropRepeats : function(s) { return new DropRepeats(s);},
222+ sampleOn : F2(sampleOn),
223+ timestamp : timestamp
224+ };
225+};
libraries/Native/Signal/Time.jsnew file+60
@@ -0,0 +1,60 @@
1+
2+Elm.Native.Time = function(elm) {
3+ 'use strict';
4+
5+ var Signal = Elm.Signal(elm);
6+ var Maybe = Elm.Maybe(elm);
7+ var Utils = Elm.Native.Utils(elm);
8+
9+ function fpsWhen(desiredFPS, isOn) {
10+ var msPerFrame = 1000 / desiredFPS;
11+ var prev = Date.now(), curr = prev, diff = 0, wasOn = true;
12+ var ticker = Signal.constant(diff);
13+ function tick(zero) { return function() {
14+ curr = Date.now();
15+ diff = zero ? 0 : curr - prev;
16+ prev = curr;
17+ elm.notify(ticker.id, diff);
18+ };
19+ }
20+ var timeoutID = 0;
21+ function f(isOn, t) {
22+ if (isOn) {
23+ timeoutID = setTimeout(tick(!wasOn && isOn), msPerFrame);
24+ } else if (wasOn) {
25+ clearTimeout(timeoutID);
26+ }
27+ wasOn = isOn;
28+ return t;
29+ }
30+ return A3( Signal.lift2, F2(f), isOn, ticker );
31+ }
32+
33+ function everyWhen(t, isOn) {
34+ var clock = Signal.constant(Date.now());
35+ function tellTime() { elm.notify(clock.id, Date.now()); }
36+ setInterval(tellTime, t);
37+ return clock;
38+ }
39+
40+ function since(t, s) {
41+ function cmp(a,b) { return !Utils.eq(a,b); }
42+ var dcount = Signal.count(A2(Signal.delay, t, s));
43+ return A3( Signal.lift2, F2(cmp), Signal.count(s), dcount );
44+ }
45+ function read(s) {
46+ var t = Date.parse(s);
47+ return isNaN(t) ? Maybe.Nothing : Maybe.Just(t);
48+ }
49+ return elm.Native.Time = {
50+ fpsWhen : F2(fpsWhen),
51+ fps : function(t) { return fpsWhen(t, Signal.constant(true)); },
52+ every : function(t) { return everyWhen(t, Signal.constant(true)) },
53+ delay : Signal.delay,
54+ timestamp : Signal.timestamp,
55+ since : F2(since),
56+ toDate : function(t) { return new window.Date(t); },
57+ read : read
58+ };
59+
60+};
libraries/Native/Signal/Touch.jsnew file+150
@@ -0,0 +1,150 @@
1+
2+Elm.Native.Touch = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Touch) return elm.Native.Touch;
7+
8+ var Signal = Elm.Signal(elm);
9+ var JS = Elm.JavaScript(elm);
10+ var _ = Elm.Native.Utils(elm);
11+
12+ function Dict() {
13+ this.keys = [];
14+ this.values = [];
15+
16+ this.insert = function(key,value) {
17+ this.keys.push(key);
18+ this.values.push(value);
19+ };
20+ this.lookup = function(key) {
21+ var i = this.keys.indexOf(key)
22+ return i >= 0 ? this.values[i] : {x:0,y:0,t:0};
23+ };
24+ this.remove = function(key) {
25+ var i = this.keys.indexOf(key);
26+ if (i < 0) return;
27+ var t = this.values[i];
28+ this.keys.splice(i,1);
29+ this.values.splice(i,1);
30+ return t;
31+ };
32+ this.clear = function() {
33+ this.keys = [];
34+ this.values = [];
35+ };
36+ }
37+
38+ var root = Signal.constant([]),
39+ tapTime = 500,
40+ hasTap = false,
41+ tap = {_:{},x:0,y:0},
42+ dict = new Dict();
43+
44+ function touch(t) {
45+ var r = dict.lookup(t.identifier);
46+ return {_ : {},
47+ id: t.identifier,
48+ x : t.pageX - elm.node.offsetX,
49+ y : t.pageY - elm.node.offsetY,
50+ x0: r.x,
51+ y0: r.y,
52+ t0: r.t
53+ };
54+ }
55+
56+ var node = elm.display === ElmRuntime.Display.FULLSCREEN ? document : elm.node;
57+
58+ function start(e) {
59+ dict.insert(e.identifier,
60+ {x: e.pageX - elm.node.offsetX,
61+ y: e.pageY - elm.node.offsetY,
62+ t: Date.now()});
63+ }
64+ function end(e) {
65+ var t = dict.remove(e.identifier);
66+ if (Date.now() - t.t < tapTime) {
67+ hasTap = true;
68+ tap = {_:{}, x:t.x, y:t.y};
69+ }
70+ }
71+
72+ function listen(name, f) {
73+ function update(e) {
74+ for (var i = e.changedTouches.length; i--; ) { f(e.changedTouches[i]); }
75+ var ts = new Array(e.touches.length);
76+ for (var i = e.touches.length; i--; ) { ts[i] = touch(e.touches[i]); }
77+ var hasListener = elm.notify(root.id, ts);
78+ if (!hasListener) return node.removeEventListener(name, update);
79+ e.preventDefault();
80+ }
81+ node.addEventListener(name, update);
82+ }
83+
84+ listen("touchstart", start);
85+ listen("touchmove", function(_){});
86+ listen("touchend", end);
87+ listen("touchcancel", end);
88+ listen("touchleave", end);
89+
90+ var mouseID = -1;
91+ function move(e) {
92+ for (var i = root.value.length; i--; ) {
93+ if (root.value[i].id === mouseID) {
94+ root.value[i].x = e.pageX - elm.node.offsetX;
95+ root.value[i].y = e.pageY - elm.node.offsetY;
96+ elm.notify(root.id, root.value);
97+ break;
98+ }
99+ }
100+ }
101+ node.addEventListener("mousedown", function(e) {
102+ node.addEventListener("mousemove", move);
103+ e.identifier = mouseID;
104+ start(e);
105+ root.value.push(touch(e));
106+ elm.notify(root.id, root.value);
107+ });
108+ node.addEventListener("mouseup", function(e) {
109+ node.removeEventListener("mousemove", move);
110+ e.identifier = mouseID;
111+ end(e);
112+ for (var i = root.value.length; i--; ) {
113+ if (root.value[i].id === mouseID) {
114+ root.value.splice(i, 1);
115+ --mouseID;
116+ break;
117+ }
118+ }
119+ elm.notify(root.id, root.value);
120+ });
121+ node.addEventListener("blur", function() {
122+ node.removeEventListener("mousemove", move);
123+ if (root.values.length > 0) {
124+ elm.notify(root.id, []);
125+ --mouseID;
126+ }
127+ dict.clear();
128+ });
129+
130+ function dependency(f) {
131+ var sig = A2( Signal.lift, f, root );
132+ root.defaultNumberOfKids += 1;
133+ sig.defaultNumberOfKids = 0;
134+ return sig;
135+ }
136+
137+ var touches = dependency(JS.toList);
138+
139+ var taps = function() {
140+ var sig = dependency(function(_) { return tap; });
141+ sig.defaultNumberOfKids = 1;
142+ function pred(_) { var b = hasTap; hasTap = false; return b; }
143+ var sig2 = A3( Signal.keepIf, pred, {_:{},x:0,y:0}, sig);
144+ sig2.defaultNumberOfKids = 0;
145+ return sig2;
146+ }();
147+
148+ return elm.Native.Touch = { touches: touches, taps: taps };
149+
150+};
libraries/Native/Signal/WebSocket.jsnew file+38
@@ -0,0 +1,38 @@
1+
2+Elm.Native.WebSocket = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.WebSocket) return elm.Native.WebSocket;
7+
8+ var Signal = Elm.Signal(elm);
9+ var JS = Elm.JavaScript(elm);
10+ var List = Elm.Native.List(elm);
11+
12+ function open(url, outgoing) {
13+ var incoming = Signal.constant(List.Nil);
14+ var ws = new WebSocket(JS.fromString(url));
15+
16+ var pending = [];
17+ var ready = false;
18+
19+ ws.onopen = function(e) {
20+ var len = pending.length;
21+ for (var i = 0; i < len; ++i) { ws.send(pending[i]); }
22+ ready = true;
23+ };
24+ ws.onmessage = function(event) {
25+ elm.notify(incoming.id, JS.toString(event.data));
26+ };
27+
28+ function send(msg) {
29+ var s = JS.fromString(msg);
30+ ready ? ws.send(s) : pending.push(s);
31+ }
32+
33+ function take1(x,y) { return x }
34+ return A3(Signal.lift2, F2(take1), incoming, A2(Signal.lift, send, outgoing));
35+ }
36+
37+ return elm.Native.WebSocket = { connect: F2(open) };
38+};
libraries/Native/Signal/Window.jsnew file+46
@@ -0,0 +1,46 @@
1+
2+Elm.Native.Window = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Window) return elm.Native.Window;
7+
8+ var Signal = Elm.Signal(elm);
9+ var Tuple2 = Elm.Native.Utils(elm).Tuple2;
10+
11+ function getWidth() { return elm.node.clientWidth; }
12+ function getHeight() {
13+ if (elm.display === ElmRuntime.Display.FULLSCREEN) {
14+ return window.innerHeight;
15+ }
16+ return elm.node.clientHeight;
17+ }
18+
19+ var dimensions = Signal.constant(Tuple2(getWidth(), getHeight()));
20+ dimensions.defaultNumberOfKids = 2;
21+
22+ // Do not move width and height into Elm. By setting the default number of kids,
23+ // the resize listener can be detached.
24+ var width = A2(Signal.lift, function(p){return p._0;}, dimensions);
25+ width.defaultNumberOfKids = 0;
26+
27+ var height = A2(Signal.lift, function(p){return p._1;}, dimensions);
28+ height.defaultNumberOfKids = 0;
29+
30+ function resizeIfNeeded() {
31+ var w = getWidth();
32+ var h = getHeight();
33+ if (dimensions.value._0 === w && dimensions.value._1 === h) return;
34+ var hasListener = elm.notify(dimensions.id, Tuple2(w,h));
35+ if (!hasListener) window.removeEventListener('resize', resizeIfNeeded);
36+ }
37+ window.addEventListener('resize', resizeIfNeeded);
38+
39+ return elm.Native.Window = {
40+ dimensions:dimensions,
41+ width:width,
42+ height:height,
43+ resizeIfNeeded:resizeIfNeeded
44+ };
45+
46+};
libraries/Native/Text.jsnew file+136
@@ -0,0 +1,136 @@
1+
2+Elm.Native.Text = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Text) return elm.Native.Text;
7+
8+ var JS = Elm.JavaScript(elm);
9+ var htmlHeight = Elm.Native.Utils(elm).htmlHeight;
10+ var Color = Elm.Native.Color(elm);
11+ var Element = Elm.Graphics.Element(elm);
12+ var show = Elm.Native.Show(elm).show;
13+
14+ function makeSpaces(s) {
15+ if (s.length == 0) { return s; }
16+ var arr = s.split('');
17+ if (arr[0] == ' ') { arr[0] = "&nbsp;" }
18+ for (var i = arr.length; --i; ) {
19+ if (arr[i][0] == ' ' && arr[i-1] == ' ') {
20+ arr[i-1] = arr[i-1] + arr[i];
21+ arr[i] = '';
22+ }
23+ }
24+ for (var i = arr.length; i--; ) {
25+ if (arr[i].length > 1 && arr[i][0] == ' ') {
26+ var spaces = arr[i].split('');
27+ for (var j = spaces.length - 2; j >= 0; j -= 2) {
28+ spaces[j] = '&nbsp;';
29+ }
30+ arr[i] = spaces.join('');
31+ }
32+ }
33+ arr = arr.join('');
34+ if (arr[arr.length-1] === " ") {
35+ return arr.slice(0,-1) + '&nbsp;';
36+ }
37+ return arr;
38+ }
39+
40+ function properEscape(str) {
41+ if (str.length == 0) return str;
42+ str = str //.replace(/&/g, "&#38;")
43+ .replace(/"/g, /*"*/ '&#34;')
44+ .replace(/'/g, /*'*/ "&#39;")
45+ .replace(/</g, "&#60;")
46+ .replace(/>/g, "&#62;")
47+ .replace(/\n/g, "<br/>");
48+ var arr = str.split('<br/>');
49+ for (var i = arr.length; i--; ) {
50+ arr[i] = makeSpaces(arr[i]);
51+ }
52+ return arr.join('<br/>');
53+ }
54+
55+ function toText(str) { return properEscape(JS.fromString(str)); }
56+
57+ function addTag(tag) { return function(text) {
58+ return '<' + tag + ' style="padding:0;margin:0">' + text + '</' + tag + '>';
59+ }
60+ }
61+
62+ function addStyle(style, value, text) {
63+ return "<span style='" + style + ":" + value + "'>" + text + "</span>";
64+ }
65+
66+ function typeface(name, text) {
67+ return addStyle('font-family', JS.fromString(name), text);
68+ }
69+ function monospace(text) {
70+ return addStyle('font-family', 'monospace', text);
71+ }
72+ function size(px, text) { return addStyle('font-size', px + 'px', text) }
73+ var header = addTag('h1');
74+ function height(h, text) { return addStyle('font-size', h+'em', text) }
75+ function italic(text) { return addStyle('font-style', 'italic', text) }
76+ var bold = addTag('b');
77+
78+ function extract(c) {
79+ if (c._3 === 1) { return 'rgb(' + c._0 + ',' + c._1 + ',' + c._2 + ')'; }
80+ return 'rgba(' + c._0 + ',' + c._1 + ',' + c._2 + ',' + c._3 + ')';
81+ }
82+ function color(c, text) {
83+ return addStyle('color', extract(c), text);
84+ }
85+ function underline(text) { return addStyle('text-decoration', 'underline', text) }
86+ function overline(text) { return addStyle('text-decoration', 'overline', text) }
87+ function strikeThrough(text) {
88+ return addStyle('text-decoration', 'line-through', text);
89+ }
90+ function link(href, text) {
91+ return "<a href='" + toText(href) + "'>" + text + "</a>";
92+ }
93+
94+ function position(pos) { return function(text) {
95+ var e = {ctor:'RawHtml',
96+ _0: '<div style="padding:0;margin:0;text-align:' +
97+ pos + '">' + text + '</div>'
98+ };
99+ var p = A2(htmlHeight, 0, text);
100+ return A3(Element.newElement, p._0, p._1, e);
101+ }
102+ }
103+
104+ function asText(v) {
105+ return position('left')(monospace(toText(show(v))));
106+ }
107+
108+ function plainText(v) {
109+ return position('left')(toText(v));
110+ }
111+
112+ return elm.Native.Text = {
113+ toText: toText,
114+
115+ header : header,
116+ height : F2(height),
117+ italic : italic,
118+ bold : bold,
119+ underline : underline,
120+ overline : overline,
121+ strikeThrough : strikeThrough,
122+ monospace : monospace,
123+ typeface : F2(typeface),
124+ color : F2(color),
125+ link : F2(link),
126+
127+ justified : position('justify'),
128+ centered : position('center'),
129+ righted : position('right'),
130+ text : position('left'),
131+ plainText : plainText,
132+
133+ asText : asText
134+ };
135+
136+};
libraries/Native/Utils.jsnew file+157
@@ -0,0 +1,157 @@
1+
2+Elm.Native.Utils = function(elm) {
3+ 'use strict';
4+
5+ elm.Native = elm.Native || {};
6+ if (elm.Native.Utils) return elm.Native.Utils;
7+
8+ function eq(x,y) {
9+ if (x === y) return true;
10+ if (typeof x === "object") {
11+ var c = 0;
12+ for (var i in x) { ++c; if (!eq(x[i],y[i])) return false; }
13+ return c === Object.keys(y).length;
14+ }
15+ if (typeof x === 'function') {
16+ throw new Error('Equality error: general function equality is ' +
17+ 'undecidable, and therefore, unsupported');
18+ }
19+ return x === y;
20+ }
21+
22+ var EQ = 0, LT = 1, GT = 2, ord = ['EQ','LT','GT'];
23+ function compare(x,y) { return { ctor: ord[cmp(x,y)] } }
24+ function cmp(x,y) {
25+ var ord;
26+ if (typeof x !== 'object') return x === y ? EQ : x < y ? LT : GT;
27+
28+ if (x.ctor === "Cons" || x.ctor === "Nil") {
29+ while (true) {
30+ if (x.ctor === "Nil" && y.ctor === "Nil") return EQ;
31+ if (x.ctor !== y.ctor) return x.ctor === 'Nil' ? LT : GT;
32+ ord = cmp(x._0, y._0);
33+ if (ord !== EQ) return ord;
34+ x = x._1;
35+ y = y._1;
36+ }
37+ }
38+
39+ if (x.ctor.slice(0,5) === 'Tuple') {
40+ var n = x.ctor.slice(5) - 0;
41+ var err = 'cannot compare tuples with more than 6 elements.';
42+ if (n === 0) return EQ;
43+ if (n >= 1) { ord = cmp(x._0, y._0); if (ord !== EQ) return ord;
44+ if (n >= 2) { ord = cmp(x._1, y._1); if (ord !== EQ) return ord;
45+ if (n >= 3) { ord = cmp(x._2, y._2); if (ord !== EQ) return ord;
46+ if (n >= 4) { ord = cmp(x._3, y._3); if (ord !== EQ) return ord;
47+ if (n >= 5) { ord = cmp(x._4, y._4); if (ord !== EQ) return ord;
48+ if (n >= 6) { ord = cmp(x._5, y._5); if (ord !== EQ) return ord;
49+ if (n >= 7) throw new Error('Comparison error: ' + err); } } } } } }
50+ return EQ;
51+ }
52+ throw new Error('Comparison error: comparison is only defined on ints, ' +
53+ 'floats, times, chars, strings, lists of comparable values, ' +
54+ 'and tuples of comparable values.')
55+ }
56+
57+
58+ var Tuple0 = { ctor: "Tuple0" };
59+ function Tuple2(x,y) { return { ctor:"Tuple2", _0:x, _1:y } }
60+
61+ var count = 0;
62+ function guid(_) { return count++ }
63+
64+ function copy(r) {
65+ var o = {};
66+ for (var i in r) { o[i] = r[i]; }
67+ return o;
68+ }
69+
70+ function remove(x,r) {
71+ var o = copy(r);
72+ if (x in o._) {
73+ o[x] = o._[x][0];
74+ o._[x] = o._[x].slice(1);
75+ if (o._[x].length === 0) { delete o._[x]; }
76+ } else {
77+ delete o[x];
78+ }
79+ return o;
80+ }
81+
82+ function replace(kvs,r) {
83+ var o = copy(r);
84+ for (var i = kvs.length; i--; ) {
85+ var kvsi = kvs[i];
86+ o[kvsi[0]] = kvsi[1];
87+ }
88+ return o;
89+ }
90+
91+ function insert(x,v,r) {
92+ var o = copy(r);
93+ if (x in o) o._[x] = [o[x]].concat(x in o._ ? o._[x].slice(0) : []);
94+ o[x] = v;
95+ return o;
96+ }
97+
98+ function max(a,b) { return a > b ? a : b }
99+ function min(a,b) { return a < b ? a : b }
100+
101+ function mod(a,b) {
102+ var r = a % b;
103+ var m = a === 0 ? 0 : (b > 0 ? (a >= 0 ? r : r+b) : -mod(-a,-b));
104+
105+ return m === b ? 0 : m;
106+ }
107+
108+ function htmlHeight(width, html) {
109+ var t = document.createElement('div');
110+ t.innerHTML = html;
111+ if (width > 0) { t.style.width = width + "px"; }
112+ t.style.visibility = "hidden";
113+ t.style.styleFloat = "left";
114+ t.style.cssFloat = "left";
115+
116+ elm.node.appendChild(t);
117+ var w = t.clientWidth;
118+ var h = t.clientHeight;
119+ elm.node.removeChild(t);
120+ return Tuple2(w,h);
121+ }
122+
123+ function adjustOffset() {
124+ var node = elm.node;
125+ var offsetX = 0, offsetY = 0;
126+ if (node.offsetParent) {
127+ do {
128+ offsetX += node.offsetLeft;
129+ offsetY += node.offsetTop;
130+ } while (node = node.offsetParent);
131+ }
132+ elm.node.offsetX = offsetX;
133+ elm.node.offsetY = offsetY;
134+ }
135+
136+ if (elm.display === ElmRuntime.Display.COMPONENT) {
137+ elm.node.addEventListener('mouseover', adjustOffset);
138+ }
139+
140+ return elm.Native.Utils = {
141+ eq:eq,
142+ cmp:compare,
143+ compare:F2(compare),
144+ Tuple0:Tuple0,
145+ Tuple2:Tuple2,
146+ copy: copy,
147+ remove: remove,
148+ replace: replace,
149+ insert: insert,
150+ guid: guid,
151+ max : F2(max),
152+ min : F2(min),
153+ mod : F2(mod),
154+ htmlHeight: F2(htmlHeight),
155+ toFloat: function(x){return x}
156+ };
157+};
libraries/Prelude.elmnew file+202
@@ -0,0 +1,202 @@
1+
2+module Prelude where
3+
4+import Native.Prelude as N
5+
6+-- Convert radians to standard Elm angles (radians).
7+radians : Float -> Float
8+radians t = t
9+
10+-- Convert degrees to standard Elm angles (radians).
11+degrees : Float -> Float
12+degrees d = d * Math.PI / 180
13+
14+-- Convert turns to standard Elm angles (radians).
15+-- One turn is equal to 360&deg;.
16+turns : Float -> Float
17+turns r = 2 * Math.PI * r
18+
19+-- Start with polar coordinates (r,&theta;)
20+-- and get out cartesian coordinates (x,y).
21+fromPolar : (Float,Float) -> (Float,Float)
22+fromPolar (r,t) = (r * N.cos t, r * N.sin t)
23+
24+-- Start with cartesian coordinates (x,y)
25+-- and get out polar coordinates (r,&theta;).
26+toPolar : (Float,Float) -> (Float,Float)
27+toPolar (x,y) = (N.sqrt (x^2 + y^2), N.atan2 y x)
28+
29+(+) : Number a -> Number a -> Number a
30+(-) : Number a -> Number a -> Number a
31+(*) : Number a -> Number a -> Number a
32+
33+-- Floating point division.
34+(/) : Float -> Float -> Float
35+
36+-- Integer division, remainder is discarded.
37+div : Int -> Int -> Int
38+
39+-- Finds the remainder after dividing one number by another: ``4 `rem` 3 == 1``
40+rem : Int -> Int -> Int
41+
42+-- Perform modular arithmetic: ``7 `mod` 2 == 1``
43+mod : Int -> Int -> Int
44+
45+-- Exponentiation: `3^2 == 9`
46+(^) : Number a -> Number a -> Number a
47+
48+cos : Float -> Float
49+sin : Float -> Float
50+tan : Float -> Float
51+acos : Float -> Float
52+asin : Float -> Float
53+
54+-- You probably do not want to use this. Because it takes `(y/x)` as the argument
55+-- there is no way to know where the negative signs come from so the resulting
56+-- angle is always between &pi;/2 and -&pi;/2 (in quadrants I and IV).
57+atan : Float -> Float
58+
59+-- This helps you find the angle of a cartesian coordinate.
60+-- You will almost certainly want to use this instead of `atan`.
61+-- So `atan2 y x` computes *atan(y/x)* but also keeps track of which
62+-- quadrant the angle should really be in. The result will be between
63+-- &pi; and -&pi;, giving you the full range of angles.
64+atan2 : Float -> Float -> Float
65+
66+-- Take the square root of a number.
67+sqrt : Number a -> Number a
68+
69+-- Take the absolute value of a number.
70+abs : Number a -> Number a
71+
72+-- Calculate the logarithm of a number with a given base: `logBase 10 100 == 2`
73+logBase : Number a -> Number a -> Number a
74+
75+-- Given two numbers, returns the smaller one.
76+min : Number a -> Number a -> Number a
77+
78+-- Given two numbers, returns the larger one.
79+max : Number a -> Number a -> Number a
80+
81+-- Clamps a number within a given range. With the expression `clamp 100 200 x`
82+-- the results are as follows:
83+--
84+-- * `100 if x < 100`
85+-- * ` x if 100 <= x < 200`
86+-- * `200 if 200 <= x`
87+clamp : Number a -> Number a -> Number a -> Number a
88+
89+-- An approximation of pi.
90+pi : Float
91+
92+-- An approximation of e.
93+e : Float
94+
95+-- Compare any two values for structural equality. Functions cannot be compared.
96+(==) : a -> a -> Bool
97+(/=) : a -> a -> Bool
98+
99+(<) : Comparable a -> Comparable a -> Bool
100+(>) : Comparable a -> Comparable a -> Bool
101+(<=) : Comparable a -> Comparable a -> Bool
102+(>=) : Comparable a -> Comparable a -> Bool
103+
104+-- Compare any two comparable values. Comparable values include `String`, `Char`,
105+-- `Int`, `Float`, `Time`, or a list or tuple containing comparable values.
106+-- These are also the only values that work as `Dict` keys or `Set` members.
107+compare : Comparable a -> Comparable a -> Order
108+
109+-- Represents the relative ordering of two things.
110+-- The relations are less than, equal to, and greater than.
111+data Order = LT | EQ | GT
112+
113+-- The and operator. True if both inputs are True.
114+(&&) : Bool -> Bool -> Bool
115+
116+-- The or operator. True if one or both inputs are True.
117+(||) : Bool -> Bool -> Bool
118+
119+-- The exclusive-or operator. True if exactly one input is True.
120+xor : Bool -> Bool -> Bool
121+
122+-- Negate a boolean value: `(not True == False)` and `(not False == True)`
123+not : Bool -> Bool
124+
125+-- Equal to true. Useful as the last case of a multi-way-if.
126+otherwise : Bool
127+otherwise = True
128+
129+
130+-- Conversions
131+
132+-- Round a number to the nearest integer.
133+round : Float -> Int
134+
135+-- Truncate a decimal number, rounding towards zero.
136+truncate : Float -> Int
137+
138+-- Floor function, rounding down.
139+floor : Float -> Int
140+
141+-- Ceiling function, rounding up.
142+ceiling : Float -> Int
143+
144+-- Convert an integer into a float.
145+toFloat : Int -> Float
146+
147+-- Convert almost any value to its string representation.
148+show : a -> String
149+
150+-- Read an integer from a string
151+readInt : String -> Maybe Int
152+
153+-- Read a float from a string.
154+readFloat : String -> Maybe Float
155+
156+-- Function Helpers
157+
158+-- Function composition: `(f . g == (\\x -> f (g x)))`
159+(.) : (b -> c) -> (a -> b) -> (a -> c)
160+
161+-- Forward function application `x |> f == f x`. This function is useful
162+-- for avoiding parenthesis and writing code in a more natural way.
163+-- Consider the following code to create a pentagon:
164+--
165+-- scale 2 (move (10,10) (filled blue (ngon 5 30)))
166+--
167+-- This can also be written as:
168+--
169+-- ngon 5 30 |> filled blue
170+-- |> move (10,10)
171+-- |> scale 2
172+(|>) : a -> (a -> b) -> b
173+
174+-- Function application `f <| x == f x`. This function is useful for avoiding
175+-- parenthesis. Consider the following code to create a text element:
176+--
177+-- text (monospace (toText "code"))
178+--
179+-- This can also be written as:
180+--
181+-- text . monospace <| toText "code"
182+(<|) : (a -> b) -> a -> b
183+
184+-- Given a value, returns exactly the same value.
185+id : a -> a
186+
187+-- Given a 2-tuple, returns the first value.
188+fst : (a,b) -> a
189+
190+-- Given a 2-tuple, returns the second value.
191+snd : (a,b) -> b
192+
193+-- Flips the order of the first two arguments to a function.
194+flip : (a -> b -> c) -> (b -> a -> c)
195+
196+-- Change how arguments are passed to a function. This splits paired arguments
197+-- into two separate arguments.
198+curry : ((a,b) -> c) -> a -> b -> c
199+
200+-- Change how arguments are passed to a function. This combines two arguments
201+-- into a sigle pair.
202+uncurry : (a -> b -> c) -> (a,b) -> c
libraries/Random.elmnew file+13
@@ -0,0 +1,13 @@
1+
2+module Random where
3+
4+import Native.Random as R
5+
6+-- Given a range from low to high and a signal of values, this produces
7+-- a new signal that changes whenever the input signal changes. The new
8+-- values are random number between 'low' and 'high' inclusive.
9+range : Int -> Int -> Signal a -> Signal Int
10+
11+-- Produces a new signal that changes whenever the input signal changes.
12+-- The new values are random numbers in [0..1).
13+float : Signal a -> Signal Float
libraries/Set.elmnew file+65
@@ -0,0 +1,65 @@
1+
2+module Set (empty,singleton,insert,remove
3+ ,member
4+ ,foldl,foldr,map
5+ ,union,intersect,diff
6+ ,toList,fromList
7+ ) where
8+
9+import Dict as Dict
10+import List as List
11+
12+type Set t = Dict t ()
13+
14+-- Create an empty set.
15+empty : Set (Comparable k)
16+empty = Dict.empty
17+
18+-- Create a set with one value.
19+singleton : Comparable k -> Set (Comparable k)
20+singleton k = Dict.singleton k ()
21+
22+-- Insert a value into a set.
23+insert : Comparable k -> Set (Comparable k) -> Set (Comparable k)
24+insert k = Dict.insert k ()
25+
26+-- Remove a value from a set. If the value is not found, no changes are made.
27+remove : Comparable k -> Set (Comparable k) -> Set (Comparable k)
28+remove = Dict.remove
29+
30+-- Determine if a value is in a set.
31+member : Comparable k -> Set (Comparable k) -> Bool
32+member = Dict.member
33+
34+-- Get the union of two sets. Keep all values.
35+union : Set (Comparable k) -> Set (Comparable k) -> Set (Comparable k)
36+union = Dict.union
37+
38+-- Get the intersection of two sets. Keeps values that appear in both sets.
39+intersect : Set (Comparable k) -> Set (Comparable k) -> Set (Comparable k)
40+intersect = Dict.intersect
41+
42+-- Get the difference between the first set and the second. Keeps values
43+-- that do not appear in the second set.
44+diff : Set (Comparable k) -> Set (Comparable k) -> Set (Comparable k)
45+diff = Dict.diff
46+
47+-- Convert a set into a list.
48+toList : Set (Comparable k) -> [Comparable k]
49+toList = Dict.keys
50+
51+-- Convert a list into a set, removing any duplicates.
52+fromList : [Comparable k] -> Set (Comparable k)
53+fromList xs = List.foldl insert empty xs
54+
55+-- Fold over the values in a set, in order from lowest to highest.
56+foldl : (Comparable a -> b -> b) -> b -> Set (Comparable a) -> b
57+foldl f b s = Dict.foldl (\k _ b -> f k b) b s
58+
59+-- Fold over the values in a set, in order from highest to lowest.
60+foldr : (Comparable a -> b -> b) -> b -> Set (Comparable a) -> b
61+foldr f b s = Dict.foldr (\k _ b -> f k b) b s
62+
63+-- Map a function onto a set, creating a new set with no duplicates.
64+map : (Comparable a -> Comparable b) -> Set (Comparable a) -> Set (Comparable b)
65+map f s = fromList (List.map f (toList s))
libraries/Signal.elmnew file+109
@@ -0,0 +1,109 @@
1+
2+-- The library for general signal manipulation. Some useful functions for
3+-- working with time (e.g. setting FPS) and combining signals and time (e.g.
4+-- delaying updates, getting timestamps) can be found in the
5+-- [`Time`](/docs/Signal/Time.elm) library.
6+--
7+-- Note: There are lift functions up to `lift8`.
8+module Signal where
9+
10+import Native.Signal as S
11+import List as L
12+
13+-- Create a constant signal that never changes.
14+constant : a -> Signal a
15+
16+-- Transform a signal with a given function.
17+lift : (a -> b) -> Signal a -> Signal b
18+
19+-- Combine two signals with a given function.
20+lift2 : (a -> b -> c) -> Signal a -> Signal b -> Signal c
21+
22+-- Combine three signals with a given function.
23+lift3 : (a -> b -> c -> d) -> Signal a -> Signal b -> Signal c -> Signal d
24+lift4 : (a -> b -> c -> d -> e) -> Signal a -> Signal b -> Signal c -> Signal d -> Signal e
25+lift5 : (a -> b -> c -> d -> e -> f) -> Signal a -> Signal b -> Signal c -> Signal d -> Signal e -> Signal f
26+lift6 : (a -> b -> c -> d -> e -> f -> g)
27+ -> Signal a -> Signal b -> Signal c -> Signal d -> Signal e -> Signal f -> Signal g
28+lift7 : (a -> b -> c -> d -> e -> f -> g -> h)
29+ -> Signal a -> Signal b -> Signal c -> Signal d -> Signal e -> Signal f -> Signal g -> Signal h
30+lift8 : (a -> b -> c -> d -> e -> f -> g -> h -> i)
31+ -> Signal a -> Signal b -> Signal c -> Signal d -> Signal e -> Signal f -> Signal g -> Signal h -> Signal i
32+
33+-- Create a past-dependent signal. Each value given on the input signal will
34+-- be accumulated, producing a new output value.
35+--
36+-- For instance, `(foldp (\\t acc -> acc + 1) 0 (Time.every second))` increments every second.
37+foldp : (a -> b -> b) -> b -> Signal a -> Signal b
38+
39+-- Merge two signals into one, biased towards the first signal if both signals
40+-- update at the same time.
41+merge : Signal a -> Signal a -> Signal a
42+
43+-- Merge many signals into one, biased towards the left-most signal if multiple
44+-- signals update simultaneously.
45+merges : [Signal a] -> Signal a
46+
47+-- Combine a list of signals into a signal of lists.
48+combine : [Signal a] -> Signal [a]
49+combine = L.foldr (S.lift2 (::)) (S.constant [])
50+
51+ -- Merge two signals into one, but distinguishing the values by marking the first
52+ -- signal as `Left` and the second signal as `Right`. This allows you to easily
53+ -- fold over non-homogeneous inputs.
54+ -- mergeEither : Signal a -> Signal b -> Signal (Either a b)
55+
56+-- Count the number of events that have occured.
57+count : Signal a -> Signal Int
58+
59+-- Count the number of events that have occured that satisfy a given predicate.
60+countIf : (a -> Bool) -> Signal a -> Signal Int
61+
62+-- Keep only events that satisfy the given predicate. Elm does not allow
63+-- undefined signals, so a base case must be provided in case the predicate is
64+-- never satisfied.
65+keepIf : (a -> Bool) -> a -> Signal a -> Signal a
66+
67+-- Drop events that satisfy the given predicate. Elm does not allow undefined
68+-- signals, so a base case must be provided in case the predicate is never
69+-- satisfied.
70+dropIf : (a -> Bool) -> a -> Signal a -> Signal a
71+
72+-- Keep events only when the first signal is true. When the first signal becomes
73+-- true, the most recent value of the second signal will be propagated. Until
74+-- the first signal becomes false again, all events will be propagated. Elm does
75+-- not allow undefined signals, so a base case must be provided in case the first
76+-- signal is never true.
77+keepWhen : Signal Bool -> a -> Signal a -> Signal a
78+
79+-- Drop events when the first signal is true. When the first signal becomes false,
80+-- the most recent value of the second signal will be propagated. Until the first
81+-- signal becomes true again, all events will be propagated. Elm does not allow
82+-- undefined signals, so a base case must be provided in case the first signal is
83+-- always true.
84+dropWhen : Signal Bool -> a -> Signal a -> Signal a
85+
86+-- Drop sequential repeated values. For example, if a signal produces the
87+-- sequence `[1,1,2,2,1]`, it becomes `[1,2,1]` by dropping the values that
88+-- are the same as the previous value.
89+dropRepeats : Signal a -> Signal a
90+
91+-- Sample from the second input every time an event occurs on the first input.
92+-- For example, `(sampleOn clicks (every second))` will give the approximate
93+-- time of the latest click.
94+sampleOn : Signal a -> Signal b -> Signal b
95+
96+-- An alias for `lift`. A prettier way to apply a
97+-- function to the current value of a signal.
98+--
99+-- lift f signal == f <~ signal
100+(<~) : (a -> b) -> Signal a -> Signal b
101+
102+-- Signal application. This takes two signals, holding a function and
103+-- a value. It applies the current function to the current value.
104+--
105+-- So the following expressions are equivalent:
106+--
107+-- scene <~ Window.dimensions ~ Mouse.position
108+-- lift2 scene Window.dimensions Mouse.position
109+(~) : Signal (a -> b) -> Signal a -> Signal b
libraries/Text.elmnew file+65
@@ -0,0 +1,65 @@
1+
2+module Text where
3+
4+import Native.Text as T
5+
6+
7+-- Convert a string into text which can be styled and displayed.
8+toText : String -> Text
9+
10+-- Set the typeface of some text. The first argument should be a comma separated listing of the desired typefaces
11+-- "helvetica, arial, sans-serif"
12+-- Works the same as the CSS font-family property.
13+typeface : String -> Text -> Text
14+
15+-- Switch to a monospace typeface. Good for code snippets.
16+monospace : Text -> Text
17+
18+-- Make text big and noticable.
19+header : Text -> Text
20+
21+-- Create a link.
22+link : String -> Text -> Text
23+
24+-- Set the height of text in \"ems\". 1em is the normal height of text. 2ems is twice that height.
25+height : Float -> Text -> Text
26+
27+-- Set the color of a string.
28+color : Color -> Text -> Text
29+
30+-- Make a string bold.
31+bold : Text -> Text
32+
33+-- Italicize a string.
34+italic : Text -> Text
35+
36+-- Draw a line above a string.
37+overline : Text -> Text
38+
39+-- Underline a string.
40+underline : Text -> Text
41+
42+-- Draw a line through a string.
43+strikeThrough : Text -> Text
44+
45+-- Display justified, styled text.
46+justified : Text -> Element
47+
48+-- Display centered, styled text.
49+centered : Text -> Element
50+
51+-- Display right justified, styled text.
52+righted : Text -> Element
53+
54+-- Display styled text.
55+text : Text -> Element
56+
57+-- Display a plain string.
58+plainText : String -> Element
59+
60+-- Convert anything to it's textual representation and make it displayable in browser
61+--
62+-- asText == text . monospace . show
63+--
64+-- Excellent for debugging.
65+asText : a -> Element
libraries/Time.elmnew file+69
@@ -0,0 +1,69 @@
1+-- Library for working with time. Type `Time` represents some number of milliseconds.
2+module Time where
3+
4+import Native.Time as T
5+
6+-- Type alias to make it clearer when you are working with time values.
7+-- Using the `Time` constants instead of raw numbers is very highly recommended.
8+type Time = Float
9+
10+-- Units of time, making it easier to specify things like a
11+-- half-second `(500 * milliseconds)` without remembering Elm&rsquo;s
12+-- underlying units of time.
13+millisecond : Time
14+millisecond = 1
15+
16+second : Time
17+second = 1000 * millisecond
18+
19+minute : Time
20+minute = 60 * second
21+
22+hour : Time
23+hour = 60 * minute
24+
25+inMilliseconds : Time -> Float
26+inMilliseconds t = t
27+
28+inSeconds : Time -> Float
29+inSeconds t = t / second
30+
31+inMinutes : Time -> Float
32+inMinutes t = t / minute
33+
34+inHours : Time -> Float
35+inHours t = t / hour
36+
37+-- Takes desired number of frames per second (fps). The resulting signal
38+-- gives a sequence of time deltas as quickly as possible until it reaches
39+-- the desired FPS. A time delta is the time between the last frame and the
40+-- current frame.
41+fps : Number a -> Signal Time
42+
43+-- Same as the fps function, but you can turn it on and off. Allows you
44+-- to do brief animations based on user input without major inefficiencies.
45+-- The first time delta after a pause is always zero, no matter how long
46+-- the pause was. This way summing the deltas will actually give the amount
47+-- of time that the output signal has been running.
48+fpsWhen : Number a -> Signal Bool -> Signal Time
49+
50+-- Takes a time interval t. The resulting signal is the current time,
51+-- updated every t.
52+every : Time -> Signal Time
53+
54+-- Takes a time `t` and any signal. The resulting boolean signal
55+-- is true for time `t` after every event on the input signal.
56+-- So ``(second `since` Mouse.clicks)`` would result in a signal
57+-- that is true for one second after each mouse click and false
58+-- otherwise.
59+since : Time -> Signal a -> Signal Bool
60+
61+-- Add a timestamp to any signal. Timestamps increase monotonically. Each
62+-- timestamp is related to a specfic event, so `Mouse.x` and `Mouse.y` will
63+-- always have the same timestamp because they both rely on the same
64+-- underlying event.
65+timestamp : Signal a -> Signal (Time, a)
66+
67+-- Delay a signal by a certain amount of time. So `(delay second Mouse.clicks)`
68+-- will update one second later than any mouse click.
69+delay : Time -> Signal a -> Signal a
libraries/Touch.elmnew file+20
@@ -0,0 +1,20 @@
1+-- This is an early version of the touch library. It will likely grow to
2+-- include gestures that would be useful for both games and web-pages.
3+module Touch where
4+
5+import Native.Touch as T
6+
7+-- Every `Touch` has `xy` coordinates. It also has an identifier `id` to
8+-- distinguish one touch from another.
9+--
10+-- A touch also keeps info about the intial point and time of contact:
11+-- `x0`, `y0`, and `t0`. This helps compute more complicated gestures
12+-- like taps, drags, and swipes which need to know about timing or direction.
13+type Touch = { x:Int, y:Int, id:Int, x0:Int, y0:Int, t0:Time }
14+
15+-- A list of ongoing touches.
16+touches : Signal [Touch]
17+
18+-- The last position that was tapped. Default value is `{x=0,y=0}`.
19+-- Updates whenever the user taps the screen.
20+taps : Signal { x:Int, y:Int }
libraries/WebSocket.elmnew file+13

This diff is too big to show here.

libraries/Window.elmnew file+14

This diff is too big to show here.

runtime/Init.jsnew file+117

This diff is too big to show here.

runtime/Render/Collage.jsnew file+340

This diff is too big to show here.

runtime/Render/Element.jsnew file+269

This diff is too big to show here.

runtime/Render/Utils.jsnew file+49

This diff is too big to show here.

runtime/Utils.jsnew file+53

This diff is too big to show here.

elm/LICENSE → server/LICENSErenamed

The content is the same.

elm-server/Server.hs → server/Server.hsrenamed+3−2

This diff is too big to show here.

elm-server/Setup.hs → server/Setup.hsrenamed

The content is the same.

elm-server/elm-server.cabal → server/elm-server.cabalrenamed+2−2

This diff is too big to show here.