aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.gitignore2
-rw-r--r--README.md1
-rw-r--r--config.txt1
-rw-r--r--elm-package.json2
-rw-r--r--package.json12
-rw-r--r--public/javascripts/.gitkeep0
-rw-r--r--public/javascripts/client.js17024
-rw-r--r--public/javascripts/elmLauncher.js13
-rw-r--r--public/javascripts/main.js28
-rw-r--r--sharedCost.cabal55
-rw-r--r--src/client/Main.elm101
-rw-r--r--src/client/ServerCommunication.elm143
-rw-r--r--src/client/elm/InitViewAction.elm25
-rw-r--r--src/client/elm/Main.elm89
-rw-r--r--src/client/elm/Model.elm (renamed from src/client/Model.elm)0
-rw-r--r--src/client/elm/Model/Config.elm (renamed from src/client/Model/Config.elm)0
-rw-r--r--src/client/elm/Model/Date.elm (renamed from src/client/Model/Date.elm)0
-rw-r--r--src/client/elm/Model/Income.elm (renamed from src/client/Model/Income.elm)0
-rw-r--r--src/client/elm/Model/Payer.elm (renamed from src/client/Model/Payer.elm)0
-rw-r--r--src/client/elm/Model/Payment.elm (renamed from src/client/Model/Payment.elm)0
-rw-r--r--src/client/elm/Model/Translations.elm (renamed from src/client/Model/Translations.elm)0
-rw-r--r--src/client/elm/Model/User.elm (renamed from src/client/Model/User.elm)0
-rw-r--r--src/client/elm/Model/View.elm (renamed from src/client/Model/View.elm)0
-rw-r--r--src/client/elm/Model/View/LoggedIn/Account.elm (renamed from src/client/Model/View/LoggedIn/Account.elm)0
-rw-r--r--src/client/elm/Model/View/LoggedIn/Add.elm (renamed from src/client/Model/View/LoggedIn/Add.elm)0
-rw-r--r--src/client/elm/Model/View/LoggedIn/Edition.elm (renamed from src/client/Model/View/LoggedIn/Edition.elm)0
-rw-r--r--src/client/elm/Model/View/LoggedIn/Monthly.elm (renamed from src/client/Model/View/LoggedIn/Monthly.elm)0
-rw-r--r--src/client/elm/Model/View/LoggedInView.elm (renamed from src/client/Model/View/LoggedInView.elm)0
-rw-r--r--src/client/elm/Model/View/SignInView.elm (renamed from src/client/Model/View/SignInView.elm)0
-rw-r--r--src/client/elm/Native/Reads.js (renamed from src/client/Native/Reads.js)0
-rw-r--r--src/client/elm/Persona.elm28
-rw-r--r--src/client/elm/Reads.elm (renamed from src/client/Reads.elm)0
-rw-r--r--src/client/elm/ServerCommunication.elm95
-rw-r--r--src/client/elm/Sign.elm43
-rw-r--r--src/client/elm/SimpleHTTP.elm41
-rw-r--r--src/client/elm/Update.elm (renamed from src/client/Update.elm)0
-rw-r--r--src/client/elm/Update/LoggedIn.elm (renamed from src/client/Update/LoggedIn.elm)0
-rw-r--r--src/client/elm/Update/LoggedIn/Account.elm (renamed from src/client/Update/LoggedIn/Account.elm)0
-rw-r--r--src/client/elm/Update/LoggedIn/Add.elm (renamed from src/client/Update/LoggedIn/Add.elm)0
-rw-r--r--src/client/elm/Update/LoggedIn/Monthly.elm (renamed from src/client/Update/LoggedIn/Monthly.elm)0
-rw-r--r--src/client/elm/Update/SignIn.elm (renamed from src/client/Update/SignIn.elm)11
-rw-r--r--src/client/elm/Utils/Dict.elm (renamed from src/client/Utils/Dict.elm)0
-rw-r--r--src/client/elm/Utils/Either.elm (renamed from src/client/Utils/Either.elm)0
-rw-r--r--src/client/elm/Utils/Maybe.elm (renamed from src/client/Utils/Maybe.elm)0
-rw-r--r--src/client/elm/Utils/Validation.elm (renamed from src/client/Utils/Validation.elm)0
-rw-r--r--src/client/elm/View/Date.elm (renamed from src/client/View/Date.elm)0
-rw-r--r--src/client/elm/View/Events.elm (renamed from src/client/View/Events.elm)0
-rw-r--r--src/client/elm/View/Expand.elm (renamed from src/client/View/Expand.elm)0
-rw-r--r--src/client/elm/View/Header.elm (renamed from src/client/View/Header.elm)15
-rw-r--r--src/client/elm/View/Icon.elm (renamed from src/client/View/Icon.elm)0
-rw-r--r--src/client/elm/View/Loading.elm (renamed from src/client/View/Loading.elm)0
-rw-r--r--src/client/elm/View/LoggedIn.elm (renamed from src/client/View/LoggedIn.elm)0
-rw-r--r--src/client/elm/View/LoggedIn/Account.elm (renamed from src/client/View/LoggedIn/Account.elm)0
-rw-r--r--src/client/elm/View/LoggedIn/Add.elm (renamed from src/client/View/LoggedIn/Add.elm)0
-rw-r--r--src/client/elm/View/LoggedIn/Monthly.elm (renamed from src/client/View/LoggedIn/Monthly.elm)0
-rw-r--r--src/client/elm/View/LoggedIn/Paging.elm (renamed from src/client/View/LoggedIn/Paging.elm)0
-rw-r--r--src/client/elm/View/LoggedIn/Table.elm (renamed from src/client/View/LoggedIn/Table.elm)0
-rw-r--r--src/client/elm/View/Page.elm (renamed from src/client/View/Page.elm)0
-rw-r--r--src/client/elm/View/Price.elm (renamed from src/client/View/Price.elm)0
-rw-r--r--src/client/elm/View/SignIn.elm (renamed from src/client/View/SignIn.elm)13
-rw-r--r--src/client/js/main.js28
-rw-r--r--src/server/Config.hs2
-rw-r--r--src/server/Controller/SignIn.hs84
-rw-r--r--src/server/Design/Header.hs2
-rw-r--r--src/server/Design/SignIn.hs20
-rw-r--r--src/server/Main.hs12
-rw-r--r--src/server/Model/Database.hs1
-rw-r--r--src/server/Model/Message/Key.hs6
-rw-r--r--src/server/Model/Message/Translations.hs26
-rw-r--r--src/server/Model/SignIn.hs17
-rw-r--r--src/server/Persona.hs42
-rw-r--r--src/server/Secure.hs7
-rw-r--r--src/server/View/Page.hs4
73 files changed, 17520 insertions, 473 deletions
diff --git a/.gitignore b/.gitignore
index 7540460..c391230 100644
--- a/.gitignore
+++ b/.gitignore
@@ -5,7 +5,7 @@ database
database-shm
database-wal
elm-stuff/
-public/javascripts/client.js
+./public/javascripts/*.js
sessionKey
deploy
kimsufi.tar.gz
diff --git a/README.md b/README.md
index 7023624..631926e 100644
--- a/README.md
+++ b/README.md
@@ -19,6 +19,5 @@ Here is an example configuration file:
```
hostname = localhost:3001
port = 3001
-sign-in-expiration-mn = 5
currency = €
```
diff --git a/config.txt b/config.txt
index 1c9e0b0..0fbe5df 100644
--- a/config.txt
+++ b/config.txt
@@ -1,4 +1,3 @@
hostname = localhost:3001
port = 3001
-sign-in-expiration-mn = 5
currency = €
diff --git a/elm-package.json b/elm-package.json
index 1835a26..b433fb2 100644
--- a/elm-package.json
+++ b/elm-package.json
@@ -3,7 +3,7 @@
"summary": "SharedCost",
"repository": "https://github.com/guyonvarch/sharedCost.git",
"license": "BSD3",
- "source-directories": ["src/client"],
+ "source-directories": ["src/client/elm"],
"exposed-modules": [],
"elm-version": "0.15.1 <= v < 0.16.0",
"dependencies": {
diff --git a/package.json b/package.json
index a44c384..cf98877 100644
--- a/package.json
+++ b/package.json
@@ -1,15 +1,17 @@
{
"devDependencies": {
- "watch": "0.16.0"
+ "watch": "0.17.1"
},
"scripts": {
- "watch": "npm run watch-server & npm run watch-client",
+ "watch": "npm run watch-server & npm run watch-elm & npm run watch-js",
"watch-server": "watch 'npm run build-and-launch-server --silent' src/server",
- "watch-client": "watch 'npm run build-client --silent' src/client",
+ "watch-elm": "watch 'npm run build-elm --silent' src/client/elm",
+ "watch-js": "watch 'npm run build-js --silent' src/client/js",
- "build": "npm run build-server && npm run build-client",
+ "build": "npm run build-server && npm run build-elm && npm run build-js",
"build-server": "cabal build",
- "build-client": "elm make src/client/Main.elm --output public/javascripts/client.js",
+ "build-elm": "elm make src/client/elm/Main.elm --output public/javascripts/client.js",
+ "build-js": "cp src/client/js/main.js public/javascripts/main.js && echo 'javascript pasted.'",
"build-and-launch-server": "npm run build-server && npm run kill-server && npm run launch-server",
"launch-server": "./dist/build/sharedCost/sharedCost &",
diff --git a/public/javascripts/.gitkeep b/public/javascripts/.gitkeep
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/public/javascripts/.gitkeep
diff --git a/public/javascripts/client.js b/public/javascripts/client.js
new file mode 100644
index 0000000..59f8d69
--- /dev/null
+++ b/public/javascripts/client.js
@@ -0,0 +1,17024 @@
+var Elm = Elm || { Native: {} };
+Elm.Array = Elm.Array || {};
+Elm.Array.make = function (_elm) {
+ "use strict";
+ _elm.Array = _elm.Array || {};
+ if (_elm.Array.values)
+ return _elm.Array.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Array",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Array = Elm.Native.Array.make(_elm);
+ var append = $Native$Array.append;
+ var length = $Native$Array.length;
+ var isEmpty = function (array) {
+ return _U.eq(length(array),
+ 0);
+ };
+ var slice = $Native$Array.slice;
+ var set = $Native$Array.set;
+ var get = F2(function (i,
+ array) {
+ return _U.cmp(0,
+ i) < 1 && _U.cmp(i,
+ $Native$Array.length(array)) < 0 ? $Maybe.Just(A2($Native$Array.get,
+ i,
+ array)) : $Maybe.Nothing;
+ });
+ var push = $Native$Array.push;
+ var empty = $Native$Array.empty;
+ var filter = F2(function (isOkay,
+ arr) {
+ var update = F2(function (x,
+ xs) {
+ return isOkay(x) ? A2($Native$Array.push,
+ x,
+ xs) : xs;
+ });
+ return A3($Native$Array.foldl,
+ update,
+ $Native$Array.empty,
+ arr);
+ });
+ var foldr = $Native$Array.foldr;
+ var foldl = $Native$Array.foldl;
+ var indexedMap = $Native$Array.indexedMap;
+ var map = $Native$Array.map;
+ var toIndexedList = function (array) {
+ return A3($List.map2,
+ F2(function (v0,v1) {
+ return {ctor: "_Tuple2"
+ ,_0: v0
+ ,_1: v1};
+ }),
+ _L.range(0,
+ $Native$Array.length(array) - 1),
+ $Native$Array.toList(array));
+ };
+ var toList = $Native$Array.toList;
+ var fromList = $Native$Array.fromList;
+ var initialize = $Native$Array.initialize;
+ var repeat = F2(function (n,e) {
+ return A2(initialize,
+ n,
+ $Basics.always(e));
+ });
+ var Array = {ctor: "Array"};
+ _elm.Array.values = {_op: _op
+ ,empty: empty
+ ,repeat: repeat
+ ,initialize: initialize
+ ,fromList: fromList
+ ,isEmpty: isEmpty
+ ,length: length
+ ,push: push
+ ,append: append
+ ,get: get
+ ,set: set
+ ,slice: slice
+ ,toList: toList
+ ,toIndexedList: toIndexedList
+ ,map: map
+ ,indexedMap: indexedMap
+ ,filter: filter
+ ,foldl: foldl
+ ,foldr: foldr};
+ return _elm.Array.values;
+};
+Elm.Basics = Elm.Basics || {};
+Elm.Basics.make = function (_elm) {
+ "use strict";
+ _elm.Basics = _elm.Basics || {};
+ if (_elm.Basics.values)
+ return _elm.Basics.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Basics",
+ $Native$Basics = Elm.Native.Basics.make(_elm),
+ $Native$Show = Elm.Native.Show.make(_elm),
+ $Native$Utils = Elm.Native.Utils.make(_elm);
+ var uncurry = F2(function (f,
+ _v0) {
+ var $ = _v0,
+ a = $._0,
+ b = $._1;
+ return A2(f,a,b);
+ });
+ var curry = F3(function (f,
+ a,
+ b) {
+ return f({ctor: "_Tuple2"
+ ,_0: a
+ ,_1: b});
+ });
+ var flip = F3(function (f,b,a) {
+ return A2(f,a,b);
+ });
+ var snd = function (_v1) {
+ var _ = _v1;
+ var b = function () {
+ switch (_.ctor)
+ {case "_Tuple2": return _._1;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }();
+ return b;
+ };
+ var fst = function (_v5) {
+ var _ = _v5;
+ var a = function () {
+ switch (_.ctor)
+ {case "_Tuple2": return _._0;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }();
+ return a;
+ };
+ var always = F2(function (a,
+ _v9) {
+ var _ = _v9;
+ return a;
+ });
+ var identity = function (x) {
+ return x;
+ };
+ _op["<|"] = F2(function (f,x) {
+ return f(x);
+ });
+ _op["|>"] = F2(function (x,f) {
+ return f(x);
+ });
+ _op[">>"] = F3(function (f,
+ g,
+ x) {
+ return g(f(x));
+ });
+ _op["<<"] = F3(function (g,
+ f,
+ x) {
+ return g(f(x));
+ });
+ _op["++"] = $Native$Utils.append;
+ var toString = $Native$Show.toString;
+ var isInfinite = $Native$Basics.isInfinite;
+ var isNaN = $Native$Basics.isNaN;
+ var toFloat = $Native$Basics.toFloat;
+ var ceiling = $Native$Basics.ceiling;
+ var floor = $Native$Basics.floor;
+ var truncate = $Native$Basics.truncate;
+ var round = $Native$Basics.round;
+ var otherwise = true;
+ var not = $Native$Basics.not;
+ var xor = $Native$Basics.xor;
+ _op["||"] = $Native$Basics.or;
+ _op["&&"] = $Native$Basics.and;
+ var max = $Native$Basics.max;
+ var min = $Native$Basics.min;
+ var GT = {ctor: "GT"};
+ var EQ = {ctor: "EQ"};
+ var LT = {ctor: "LT"};
+ var compare = $Native$Basics.compare;
+ _op[">="] = $Native$Basics.ge;
+ _op["<="] = $Native$Basics.le;
+ _op[">"] = $Native$Basics.gt;
+ _op["<"] = $Native$Basics.lt;
+ _op["/="] = $Native$Basics.neq;
+ _op["=="] = $Native$Basics.eq;
+ var e = $Native$Basics.e;
+ var pi = $Native$Basics.pi;
+ var clamp = $Native$Basics.clamp;
+ var logBase = $Native$Basics.logBase;
+ var abs = $Native$Basics.abs;
+ var negate = $Native$Basics.negate;
+ var sqrt = $Native$Basics.sqrt;
+ var atan2 = $Native$Basics.atan2;
+ var atan = $Native$Basics.atan;
+ var asin = $Native$Basics.asin;
+ var acos = $Native$Basics.acos;
+ var tan = $Native$Basics.tan;
+ var sin = $Native$Basics.sin;
+ var cos = $Native$Basics.cos;
+ _op["^"] = $Native$Basics.exp;
+ _op["%"] = $Native$Basics.mod;
+ var rem = $Native$Basics.rem;
+ _op["//"] = $Native$Basics.div;
+ _op["/"] = $Native$Basics.floatDiv;
+ _op["*"] = $Native$Basics.mul;
+ _op["-"] = $Native$Basics.sub;
+ _op["+"] = $Native$Basics.add;
+ var toPolar = $Native$Basics.toPolar;
+ var fromPolar = $Native$Basics.fromPolar;
+ var turns = $Native$Basics.turns;
+ var degrees = $Native$Basics.degrees;
+ var radians = function (t) {
+ return t;
+ };
+ _elm.Basics.values = {_op: _op
+ ,max: max
+ ,min: min
+ ,compare: compare
+ ,not: not
+ ,xor: xor
+ ,otherwise: otherwise
+ ,rem: rem
+ ,negate: negate
+ ,abs: abs
+ ,sqrt: sqrt
+ ,clamp: clamp
+ ,logBase: logBase
+ ,e: e
+ ,pi: pi
+ ,cos: cos
+ ,sin: sin
+ ,tan: tan
+ ,acos: acos
+ ,asin: asin
+ ,atan: atan
+ ,atan2: atan2
+ ,round: round
+ ,floor: floor
+ ,ceiling: ceiling
+ ,truncate: truncate
+ ,toFloat: toFloat
+ ,degrees: degrees
+ ,radians: radians
+ ,turns: turns
+ ,toPolar: toPolar
+ ,fromPolar: fromPolar
+ ,isNaN: isNaN
+ ,isInfinite: isInfinite
+ ,toString: toString
+ ,fst: fst
+ ,snd: snd
+ ,identity: identity
+ ,always: always
+ ,flip: flip
+ ,curry: curry
+ ,uncurry: uncurry
+ ,LT: LT
+ ,EQ: EQ
+ ,GT: GT};
+ return _elm.Basics.values;
+};
+Elm.Char = Elm.Char || {};
+Elm.Char.make = function (_elm) {
+ "use strict";
+ _elm.Char = _elm.Char || {};
+ if (_elm.Char.values)
+ return _elm.Char.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Char",
+ $Basics = Elm.Basics.make(_elm),
+ $Native$Char = Elm.Native.Char.make(_elm);
+ var fromCode = $Native$Char.fromCode;
+ var toCode = $Native$Char.toCode;
+ var toLocaleLower = $Native$Char.toLocaleLower;
+ var toLocaleUpper = $Native$Char.toLocaleUpper;
+ var toLower = $Native$Char.toLower;
+ var toUpper = $Native$Char.toUpper;
+ var isBetween = F3(function (low,
+ high,
+ $char) {
+ var code = toCode($char);
+ return _U.cmp(code,
+ toCode(low)) > -1 && _U.cmp(code,
+ toCode(high)) < 1;
+ });
+ var isUpper = A2(isBetween,
+ _U.chr("A"),
+ _U.chr("Z"));
+ var isLower = A2(isBetween,
+ _U.chr("a"),
+ _U.chr("z"));
+ var isDigit = A2(isBetween,
+ _U.chr("0"),
+ _U.chr("9"));
+ var isOctDigit = A2(isBetween,
+ _U.chr("0"),
+ _U.chr("7"));
+ var isHexDigit = function ($char) {
+ return isDigit($char) || (A3(isBetween,
+ _U.chr("a"),
+ _U.chr("f"),
+ $char) || A3(isBetween,
+ _U.chr("A"),
+ _U.chr("F"),
+ $char));
+ };
+ _elm.Char.values = {_op: _op
+ ,isUpper: isUpper
+ ,isLower: isLower
+ ,isDigit: isDigit
+ ,isOctDigit: isOctDigit
+ ,isHexDigit: isHexDigit
+ ,toUpper: toUpper
+ ,toLower: toLower
+ ,toLocaleUpper: toLocaleUpper
+ ,toLocaleLower: toLocaleLower
+ ,toCode: toCode
+ ,fromCode: fromCode};
+ return _elm.Char.values;
+};
+Elm.Color = Elm.Color || {};
+Elm.Color.make = function (_elm) {
+ "use strict";
+ _elm.Color = _elm.Color || {};
+ if (_elm.Color.values)
+ return _elm.Color.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Color",
+ $Basics = Elm.Basics.make(_elm);
+ var Radial = F5(function (a,
+ b,
+ c,
+ d,
+ e) {
+ return {ctor: "Radial"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d
+ ,_4: e};
+ });
+ var radial = Radial;
+ var Linear = F3(function (a,
+ b,
+ c) {
+ return {ctor: "Linear"
+ ,_0: a
+ ,_1: b
+ ,_2: c};
+ });
+ var linear = Linear;
+ var fmod = F2(function (f,n) {
+ var integer = $Basics.floor(f);
+ return $Basics.toFloat(A2($Basics._op["%"],
+ integer,
+ n)) + f - $Basics.toFloat(integer);
+ });
+ var rgbToHsl = F3(function (red,
+ green,
+ blue) {
+ var b = $Basics.toFloat(blue) / 255;
+ var g = $Basics.toFloat(green) / 255;
+ var r = $Basics.toFloat(red) / 255;
+ var cMax = A2($Basics.max,
+ A2($Basics.max,r,g),
+ b);
+ var cMin = A2($Basics.min,
+ A2($Basics.min,r,g),
+ b);
+ var c = cMax - cMin;
+ var lightness = (cMax + cMin) / 2;
+ var saturation = _U.eq(lightness,
+ 0) ? 0 : c / (1 - $Basics.abs(2 * lightness - 1));
+ var hue = $Basics.degrees(60) * (_U.eq(cMax,
+ r) ? A2(fmod,
+ (g - b) / c,
+ 6) : _U.eq(cMax,
+ g) ? (b - r) / c + 2 : _U.eq(cMax,
+ b) ? (r - g) / c + 4 : _U.badIf($moduleName,
+ "between lines 150 and 152"));
+ return {ctor: "_Tuple3"
+ ,_0: hue
+ ,_1: saturation
+ ,_2: lightness};
+ });
+ var hslToRgb = F3(function (hue,
+ saturation,
+ lightness) {
+ var hue$ = hue / $Basics.degrees(60);
+ var chroma = (1 - $Basics.abs(2 * lightness - 1)) * saturation;
+ var x = chroma * (1 - $Basics.abs(A2(fmod,
+ hue$,
+ 2) - 1));
+ var $ = _U.cmp(hue$,
+ 0) < 0 ? {ctor: "_Tuple3"
+ ,_0: 0
+ ,_1: 0
+ ,_2: 0} : _U.cmp(hue$,
+ 1) < 0 ? {ctor: "_Tuple3"
+ ,_0: chroma
+ ,_1: x
+ ,_2: 0} : _U.cmp(hue$,
+ 2) < 0 ? {ctor: "_Tuple3"
+ ,_0: x
+ ,_1: chroma
+ ,_2: 0} : _U.cmp(hue$,
+ 3) < 0 ? {ctor: "_Tuple3"
+ ,_0: 0
+ ,_1: chroma
+ ,_2: x} : _U.cmp(hue$,
+ 4) < 0 ? {ctor: "_Tuple3"
+ ,_0: 0
+ ,_1: x
+ ,_2: chroma} : _U.cmp(hue$,
+ 5) < 0 ? {ctor: "_Tuple3"
+ ,_0: x
+ ,_1: 0
+ ,_2: chroma} : _U.cmp(hue$,
+ 6) < 0 ? {ctor: "_Tuple3"
+ ,_0: chroma
+ ,_1: 0
+ ,_2: x} : {ctor: "_Tuple3"
+ ,_0: 0
+ ,_1: 0
+ ,_2: 0},
+ r = $._0,
+ g = $._1,
+ b = $._2;
+ var m = lightness - chroma / 2;
+ return {ctor: "_Tuple3"
+ ,_0: r + m
+ ,_1: g + m
+ ,_2: b + m};
+ });
+ var toRgb = function (color) {
+ switch (color.ctor)
+ {case "HSLA":
+ var $ = A3(hslToRgb,
+ color._0,
+ color._1,
+ color._2),
+ r = $._0,
+ g = $._1,
+ b = $._2;
+ return {_: {}
+ ,alpha: color._3
+ ,blue: $Basics.round(255 * b)
+ ,green: $Basics.round(255 * g)
+ ,red: $Basics.round(255 * r)};
+ case "RGBA": return {_: {}
+ ,alpha: color._3
+ ,blue: color._2
+ ,green: color._1
+ ,red: color._0};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var toHsl = function (color) {
+ switch (color.ctor)
+ {case "HSLA": return {_: {}
+ ,alpha: color._3
+ ,hue: color._0
+ ,lightness: color._2
+ ,saturation: color._1};
+ case "RGBA":
+ var $ = A3(rgbToHsl,
+ color._0,
+ color._1,
+ color._2),
+ h = $._0,
+ s = $._1,
+ l = $._2;
+ return {_: {}
+ ,alpha: color._3
+ ,hue: h
+ ,lightness: l
+ ,saturation: s};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var HSLA = F4(function (a,
+ b,
+ c,
+ d) {
+ return {ctor: "HSLA"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d};
+ });
+ var hsla = F4(function (hue,
+ saturation,
+ lightness,
+ alpha) {
+ return A4(HSLA,
+ hue - $Basics.turns($Basics.toFloat($Basics.floor(hue / (2 * $Basics.pi)))),
+ saturation,
+ lightness,
+ alpha);
+ });
+ var hsl = F3(function (hue,
+ saturation,
+ lightness) {
+ return A4(hsla,
+ hue,
+ saturation,
+ lightness,
+ 1);
+ });
+ var complement = function (color) {
+ switch (color.ctor)
+ {case "HSLA": return A4(hsla,
+ color._0 + $Basics.degrees(180),
+ color._1,
+ color._2,
+ color._3);
+ case "RGBA":
+ var $ = A3(rgbToHsl,
+ color._0,
+ color._1,
+ color._2),
+ h = $._0,
+ s = $._1,
+ l = $._2;
+ return A4(hsla,
+ h + $Basics.degrees(180),
+ s,
+ l,
+ color._3);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var grayscale = function (p) {
+ return A4(HSLA,0,0,1 - p,1);
+ };
+ var greyscale = function (p) {
+ return A4(HSLA,0,0,1 - p,1);
+ };
+ var RGBA = F4(function (a,
+ b,
+ c,
+ d) {
+ return {ctor: "RGBA"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d};
+ });
+ var rgba = RGBA;
+ var rgb = F3(function (r,g,b) {
+ return A4(RGBA,r,g,b,1);
+ });
+ var lightRed = A4(RGBA,
+ 239,
+ 41,
+ 41,
+ 1);
+ var red = A4(RGBA,204,0,0,1);
+ var darkRed = A4(RGBA,
+ 164,
+ 0,
+ 0,
+ 1);
+ var lightOrange = A4(RGBA,
+ 252,
+ 175,
+ 62,
+ 1);
+ var orange = A4(RGBA,
+ 245,
+ 121,
+ 0,
+ 1);
+ var darkOrange = A4(RGBA,
+ 206,
+ 92,
+ 0,
+ 1);
+ var lightYellow = A4(RGBA,
+ 255,
+ 233,
+ 79,
+ 1);
+ var yellow = A4(RGBA,
+ 237,
+ 212,
+ 0,
+ 1);
+ var darkYellow = A4(RGBA,
+ 196,
+ 160,
+ 0,
+ 1);
+ var lightGreen = A4(RGBA,
+ 138,
+ 226,
+ 52,
+ 1);
+ var green = A4(RGBA,
+ 115,
+ 210,
+ 22,
+ 1);
+ var darkGreen = A4(RGBA,
+ 78,
+ 154,
+ 6,
+ 1);
+ var lightBlue = A4(RGBA,
+ 114,
+ 159,
+ 207,
+ 1);
+ var blue = A4(RGBA,
+ 52,
+ 101,
+ 164,
+ 1);
+ var darkBlue = A4(RGBA,
+ 32,
+ 74,
+ 135,
+ 1);
+ var lightPurple = A4(RGBA,
+ 173,
+ 127,
+ 168,
+ 1);
+ var purple = A4(RGBA,
+ 117,
+ 80,
+ 123,
+ 1);
+ var darkPurple = A4(RGBA,
+ 92,
+ 53,
+ 102,
+ 1);
+ var lightBrown = A4(RGBA,
+ 233,
+ 185,
+ 110,
+ 1);
+ var brown = A4(RGBA,
+ 193,
+ 125,
+ 17,
+ 1);
+ var darkBrown = A4(RGBA,
+ 143,
+ 89,
+ 2,
+ 1);
+ var black = A4(RGBA,0,0,0,1);
+ var white = A4(RGBA,
+ 255,
+ 255,
+ 255,
+ 1);
+ var lightGrey = A4(RGBA,
+ 238,
+ 238,
+ 236,
+ 1);
+ var grey = A4(RGBA,
+ 211,
+ 215,
+ 207,
+ 1);
+ var darkGrey = A4(RGBA,
+ 186,
+ 189,
+ 182,
+ 1);
+ var lightGray = A4(RGBA,
+ 238,
+ 238,
+ 236,
+ 1);
+ var gray = A4(RGBA,
+ 211,
+ 215,
+ 207,
+ 1);
+ var darkGray = A4(RGBA,
+ 186,
+ 189,
+ 182,
+ 1);
+ var lightCharcoal = A4(RGBA,
+ 136,
+ 138,
+ 133,
+ 1);
+ var charcoal = A4(RGBA,
+ 85,
+ 87,
+ 83,
+ 1);
+ var darkCharcoal = A4(RGBA,
+ 46,
+ 52,
+ 54,
+ 1);
+ _elm.Color.values = {_op: _op
+ ,rgb: rgb
+ ,rgba: rgba
+ ,hsl: hsl
+ ,hsla: hsla
+ ,greyscale: greyscale
+ ,grayscale: grayscale
+ ,complement: complement
+ ,linear: linear
+ ,radial: radial
+ ,toRgb: toRgb
+ ,toHsl: toHsl
+ ,red: red
+ ,orange: orange
+ ,yellow: yellow
+ ,green: green
+ ,blue: blue
+ ,purple: purple
+ ,brown: brown
+ ,lightRed: lightRed
+ ,lightOrange: lightOrange
+ ,lightYellow: lightYellow
+ ,lightGreen: lightGreen
+ ,lightBlue: lightBlue
+ ,lightPurple: lightPurple
+ ,lightBrown: lightBrown
+ ,darkRed: darkRed
+ ,darkOrange: darkOrange
+ ,darkYellow: darkYellow
+ ,darkGreen: darkGreen
+ ,darkBlue: darkBlue
+ ,darkPurple: darkPurple
+ ,darkBrown: darkBrown
+ ,white: white
+ ,lightGrey: lightGrey
+ ,grey: grey
+ ,darkGrey: darkGrey
+ ,lightCharcoal: lightCharcoal
+ ,charcoal: charcoal
+ ,darkCharcoal: darkCharcoal
+ ,black: black
+ ,lightGray: lightGray
+ ,gray: gray
+ ,darkGray: darkGray};
+ return _elm.Color.values;
+};
+Elm.Date = Elm.Date || {};
+Elm.Date.make = function (_elm) {
+ "use strict";
+ _elm.Date = _elm.Date || {};
+ if (_elm.Date.values)
+ return _elm.Date.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Date",
+ $Native$Date = Elm.Native.Date.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Time = Elm.Time.make(_elm);
+ var millisecond = $Native$Date.millisecond;
+ var second = $Native$Date.second;
+ var minute = $Native$Date.minute;
+ var hour = $Native$Date.hour;
+ var dayOfWeek = $Native$Date.dayOfWeek;
+ var day = $Native$Date.day;
+ var month = $Native$Date.month;
+ var year = $Native$Date.year;
+ var fromTime = $Native$Date.fromTime;
+ var toTime = $Native$Date.toTime;
+ var fromString = $Native$Date.read;
+ var Dec = {ctor: "Dec"};
+ var Nov = {ctor: "Nov"};
+ var Oct = {ctor: "Oct"};
+ var Sep = {ctor: "Sep"};
+ var Aug = {ctor: "Aug"};
+ var Jul = {ctor: "Jul"};
+ var Jun = {ctor: "Jun"};
+ var May = {ctor: "May"};
+ var Apr = {ctor: "Apr"};
+ var Mar = {ctor: "Mar"};
+ var Feb = {ctor: "Feb"};
+ var Jan = {ctor: "Jan"};
+ var Sun = {ctor: "Sun"};
+ var Sat = {ctor: "Sat"};
+ var Fri = {ctor: "Fri"};
+ var Thu = {ctor: "Thu"};
+ var Wed = {ctor: "Wed"};
+ var Tue = {ctor: "Tue"};
+ var Mon = {ctor: "Mon"};
+ var Date = {ctor: "Date"};
+ _elm.Date.values = {_op: _op
+ ,fromString: fromString
+ ,toTime: toTime
+ ,fromTime: fromTime
+ ,year: year
+ ,month: month
+ ,day: day
+ ,dayOfWeek: dayOfWeek
+ ,hour: hour
+ ,minute: minute
+ ,second: second
+ ,millisecond: millisecond
+ ,Jan: Jan
+ ,Feb: Feb
+ ,Mar: Mar
+ ,Apr: Apr
+ ,May: May
+ ,Jun: Jun
+ ,Jul: Jul
+ ,Aug: Aug
+ ,Sep: Sep
+ ,Oct: Oct
+ ,Nov: Nov
+ ,Dec: Dec
+ ,Mon: Mon
+ ,Tue: Tue
+ ,Wed: Wed
+ ,Thu: Thu
+ ,Fri: Fri
+ ,Sat: Sat
+ ,Sun: Sun};
+ return _elm.Date.values;
+};
+Elm.Debug = Elm.Debug || {};
+Elm.Debug.make = function (_elm) {
+ "use strict";
+ _elm.Debug = _elm.Debug || {};
+ if (_elm.Debug.values)
+ return _elm.Debug.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Debug",
+ $Graphics$Collage = Elm.Graphics.Collage.make(_elm),
+ $Native$Debug = Elm.Native.Debug.make(_elm);
+ var trace = $Native$Debug.tracePath;
+ var watchSummary = $Native$Debug.watchSummary;
+ var watch = $Native$Debug.watch;
+ var crash = $Native$Debug.crash;
+ var log = $Native$Debug.log;
+ _elm.Debug.values = {_op: _op
+ ,log: log
+ ,crash: crash
+ ,watch: watch
+ ,watchSummary: watchSummary
+ ,trace: trace};
+ return _elm.Debug.values;
+};
+Elm.Dict = Elm.Dict || {};
+Elm.Dict.make = function (_elm) {
+ "use strict";
+ _elm.Dict = _elm.Dict || {};
+ if (_elm.Dict.values)
+ return _elm.Dict.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Dict",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Debug = Elm.Native.Debug.make(_elm),
+ $String = Elm.String.make(_elm);
+ var foldr = F3(function (f,
+ acc,
+ t) {
+ _v0: while (true) {
+ switch (t.ctor)
+ {case "RBEmpty":
+ switch (t._0.ctor)
+ {case "LBlack": return acc;}
+ break;
+ case "RBNode": var _v8 = f,
+ _v9 = A3(f,
+ t._1,
+ t._2,
+ A3(foldr,f,acc,t._4)),
+ _v10 = t._3;
+ f = _v8;
+ acc = _v9;
+ t = _v10;
+ continue _v0;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ });
+ var keys = function (dict) {
+ return A3(foldr,
+ F3(function (key,
+ value,
+ keyList) {
+ return A2($List._op["::"],
+ key,
+ keyList);
+ }),
+ _L.fromArray([]),
+ dict);
+ };
+ var values = function (dict) {
+ return A3(foldr,
+ F3(function (key,
+ value,
+ valueList) {
+ return A2($List._op["::"],
+ value,
+ valueList);
+ }),
+ _L.fromArray([]),
+ dict);
+ };
+ var toList = function (dict) {
+ return A3(foldr,
+ F3(function (key,value,list) {
+ return A2($List._op["::"],
+ {ctor: "_Tuple2"
+ ,_0: key
+ ,_1: value},
+ list);
+ }),
+ _L.fromArray([]),
+ dict);
+ };
+ var foldl = F3(function (f,
+ acc,
+ dict) {
+ _v11: while (true) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBlack": return acc;}
+ break;
+ case "RBNode": var _v19 = f,
+ _v20 = A3(f,
+ dict._1,
+ dict._2,
+ A3(foldl,f,acc,dict._3)),
+ _v21 = dict._4;
+ f = _v19;
+ acc = _v20;
+ dict = _v21;
+ continue _v11;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ });
+ var isBBlack = function (dict) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBBlack": return true;}
+ break;
+ case "RBNode":
+ switch (dict._0.ctor)
+ {case "BBlack": return true;}
+ break;}
+ return false;
+ };
+ var showFlag = function (f) {
+ switch (f.ctor)
+ {case "Insert": return "Insert";
+ case "Remove": return "Remove";
+ case "Same": return "Same";}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var Same = {ctor: "Same"};
+ var Remove = {ctor: "Remove"};
+ var Insert = {ctor: "Insert"};
+ var get = F2(function (targetKey,
+ dict) {
+ _v30: while (true) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBlack":
+ return $Maybe.Nothing;}
+ break;
+ case "RBNode":
+ var _v38 = A2($Basics.compare,
+ targetKey,
+ dict._1);
+ switch (_v38.ctor)
+ {case "EQ":
+ return $Maybe.Just(dict._2);
+ case "GT": var _v39 = targetKey,
+ _v40 = dict._4;
+ targetKey = _v39;
+ dict = _v40;
+ continue _v30;
+ case "LT": var _v41 = targetKey,
+ _v42 = dict._3;
+ targetKey = _v41;
+ dict = _v42;
+ continue _v30;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ });
+ var member = F2(function (key,
+ dict) {
+ var _v43 = A2(get,key,dict);
+ switch (_v43.ctor)
+ {case "Just": return true;
+ case "Nothing": return false;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var max = function (dict) {
+ _v45: while (true) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ return $Native$Debug.crash("(max Empty) is not defined");
+ case "RBNode":
+ switch (dict._4.ctor)
+ {case "RBEmpty":
+ return {ctor: "_Tuple2"
+ ,_0: dict._1
+ ,_1: dict._2};}
+ var _v54 = dict._4;
+ dict = _v54;
+ continue _v45;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ };
+ var min = function (dict) {
+ _v55: while (true) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBlack":
+ return $Native$Debug.crash("(min Empty) is not defined");}
+ break;
+ case "RBNode":
+ switch (dict._3.ctor)
+ {case "RBEmpty":
+ switch (dict._3._0.ctor)
+ {case "LBlack":
+ return {ctor: "_Tuple2"
+ ,_0: dict._1
+ ,_1: dict._2};}
+ break;}
+ var _v64 = dict._3;
+ dict = _v64;
+ continue _v55;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ };
+ var RBEmpty = function (a) {
+ return {ctor: "RBEmpty"
+ ,_0: a};
+ };
+ var RBNode = F5(function (a,
+ b,
+ c,
+ d,
+ e) {
+ return {ctor: "RBNode"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d
+ ,_4: e};
+ });
+ var showLColor = function (color) {
+ switch (color.ctor)
+ {case "LBBlack":
+ return "LBBlack";
+ case "LBlack": return "LBlack";}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var LBBlack = {ctor: "LBBlack"};
+ var LBlack = {ctor: "LBlack"};
+ var empty = RBEmpty(LBlack);
+ var isEmpty = function (dict) {
+ return _U.eq(dict,empty);
+ };
+ var map = F2(function (f,dict) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBlack":
+ return RBEmpty(LBlack);}
+ break;
+ case "RBNode": return A5(RBNode,
+ dict._0,
+ dict._1,
+ A2(f,dict._1,dict._2),
+ A2(map,f,dict._3),
+ A2(map,f,dict._4));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var showNColor = function (c) {
+ switch (c.ctor)
+ {case "BBlack": return "BBlack";
+ case "Black": return "Black";
+ case "NBlack": return "NBlack";
+ case "Red": return "Red";}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var reportRemBug = F4(function (msg,
+ c,
+ lgot,
+ rgot) {
+ return $Native$Debug.crash($String.concat(_L.fromArray(["Internal red-black tree invariant violated, expected "
+ ,msg
+ ," and got "
+ ,showNColor(c)
+ ,"/"
+ ,lgot
+ ,"/"
+ ,rgot
+ ,"\nPlease report this bug to <https://github.com/elm-lang/Elm/issues>"])));
+ });
+ var NBlack = {ctor: "NBlack"};
+ var BBlack = {ctor: "BBlack"};
+ var Black = {ctor: "Black"};
+ var ensureBlackRoot = function (dict) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBlack": return dict;}
+ break;
+ case "RBNode":
+ switch (dict._0.ctor)
+ {case "Black": return dict;
+ case "Red": return A5(RBNode,
+ Black,
+ dict._1,
+ dict._2,
+ dict._3,
+ dict._4);}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var blackish = function (t) {
+ switch (t.ctor)
+ {case "RBEmpty": return true;
+ case "RBNode":
+ return _U.eq(t._0,
+ Black) || _U.eq(t._0,BBlack);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var blacken = function (t) {
+ switch (t.ctor)
+ {case "RBEmpty":
+ return RBEmpty(LBlack);
+ case "RBNode": return A5(RBNode,
+ Black,
+ t._1,
+ t._2,
+ t._3,
+ t._4);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var Red = {ctor: "Red"};
+ var moreBlack = function (color) {
+ switch (color.ctor)
+ {case "BBlack":
+ return $Native$Debug.crash("Can\'t make a double black node more black!");
+ case "Black": return BBlack;
+ case "NBlack": return Red;
+ case "Red": return Black;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var lessBlack = function (color) {
+ switch (color.ctor)
+ {case "BBlack": return Black;
+ case "Black": return Red;
+ case "NBlack":
+ return $Native$Debug.crash("Can\'t make a negative black node less black!");
+ case "Red": return NBlack;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var lessBlackTree = function (dict) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBBlack":
+ return RBEmpty(LBlack);}
+ break;
+ case "RBNode": return A5(RBNode,
+ lessBlack(dict._0),
+ dict._1,
+ dict._2,
+ dict._3,
+ dict._4);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var redden = function (t) {
+ switch (t.ctor)
+ {case "RBEmpty":
+ return $Native$Debug.crash("can\'t make a Leaf red");
+ case "RBNode": return A5(RBNode,
+ Red,
+ t._1,
+ t._2,
+ t._3,
+ t._4);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var balance_node = function (t) {
+ var assemble = function (col) {
+ return function (xk) {
+ return function (xv) {
+ return function (yk) {
+ return function (yv) {
+ return function (zk) {
+ return function (zv) {
+ return function (a) {
+ return function (b) {
+ return function (c) {
+ return function (d) {
+ return A5(RBNode,
+ lessBlack(col),
+ yk,
+ yv,
+ A5(RBNode,Black,xk,xv,a,b),
+ A5(RBNode,Black,zk,zv,c,d));
+ };
+ };
+ };
+ };
+ };
+ };
+ };
+ };
+ };
+ };
+ };
+ if (blackish(t)) {
+ switch (t.ctor)
+ {case "RBNode":
+ switch (t._3.ctor)
+ {case "RBNode":
+ switch (t._3._0.ctor)
+ {case "Red":
+ switch (t._3._3.ctor)
+ {case "RBNode":
+ switch (t._3._3._0.ctor)
+ {case "Red":
+ return assemble(t._0)(t._3._3._1)(t._3._3._2)(t._3._1)(t._3._2)(t._1)(t._2)(t._3._3._3)(t._3._3._4)(t._3._4)(t._4);}
+ break;}
+ switch (t._3._4.ctor)
+ {case "RBNode":
+ switch (t._3._4._0.ctor)
+ {case "Red":
+ return assemble(t._0)(t._3._1)(t._3._2)(t._3._4._1)(t._3._4._2)(t._1)(t._2)(t._3._3)(t._3._4._3)(t._3._4._4)(t._4);}
+ break;}
+ break;}
+ break;}
+ switch (t._4.ctor)
+ {case "RBNode":
+ switch (t._4._0.ctor)
+ {case "Red":
+ switch (t._4._3.ctor)
+ {case "RBNode":
+ switch (t._4._3._0.ctor)
+ {case "Red":
+ return assemble(t._0)(t._1)(t._2)(t._4._3._1)(t._4._3._2)(t._4._1)(t._4._2)(t._3)(t._4._3._3)(t._4._3._4)(t._4._4);}
+ break;}
+ switch (t._4._4.ctor)
+ {case "RBNode":
+ switch (t._4._4._0.ctor)
+ {case "Red":
+ return assemble(t._0)(t._1)(t._2)(t._4._1)(t._4._2)(t._4._4._1)(t._4._4._2)(t._3)(t._4._3)(t._4._4._3)(t._4._4._4);}
+ break;}
+ break;}
+ break;}
+ switch (t._0.ctor)
+ {case "BBlack":
+ switch (t._4.ctor)
+ {case "RBNode":
+ switch (t._4._0.ctor)
+ {case "NBlack":
+ switch (t._4._3.ctor)
+ {case "RBNode":
+ switch (t._4._3._0.ctor)
+ {case "Black":
+ switch (t._4._4.ctor)
+ {case "RBNode":
+ switch (t._4._4._0.ctor)
+ {case "Black": return A5(RBNode,
+ Black,
+ t._4._3._1,
+ t._4._3._2,
+ A5(RBNode,
+ Black,
+ t._1,
+ t._2,
+ t._3,
+ t._4._3._3),
+ A5(balance,
+ Black,
+ t._4._1,
+ t._4._2,
+ t._4._3._4,
+ redden(t._4._4)));}
+ break;}
+ return t;}
+ break;}
+ break;}
+ break;}
+ switch (t._3.ctor)
+ {case "RBNode":
+ switch (t._3._0.ctor)
+ {case "NBlack":
+ switch (t._3._4.ctor)
+ {case "RBNode":
+ switch (t._3._4._0.ctor)
+ {case "Black":
+ switch (t._3._3.ctor)
+ {case "RBNode":
+ switch (t._3._3._0.ctor)
+ {case "Black": return A5(RBNode,
+ Black,
+ t._3._4._1,
+ t._3._4._2,
+ A5(balance,
+ Black,
+ t._3._1,
+ t._3._2,
+ redden(t._3._3),
+ t._3._4._3),
+ A5(RBNode,
+ Black,
+ t._1,
+ t._2,
+ t._3._4._4,
+ t._4));}
+ break;}
+ return t;}
+ break;}
+ break;}
+ break;}
+ break;}
+ break;}
+ return t;
+ } else return t;
+ };
+ var balance = F5(function (c,
+ k,
+ v,
+ l,
+ r) {
+ return balance_node(A5(RBNode,
+ c,
+ k,
+ v,
+ l,
+ r));
+ });
+ var bubble = F5(function (c,
+ k,
+ v,
+ l,
+ r) {
+ return isBBlack(l) || isBBlack(r) ? A5(balance,
+ moreBlack(c),
+ k,
+ v,
+ lessBlackTree(l),
+ lessBlackTree(r)) : A5(RBNode,
+ c,
+ k,
+ v,
+ l,
+ r);
+ });
+ var remove_max = F5(function (c,
+ k,
+ v,
+ l,
+ r) {
+ switch (r.ctor)
+ {case "RBEmpty": return A3(rem,
+ c,
+ l,
+ r);
+ case "RBNode": return A5(bubble,
+ c,
+ k,
+ v,
+ l,
+ A5(remove_max,
+ r._0,
+ r._1,
+ r._2,
+ r._3,
+ r._4));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var rem = F3(function (c,l,r) {
+ var _v186 = {ctor: "_Tuple2"
+ ,_0: l
+ ,_1: r};
+ switch (_v186.ctor)
+ {case "_Tuple2":
+ switch (_v186._0.ctor)
+ {case "RBEmpty":
+ switch (_v186._1.ctor)
+ {case "RBEmpty": switch (c.ctor)
+ {case "Black":
+ return RBEmpty(LBBlack);
+ case "Red":
+ return RBEmpty(LBlack);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "RBNode":
+ var _v208 = {ctor: "_Tuple3"
+ ,_0: c
+ ,_1: _v186._0._0
+ ,_2: _v186._1._0};
+ switch (_v208.ctor)
+ {case "_Tuple3":
+ switch (_v208._0.ctor)
+ {case "Black":
+ switch (_v208._1.ctor)
+ {case "LBlack":
+ switch (_v208._2.ctor)
+ {case "Red": return A5(RBNode,
+ Black,
+ _v186._1._1,
+ _v186._1._2,
+ _v186._1._3,
+ _v186._1._4);}
+ break;}
+ break;}
+ break;}
+ return A4(reportRemBug,
+ "Black/LBlack/Red",
+ c,
+ showLColor(_v186._0._0),
+ showNColor(_v186._1._0));}
+ break;
+ case "RBNode":
+ switch (_v186._1.ctor)
+ {case "RBEmpty":
+ var _v212 = {ctor: "_Tuple3"
+ ,_0: c
+ ,_1: _v186._0._0
+ ,_2: _v186._1._0};
+ switch (_v212.ctor)
+ {case "_Tuple3":
+ switch (_v212._0.ctor)
+ {case "Black":
+ switch (_v212._1.ctor)
+ {case "Red":
+ switch (_v212._2.ctor)
+ {case "LBlack":
+ return A5(RBNode,
+ Black,
+ _v186._0._1,
+ _v186._0._2,
+ _v186._0._3,
+ _v186._0._4);}
+ break;}
+ break;}
+ break;}
+ return A4(reportRemBug,
+ "Black/Red/LBlack",
+ c,
+ showNColor(_v186._0._0),
+ showLColor(_v186._1._0));
+ case "RBNode":
+ var l$ = A5(remove_max,
+ _v186._0._0,
+ _v186._0._1,
+ _v186._0._2,
+ _v186._0._3,
+ _v186._0._4);
+ var r = A5(RBNode,
+ _v186._1._0,
+ _v186._1._1,
+ _v186._1._2,
+ _v186._1._3,
+ _v186._1._4);
+ var l = A5(RBNode,
+ _v186._0._0,
+ _v186._0._1,
+ _v186._0._2,
+ _v186._0._3,
+ _v186._0._4);
+ var $ = max(l),
+ k = $._0,
+ v = $._1;
+ return A5(bubble,c,k,v,l$,r);}
+ break;}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var update = F3(function (k,
+ alter,
+ dict) {
+ var up = function (dict) {
+ switch (dict.ctor)
+ {case "RBEmpty":
+ switch (dict._0.ctor)
+ {case "LBlack":
+ var _v223 = alter($Maybe.Nothing);
+ switch (_v223.ctor)
+ {case "Just":
+ return {ctor: "_Tuple2"
+ ,_0: Insert
+ ,_1: A5(RBNode,
+ Red,
+ k,
+ _v223._0,
+ empty,
+ empty)};
+ case "Nothing":
+ return {ctor: "_Tuple2"
+ ,_0: Same
+ ,_1: empty};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");}
+ break;
+ case "RBNode":
+ var _v225 = A2($Basics.compare,
+ k,
+ dict._1);
+ switch (_v225.ctor)
+ {case "EQ":
+ var _v226 = alter($Maybe.Just(dict._2));
+ switch (_v226.ctor)
+ {case "Just":
+ return {ctor: "_Tuple2"
+ ,_0: Same
+ ,_1: A5(RBNode,
+ dict._0,
+ dict._1,
+ _v226._0,
+ dict._3,
+ dict._4)};
+ case "Nothing":
+ return {ctor: "_Tuple2"
+ ,_0: Remove
+ ,_1: A3(rem,
+ dict._0,
+ dict._3,
+ dict._4)};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "GT": var $ = up(dict._4),
+ flag = $._0,
+ newRight = $._1;
+ switch (flag.ctor)
+ {case "Insert":
+ return {ctor: "_Tuple2"
+ ,_0: Insert
+ ,_1: A5(balance,
+ dict._0,
+ dict._1,
+ dict._2,
+ dict._3,
+ newRight)};
+ case "Remove":
+ return {ctor: "_Tuple2"
+ ,_0: Remove
+ ,_1: A5(bubble,
+ dict._0,
+ dict._1,
+ dict._2,
+ dict._3,
+ newRight)};
+ case "Same":
+ return {ctor: "_Tuple2"
+ ,_0: Same
+ ,_1: A5(RBNode,
+ dict._0,
+ dict._1,
+ dict._2,
+ dict._3,
+ newRight)};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "LT": var $ = up(dict._3),
+ flag = $._0,
+ newLeft = $._1;
+ switch (flag.ctor)
+ {case "Insert":
+ return {ctor: "_Tuple2"
+ ,_0: Insert
+ ,_1: A5(balance,
+ dict._0,
+ dict._1,
+ dict._2,
+ newLeft,
+ dict._4)};
+ case "Remove":
+ return {ctor: "_Tuple2"
+ ,_0: Remove
+ ,_1: A5(bubble,
+ dict._0,
+ dict._1,
+ dict._2,
+ newLeft,
+ dict._4)};
+ case "Same":
+ return {ctor: "_Tuple2"
+ ,_0: Same
+ ,_1: A5(RBNode,
+ dict._0,
+ dict._1,
+ dict._2,
+ newLeft,
+ dict._4)};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var $ = up(dict),
+ flag = $._0,
+ updatedDict = $._1;
+ switch (flag.ctor)
+ {case "Insert":
+ return ensureBlackRoot(updatedDict);
+ case "Remove":
+ return blacken(updatedDict);
+ case "Same":
+ return updatedDict;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var insert = F3(function (key,
+ value,
+ dict) {
+ return A3(update,
+ key,
+ $Basics.always($Maybe.Just(value)),
+ dict);
+ });
+ var singleton = F2(function (key,
+ value) {
+ return A3(insert,
+ key,
+ value,
+ empty);
+ });
+ var union = F2(function (t1,
+ t2) {
+ return A3(foldl,
+ insert,
+ t2,
+ t1);
+ });
+ var fromList = function (assocs) {
+ return A3($List.foldl,
+ F2(function (_v231,dict) {
+ var $ = _v231,
+ key = $._0,
+ value = $._1;
+ return A3(insert,
+ key,
+ value,
+ dict);
+ }),
+ empty,
+ assocs);
+ };
+ var filter = F2(function (predicate,
+ dictionary) {
+ var add = F3(function (key,
+ value,
+ dict) {
+ return A2(predicate,
+ key,
+ value) ? A3(insert,
+ key,
+ value,
+ dict) : dict;
+ });
+ return A3(foldl,
+ add,
+ empty,
+ dictionary);
+ });
+ var intersect = F2(function (t1,
+ t2) {
+ return A2(filter,
+ F2(function (k,_v232) {
+ var _ = _v232;
+ return A2(member,k,t2);
+ }),
+ t1);
+ });
+ var partition = F2(function (predicate,
+ dict) {
+ var add = F3(function (key,
+ value,
+ _v233) {
+ var $ = _v233,
+ t1 = $._0,
+ t2 = $._1;
+ return A2(predicate,
+ key,
+ value) ? {ctor: "_Tuple2"
+ ,_0: A3(insert,key,value,t1)
+ ,_1: t2} : {ctor: "_Tuple2"
+ ,_0: t1
+ ,_1: A3(insert,key,value,t2)};
+ });
+ return A3(foldl,
+ add,
+ {ctor: "_Tuple2"
+ ,_0: empty
+ ,_1: empty},
+ dict);
+ });
+ var remove = F2(function (key,
+ dict) {
+ return A3(update,
+ key,
+ $Basics.always($Maybe.Nothing),
+ dict);
+ });
+ var diff = F2(function (t1,t2) {
+ return A3(foldl,
+ F3(function (k,v,t) {
+ return A2(remove,k,t);
+ }),
+ t1,
+ t2);
+ });
+ _elm.Dict.values = {_op: _op
+ ,empty: empty
+ ,singleton: singleton
+ ,insert: insert
+ ,update: update
+ ,isEmpty: isEmpty
+ ,get: get
+ ,remove: remove
+ ,member: member
+ ,filter: filter
+ ,partition: partition
+ ,foldl: foldl
+ ,foldr: foldr
+ ,map: map
+ ,union: union
+ ,intersect: intersect
+ ,diff: diff
+ ,keys: keys
+ ,values: values
+ ,toList: toList
+ ,fromList: fromList};
+ return _elm.Dict.values;
+};
+Elm.Graphics = Elm.Graphics || {};
+Elm.Graphics.Collage = Elm.Graphics.Collage || {};
+Elm.Graphics.Collage.make = function (_elm) {
+ "use strict";
+ _elm.Graphics = _elm.Graphics || {};
+ _elm.Graphics.Collage = _elm.Graphics.Collage || {};
+ if (_elm.Graphics.Collage.values)
+ return _elm.Graphics.Collage.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Graphics.Collage",
+ $Basics = Elm.Basics.make(_elm),
+ $Color = Elm.Color.make(_elm),
+ $Graphics$Element = Elm.Graphics.Element.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Native$Graphics$Collage = Elm.Native.Graphics.Collage.make(_elm),
+ $Text = Elm.Text.make(_elm),
+ $Transform2D = Elm.Transform2D.make(_elm);
+ var ngon = F2(function (n,r) {
+ var m = $Basics.toFloat(n);
+ var t = 2 * $Basics.pi / m;
+ var f = function (i) {
+ return {ctor: "_Tuple2"
+ ,_0: r * $Basics.cos(t * i)
+ ,_1: r * $Basics.sin(t * i)};
+ };
+ return A2($List.map,
+ f,
+ _L.range(0,m - 1));
+ });
+ var oval = F2(function (w,h) {
+ var hh = h / 2;
+ var hw = w / 2;
+ var n = 50;
+ var t = 2 * $Basics.pi / n;
+ var f = function (i) {
+ return {ctor: "_Tuple2"
+ ,_0: hw * $Basics.cos(t * i)
+ ,_1: hh * $Basics.sin(t * i)};
+ };
+ return A2($List.map,
+ f,
+ _L.range(0,n - 1));
+ });
+ var circle = function (r) {
+ return A2(oval,2 * r,2 * r);
+ };
+ var rect = F2(function (w,h) {
+ var hh = h / 2;
+ var hw = w / 2;
+ return _L.fromArray([{ctor: "_Tuple2"
+ ,_0: 0 - hw
+ ,_1: 0 - hh}
+ ,{ctor: "_Tuple2"
+ ,_0: 0 - hw
+ ,_1: hh}
+ ,{ctor: "_Tuple2",_0: hw,_1: hh}
+ ,{ctor: "_Tuple2"
+ ,_0: hw
+ ,_1: 0 - hh}]);
+ });
+ var square = function (n) {
+ return A2(rect,n,n);
+ };
+ var polygon = function (points) {
+ return points;
+ };
+ var segment = F2(function (p1,
+ p2) {
+ return _L.fromArray([p1,p2]);
+ });
+ var path = function (ps) {
+ return ps;
+ };
+ var collage = $Native$Graphics$Collage.collage;
+ var alpha = F2(function (a,f) {
+ return _U.replace([["alpha"
+ ,a]],
+ f);
+ });
+ var rotate = F2(function (t,f) {
+ return _U.replace([["theta"
+ ,f.theta + t]],
+ f);
+ });
+ var scale = F2(function (s,f) {
+ return _U.replace([["scale"
+ ,f.scale * s]],
+ f);
+ });
+ var moveY = F2(function (y,f) {
+ return _U.replace([["y"
+ ,f.y + y]],
+ f);
+ });
+ var moveX = F2(function (x,f) {
+ return _U.replace([["x"
+ ,f.x + x]],
+ f);
+ });
+ var move = F2(function (_v0,f) {
+ var $ = _v0,
+ x = $._0,
+ y = $._1;
+ return _U.replace([["x",f.x + x]
+ ,["y",f.y + y]],
+ f);
+ });
+ var form = function (f) {
+ return {_: {}
+ ,alpha: 1
+ ,form: f
+ ,scale: 1
+ ,theta: 0
+ ,x: 0
+ ,y: 0};
+ };
+ var Fill = function (a) {
+ return {ctor: "Fill",_0: a};
+ };
+ var Line = function (a) {
+ return {ctor: "Line",_0: a};
+ };
+ var FGroup = F2(function (a,b) {
+ return {ctor: "FGroup"
+ ,_0: a
+ ,_1: b};
+ });
+ var group = function (fs) {
+ return form(A2(FGroup,
+ $Transform2D.identity,
+ fs));
+ };
+ var groupTransform = F2(function (matrix,
+ fs) {
+ return form(A2(FGroup,
+ matrix,
+ fs));
+ });
+ var FElement = function (a) {
+ return {ctor: "FElement"
+ ,_0: a};
+ };
+ var toForm = function (e) {
+ return form(FElement(e));
+ };
+ var FImage = F4(function (a,
+ b,
+ c,
+ d) {
+ return {ctor: "FImage"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d};
+ });
+ var sprite = F4(function (w,
+ h,
+ pos,
+ src) {
+ return form(A4(FImage,
+ w,
+ h,
+ pos,
+ src));
+ });
+ var FText = function (a) {
+ return {ctor: "FText",_0: a};
+ };
+ var text = function (t) {
+ return form(FText(t));
+ };
+ var FOutlinedText = F2(function (a,
+ b) {
+ return {ctor: "FOutlinedText"
+ ,_0: a
+ ,_1: b};
+ });
+ var outlinedText = F2(function (ls,
+ t) {
+ return form(A2(FOutlinedText,
+ ls,
+ t));
+ });
+ var FShape = F2(function (a,b) {
+ return {ctor: "FShape"
+ ,_0: a
+ ,_1: b};
+ });
+ var fill = F2(function (style,
+ shape) {
+ return form(A2(FShape,
+ Fill(style),
+ shape));
+ });
+ var outlined = F2(function (style,
+ shape) {
+ return form(A2(FShape,
+ Line(style),
+ shape));
+ });
+ var FPath = F2(function (a,b) {
+ return {ctor: "FPath"
+ ,_0: a
+ ,_1: b};
+ });
+ var traced = F2(function (style,
+ path) {
+ return form(A2(FPath,
+ style,
+ path));
+ });
+ var LineStyle = F6(function (a,
+ b,
+ c,
+ d,
+ e,
+ f) {
+ return {_: {}
+ ,cap: c
+ ,color: a
+ ,dashOffset: f
+ ,dashing: e
+ ,join: d
+ ,width: b};
+ });
+ var Clipped = {ctor: "Clipped"};
+ var Sharp = function (a) {
+ return {ctor: "Sharp",_0: a};
+ };
+ var Smooth = {ctor: "Smooth"};
+ var Padded = {ctor: "Padded"};
+ var Round = {ctor: "Round"};
+ var Flat = {ctor: "Flat"};
+ var defaultLine = {_: {}
+ ,cap: Flat
+ ,color: $Color.black
+ ,dashOffset: 0
+ ,dashing: _L.fromArray([])
+ ,join: Sharp(10)
+ ,width: 1};
+ var solid = function (clr) {
+ return _U.replace([["color"
+ ,clr]],
+ defaultLine);
+ };
+ var dashed = function (clr) {
+ return _U.replace([["color"
+ ,clr]
+ ,["dashing"
+ ,_L.fromArray([8,4])]],
+ defaultLine);
+ };
+ var dotted = function (clr) {
+ return _U.replace([["color"
+ ,clr]
+ ,["dashing"
+ ,_L.fromArray([3,3])]],
+ defaultLine);
+ };
+ var Grad = function (a) {
+ return {ctor: "Grad",_0: a};
+ };
+ var gradient = F2(function (grad,
+ shape) {
+ return A2(fill,
+ Grad(grad),
+ shape);
+ });
+ var Texture = function (a) {
+ return {ctor: "Texture"
+ ,_0: a};
+ };
+ var textured = F2(function (src,
+ shape) {
+ return A2(fill,
+ Texture(src),
+ shape);
+ });
+ var Solid = function (a) {
+ return {ctor: "Solid",_0: a};
+ };
+ var filled = F2(function (color,
+ shape) {
+ return A2(fill,
+ Solid(color),
+ shape);
+ });
+ var Form = F6(function (a,
+ b,
+ c,
+ d,
+ e,
+ f) {
+ return {_: {}
+ ,alpha: e
+ ,form: f
+ ,scale: b
+ ,theta: a
+ ,x: c
+ ,y: d};
+ });
+ _elm.Graphics.Collage.values = {_op: _op
+ ,collage: collage
+ ,toForm: toForm
+ ,filled: filled
+ ,textured: textured
+ ,gradient: gradient
+ ,outlined: outlined
+ ,traced: traced
+ ,text: text
+ ,outlinedText: outlinedText
+ ,move: move
+ ,moveX: moveX
+ ,moveY: moveY
+ ,scale: scale
+ ,rotate: rotate
+ ,alpha: alpha
+ ,group: group
+ ,groupTransform: groupTransform
+ ,rect: rect
+ ,oval: oval
+ ,square: square
+ ,circle: circle
+ ,ngon: ngon
+ ,polygon: polygon
+ ,segment: segment
+ ,path: path
+ ,solid: solid
+ ,dashed: dashed
+ ,dotted: dotted
+ ,defaultLine: defaultLine
+ ,Form: Form
+ ,LineStyle: LineStyle
+ ,Flat: Flat
+ ,Round: Round
+ ,Padded: Padded
+ ,Smooth: Smooth
+ ,Sharp: Sharp
+ ,Clipped: Clipped};
+ return _elm.Graphics.Collage.values;
+};
+Elm.Graphics = Elm.Graphics || {};
+Elm.Graphics.Element = Elm.Graphics.Element || {};
+Elm.Graphics.Element.make = function (_elm) {
+ "use strict";
+ _elm.Graphics = _elm.Graphics || {};
+ _elm.Graphics.Element = _elm.Graphics.Element || {};
+ if (_elm.Graphics.Element.values)
+ return _elm.Graphics.Element.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Graphics.Element",
+ $Basics = Elm.Basics.make(_elm),
+ $Color = Elm.Color.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Graphics$Element = Elm.Native.Graphics.Element.make(_elm),
+ $Text = Elm.Text.make(_elm);
+ var DOut = {ctor: "DOut"};
+ var outward = DOut;
+ var DIn = {ctor: "DIn"};
+ var inward = DIn;
+ var DRight = {ctor: "DRight"};
+ var right = DRight;
+ var DLeft = {ctor: "DLeft"};
+ var left = DLeft;
+ var DDown = {ctor: "DDown"};
+ var down = DDown;
+ var DUp = {ctor: "DUp"};
+ var up = DUp;
+ var Position = F4(function (a,
+ b,
+ c,
+ d) {
+ return {_: {}
+ ,horizontal: a
+ ,vertical: b
+ ,x: c
+ ,y: d};
+ });
+ var Relative = function (a) {
+ return {ctor: "Relative"
+ ,_0: a};
+ };
+ var relative = Relative;
+ var Absolute = function (a) {
+ return {ctor: "Absolute"
+ ,_0: a};
+ };
+ var absolute = Absolute;
+ var N = {ctor: "N"};
+ var bottomLeftAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: N
+ ,vertical: N
+ ,x: x
+ ,y: y};
+ });
+ var Z = {ctor: "Z"};
+ var middle = {_: {}
+ ,horizontal: Z
+ ,vertical: Z
+ ,x: Relative(0.5)
+ ,y: Relative(0.5)};
+ var midLeft = _U.replace([["horizontal"
+ ,N]
+ ,["x",Absolute(0)]],
+ middle);
+ var middleAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: Z
+ ,vertical: Z
+ ,x: x
+ ,y: y};
+ });
+ var midLeftAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: N
+ ,vertical: Z
+ ,x: x
+ ,y: y};
+ });
+ var midBottomAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: Z
+ ,vertical: N
+ ,x: x
+ ,y: y};
+ });
+ var P = {ctor: "P"};
+ var topLeft = {_: {}
+ ,horizontal: N
+ ,vertical: P
+ ,x: Absolute(0)
+ ,y: Absolute(0)};
+ var bottomLeft = _U.replace([["vertical"
+ ,N]],
+ topLeft);
+ var topRight = _U.replace([["horizontal"
+ ,P]],
+ topLeft);
+ var bottomRight = _U.replace([["horizontal"
+ ,P]],
+ bottomLeft);
+ var midRight = _U.replace([["horizontal"
+ ,P]],
+ midLeft);
+ var midTop = _U.replace([["vertical"
+ ,P]
+ ,["y",Absolute(0)]],
+ middle);
+ var midBottom = _U.replace([["vertical"
+ ,N]],
+ midTop);
+ var topLeftAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: N
+ ,vertical: P
+ ,x: x
+ ,y: y};
+ });
+ var topRightAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: P
+ ,vertical: P
+ ,x: x
+ ,y: y};
+ });
+ var bottomRightAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: P
+ ,vertical: N
+ ,x: x
+ ,y: y};
+ });
+ var midRightAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: P
+ ,vertical: Z
+ ,x: x
+ ,y: y};
+ });
+ var midTopAt = F2(function (x,
+ y) {
+ return {_: {}
+ ,horizontal: Z
+ ,vertical: P
+ ,x: x
+ ,y: y};
+ });
+ var justified = $Native$Graphics$Element.block("justify");
+ var centered = $Native$Graphics$Element.block("center");
+ var rightAligned = $Native$Graphics$Element.block("right");
+ var leftAligned = $Native$Graphics$Element.block("left");
+ var show = function (value) {
+ return leftAligned($Text.monospace($Text.fromString($Basics.toString(value))));
+ };
+ var Tiled = {ctor: "Tiled"};
+ var Cropped = function (a) {
+ return {ctor: "Cropped"
+ ,_0: a};
+ };
+ var Fitted = {ctor: "Fitted"};
+ var Plain = {ctor: "Plain"};
+ var Custom = {ctor: "Custom"};
+ var RawHtml = {ctor: "RawHtml"};
+ var Spacer = {ctor: "Spacer"};
+ var Flow = F2(function (a,b) {
+ return {ctor: "Flow"
+ ,_0: a
+ ,_1: b};
+ });
+ var Container = F2(function (a,
+ b) {
+ return {ctor: "Container"
+ ,_0: a
+ ,_1: b};
+ });
+ var Image = F4(function (a,
+ b,
+ c,
+ d) {
+ return {ctor: "Image"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d};
+ });
+ var newElement = $Native$Graphics$Element.newElement;
+ var image = F3(function (w,
+ h,
+ src) {
+ return A3(newElement,
+ w,
+ h,
+ A4(Image,Plain,w,h,src));
+ });
+ var fittedImage = F3(function (w,
+ h,
+ src) {
+ return A3(newElement,
+ w,
+ h,
+ A4(Image,Fitted,w,h,src));
+ });
+ var croppedImage = F4(function (pos,
+ w,
+ h,
+ src) {
+ return A3(newElement,
+ w,
+ h,
+ A4(Image,Cropped(pos),w,h,src));
+ });
+ var tiledImage = F3(function (w,
+ h,
+ src) {
+ return A3(newElement,
+ w,
+ h,
+ A4(Image,Tiled,w,h,src));
+ });
+ var container = F4(function (w,
+ h,
+ pos,
+ e) {
+ return A3(newElement,
+ w,
+ h,
+ A2(Container,pos,e));
+ });
+ var spacer = F2(function (w,h) {
+ return A3(newElement,
+ w,
+ h,
+ Spacer);
+ });
+ var link = F2(function (href,
+ e) {
+ var p = e.props;
+ return {_: {}
+ ,element: e.element
+ ,props: _U.replace([["href"
+ ,href]],
+ p)};
+ });
+ var tag = F2(function (name,e) {
+ var p = e.props;
+ return {_: {}
+ ,element: e.element
+ ,props: _U.replace([["tag"
+ ,name]],
+ p)};
+ });
+ var color = F2(function (c,e) {
+ var p = e.props;
+ return {_: {}
+ ,element: e.element
+ ,props: _U.replace([["color"
+ ,$Maybe.Just(c)]],
+ p)};
+ });
+ var opacity = F2(function (o,
+ e) {
+ var p = e.props;
+ return {_: {}
+ ,element: e.element
+ ,props: _U.replace([["opacity"
+ ,o]],
+ p)};
+ });
+ var height = F2(function (nh,
+ e) {
+ var p = e.props;
+ var props = function () {
+ var _v0 = e.element;
+ switch (_v0.ctor)
+ {case "Image":
+ return _U.replace([["width"
+ ,$Basics.round($Basics.toFloat(_v0._1) / $Basics.toFloat(_v0._2) * $Basics.toFloat(nh))]],
+ p);}
+ return p;
+ }();
+ return {_: {}
+ ,element: e.element
+ ,props: _U.replace([["height"
+ ,nh]],
+ p)};
+ });
+ var width = F2(function (nw,e) {
+ var p = e.props;
+ var props = function () {
+ var _v5 = e.element;
+ switch (_v5.ctor)
+ {case "Image":
+ return _U.replace([["height"
+ ,$Basics.round($Basics.toFloat(_v5._2) / $Basics.toFloat(_v5._1) * $Basics.toFloat(nw))]],
+ p);
+ case "RawHtml":
+ return _U.replace([["height"
+ ,$Basics.snd(A2($Native$Graphics$Element.htmlHeight,
+ nw,
+ e.element))]],
+ p);}
+ return p;
+ }();
+ return {_: {}
+ ,element: e.element
+ ,props: _U.replace([["width"
+ ,nw]],
+ props)};
+ });
+ var size = F3(function (w,h,e) {
+ return A2(height,
+ h,
+ A2(width,w,e));
+ });
+ var sizeOf = function (e) {
+ return {ctor: "_Tuple2"
+ ,_0: e.props.width
+ ,_1: e.props.height};
+ };
+ var heightOf = function (e) {
+ return e.props.height;
+ };
+ var widthOf = function (e) {
+ return e.props.width;
+ };
+ var above = F2(function (hi,
+ lo) {
+ return A3(newElement,
+ A2($Basics.max,
+ widthOf(hi),
+ widthOf(lo)),
+ heightOf(hi) + heightOf(lo),
+ A2(Flow,
+ DDown,
+ _L.fromArray([hi,lo])));
+ });
+ var below = F2(function (lo,
+ hi) {
+ return A3(newElement,
+ A2($Basics.max,
+ widthOf(hi),
+ widthOf(lo)),
+ heightOf(hi) + heightOf(lo),
+ A2(Flow,
+ DDown,
+ _L.fromArray([hi,lo])));
+ });
+ var beside = F2(function (lft,
+ rht) {
+ return A3(newElement,
+ widthOf(lft) + widthOf(rht),
+ A2($Basics.max,
+ heightOf(lft),
+ heightOf(rht)),
+ A2(Flow,
+ right,
+ _L.fromArray([lft,rht])));
+ });
+ var layers = function (es) {
+ var hs = A2($List.map,
+ heightOf,
+ es);
+ var ws = A2($List.map,
+ widthOf,
+ es);
+ return A3(newElement,
+ A2($Maybe.withDefault,
+ 0,
+ $List.maximum(ws)),
+ A2($Maybe.withDefault,
+ 0,
+ $List.maximum(hs)),
+ A2(Flow,DOut,es));
+ };
+ var empty = A2(spacer,0,0);
+ var flow = F2(function (dir,
+ es) {
+ var newFlow = F2(function (w,
+ h) {
+ return A3(newElement,
+ w,
+ h,
+ A2(Flow,dir,es));
+ });
+ var maxOrZero = function (list) {
+ return A2($Maybe.withDefault,
+ 0,
+ $List.maximum(list));
+ };
+ var hs = A2($List.map,
+ heightOf,
+ es);
+ var ws = A2($List.map,
+ widthOf,
+ es);
+ if (_U.eq(es,_L.fromArray([])))
+ return empty; else {
+ switch (dir.ctor)
+ {case "DDown":
+ return A2(newFlow,
+ maxOrZero(ws),
+ $List.sum(hs));
+ case "DIn": return A2(newFlow,
+ maxOrZero(ws),
+ maxOrZero(hs));
+ case "DLeft": return A2(newFlow,
+ $List.sum(ws),
+ maxOrZero(hs));
+ case "DOut": return A2(newFlow,
+ maxOrZero(ws),
+ maxOrZero(hs));
+ case "DRight":
+ return A2(newFlow,
+ $List.sum(ws),
+ maxOrZero(hs));
+ case "DUp": return A2(newFlow,
+ maxOrZero(ws),
+ $List.sum(hs));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ });
+ var Properties = F9(function (a,
+ b,
+ c,
+ d,
+ e,
+ f,
+ g,
+ h,
+ i) {
+ return {_: {}
+ ,click: i
+ ,color: e
+ ,height: c
+ ,hover: h
+ ,href: f
+ ,id: a
+ ,opacity: d
+ ,tag: g
+ ,width: b};
+ });
+ var Element = F2(function (a,
+ b) {
+ return {_: {}
+ ,element: b
+ ,props: a};
+ });
+ _elm.Graphics.Element.values = {_op: _op
+ ,image: image
+ ,fittedImage: fittedImage
+ ,croppedImage: croppedImage
+ ,tiledImage: tiledImage
+ ,leftAligned: leftAligned
+ ,rightAligned: rightAligned
+ ,centered: centered
+ ,justified: justified
+ ,show: show
+ ,width: width
+ ,height: height
+ ,size: size
+ ,color: color
+ ,opacity: opacity
+ ,link: link
+ ,tag: tag
+ ,widthOf: widthOf
+ ,heightOf: heightOf
+ ,sizeOf: sizeOf
+ ,flow: flow
+ ,up: up
+ ,down: down
+ ,left: left
+ ,right: right
+ ,inward: inward
+ ,outward: outward
+ ,layers: layers
+ ,above: above
+ ,below: below
+ ,beside: beside
+ ,empty: empty
+ ,spacer: spacer
+ ,container: container
+ ,middle: middle
+ ,midTop: midTop
+ ,midBottom: midBottom
+ ,midLeft: midLeft
+ ,midRight: midRight
+ ,topLeft: topLeft
+ ,topRight: topRight
+ ,bottomLeft: bottomLeft
+ ,bottomRight: bottomRight
+ ,absolute: absolute
+ ,relative: relative
+ ,middleAt: middleAt
+ ,midTopAt: midTopAt
+ ,midBottomAt: midBottomAt
+ ,midLeftAt: midLeftAt
+ ,midRightAt: midRightAt
+ ,topLeftAt: topLeftAt
+ ,topRightAt: topRightAt
+ ,bottomLeftAt: bottomLeftAt
+ ,bottomRightAt: bottomRightAt
+ ,Element: Element
+ ,Position: Position};
+ return _elm.Graphics.Element.values;
+};
+Elm.Html = Elm.Html || {};
+Elm.Html.make = function (_elm) {
+ "use strict";
+ _elm.Html = _elm.Html || {};
+ if (_elm.Html.values)
+ return _elm.Html.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Html",
+ $Basics = Elm.Basics.make(_elm),
+ $Graphics$Element = Elm.Graphics.Element.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $VirtualDom = Elm.VirtualDom.make(_elm);
+ var fromElement = $VirtualDom.fromElement;
+ var toElement = $VirtualDom.toElement;
+ var text = $VirtualDom.text;
+ var node = $VirtualDom.node;
+ var body = node("body");
+ var section = node("section");
+ var nav = node("nav");
+ var article = node("article");
+ var aside = node("aside");
+ var h1 = node("h1");
+ var h2 = node("h2");
+ var h3 = node("h3");
+ var h4 = node("h4");
+ var h5 = node("h5");
+ var h6 = node("h6");
+ var header = node("header");
+ var footer = node("footer");
+ var address = node("address");
+ var main$ = node("main");
+ var p = node("p");
+ var hr = node("hr");
+ var pre = node("pre");
+ var blockquote = node("blockquote");
+ var ol = node("ol");
+ var ul = node("ul");
+ var li = node("li");
+ var dl = node("dl");
+ var dt = node("dt");
+ var dd = node("dd");
+ var figure = node("figure");
+ var figcaption = node("figcaption");
+ var div = node("div");
+ var a = node("a");
+ var em = node("em");
+ var strong = node("strong");
+ var small = node("small");
+ var s = node("s");
+ var cite = node("cite");
+ var q = node("q");
+ var dfn = node("dfn");
+ var abbr = node("abbr");
+ var time = node("time");
+ var code = node("code");
+ var $var = node("var");
+ var samp = node("samp");
+ var kbd = node("kbd");
+ var sub = node("sub");
+ var sup = node("sup");
+ var i = node("i");
+ var b = node("b");
+ var u = node("u");
+ var mark = node("mark");
+ var ruby = node("ruby");
+ var rt = node("rt");
+ var rp = node("rp");
+ var bdi = node("bdi");
+ var bdo = node("bdo");
+ var span = node("span");
+ var br = node("br");
+ var wbr = node("wbr");
+ var ins = node("ins");
+ var del = node("del");
+ var img = node("img");
+ var iframe = node("iframe");
+ var embed = node("embed");
+ var object = node("object");
+ var param = node("param");
+ var video = node("video");
+ var audio = node("audio");
+ var source = node("source");
+ var track = node("track");
+ var canvas = node("canvas");
+ var svg = node("svg");
+ var math = node("math");
+ var table = node("table");
+ var caption = node("caption");
+ var colgroup = node("colgroup");
+ var col = node("col");
+ var tbody = node("tbody");
+ var thead = node("thead");
+ var tfoot = node("tfoot");
+ var tr = node("tr");
+ var td = node("td");
+ var th = node("th");
+ var form = node("form");
+ var fieldset = node("fieldset");
+ var legend = node("legend");
+ var label = node("label");
+ var input = node("input");
+ var button = node("button");
+ var select = node("select");
+ var datalist = node("datalist");
+ var optgroup = node("optgroup");
+ var option = node("option");
+ var textarea = node("textarea");
+ var keygen = node("keygen");
+ var output = node("output");
+ var progress = node("progress");
+ var meter = node("meter");
+ var details = node("details");
+ var summary = node("summary");
+ var menuitem = node("menuitem");
+ var menu = node("menu");
+ _elm.Html.values = {_op: _op
+ ,node: node
+ ,text: text
+ ,toElement: toElement
+ ,fromElement: fromElement
+ ,body: body
+ ,section: section
+ ,nav: nav
+ ,article: article
+ ,aside: aside
+ ,h1: h1
+ ,h2: h2
+ ,h3: h3
+ ,h4: h4
+ ,h5: h5
+ ,h6: h6
+ ,header: header
+ ,footer: footer
+ ,address: address
+ ,main$: main$
+ ,p: p
+ ,hr: hr
+ ,pre: pre
+ ,blockquote: blockquote
+ ,ol: ol
+ ,ul: ul
+ ,li: li
+ ,dl: dl
+ ,dt: dt
+ ,dd: dd
+ ,figure: figure
+ ,figcaption: figcaption
+ ,div: div
+ ,a: a
+ ,em: em
+ ,strong: strong
+ ,small: small
+ ,s: s
+ ,cite: cite
+ ,q: q
+ ,dfn: dfn
+ ,abbr: abbr
+ ,time: time
+ ,code: code
+ ,$var: $var
+ ,samp: samp
+ ,kbd: kbd
+ ,sub: sub
+ ,sup: sup
+ ,i: i
+ ,b: b
+ ,u: u
+ ,mark: mark
+ ,ruby: ruby
+ ,rt: rt
+ ,rp: rp
+ ,bdi: bdi
+ ,bdo: bdo
+ ,span: span
+ ,br: br
+ ,wbr: wbr
+ ,ins: ins
+ ,del: del
+ ,img: img
+ ,iframe: iframe
+ ,embed: embed
+ ,object: object
+ ,param: param
+ ,video: video
+ ,audio: audio
+ ,source: source
+ ,track: track
+ ,canvas: canvas
+ ,svg: svg
+ ,math: math
+ ,table: table
+ ,caption: caption
+ ,colgroup: colgroup
+ ,col: col
+ ,tbody: tbody
+ ,thead: thead
+ ,tfoot: tfoot
+ ,tr: tr
+ ,td: td
+ ,th: th
+ ,form: form
+ ,fieldset: fieldset
+ ,legend: legend
+ ,label: label
+ ,input: input
+ ,button: button
+ ,select: select
+ ,datalist: datalist
+ ,optgroup: optgroup
+ ,option: option
+ ,textarea: textarea
+ ,keygen: keygen
+ ,output: output
+ ,progress: progress
+ ,meter: meter
+ ,details: details
+ ,summary: summary
+ ,menuitem: menuitem
+ ,menu: menu};
+ return _elm.Html.values;
+};
+Elm.Html = Elm.Html || {};
+Elm.Html.Attributes = Elm.Html.Attributes || {};
+Elm.Html.Attributes.make = function (_elm) {
+ "use strict";
+ _elm.Html = _elm.Html || {};
+ _elm.Html.Attributes = _elm.Html.Attributes || {};
+ if (_elm.Html.Attributes.values)
+ return _elm.Html.Attributes.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Html.Attributes",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Json$Encode = Elm.Json.Encode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm),
+ $VirtualDom = Elm.VirtualDom.make(_elm);
+ var attribute = $VirtualDom.attribute;
+ var property = $VirtualDom.property;
+ var stringProperty = F2(function (name,
+ string) {
+ return A2(property,
+ name,
+ $Json$Encode.string(string));
+ });
+ var $class = function (name) {
+ return A2(stringProperty,
+ "className",
+ name);
+ };
+ var id = function (name) {
+ return A2(stringProperty,
+ "id",
+ name);
+ };
+ var title = function (name) {
+ return A2(stringProperty,
+ "title",
+ name);
+ };
+ var accesskey = function ($char) {
+ return A2(stringProperty,
+ "accesskey",
+ $String.fromList(_L.fromArray([$char])));
+ };
+ var contextmenu = function (value) {
+ return A2(stringProperty,
+ "contextmenu",
+ value);
+ };
+ var dir = function (value) {
+ return A2(stringProperty,
+ "dir",
+ value);
+ };
+ var draggable = function (value) {
+ return A2(stringProperty,
+ "draggable",
+ value);
+ };
+ var dropzone = function (value) {
+ return A2(stringProperty,
+ "dropzone",
+ value);
+ };
+ var itemprop = function (value) {
+ return A2(stringProperty,
+ "itemprop",
+ value);
+ };
+ var lang = function (value) {
+ return A2(stringProperty,
+ "lang",
+ value);
+ };
+ var tabindex = function (n) {
+ return A2(stringProperty,
+ "tabIndex",
+ $Basics.toString(n));
+ };
+ var charset = function (value) {
+ return A2(stringProperty,
+ "charset",
+ value);
+ };
+ var content = function (value) {
+ return A2(stringProperty,
+ "content",
+ value);
+ };
+ var httpEquiv = function (value) {
+ return A2(stringProperty,
+ "httpEquiv",
+ value);
+ };
+ var language = function (value) {
+ return A2(stringProperty,
+ "language",
+ value);
+ };
+ var src = function (value) {
+ return A2(stringProperty,
+ "src",
+ value);
+ };
+ var height = function (value) {
+ return A2(stringProperty,
+ "height",
+ $Basics.toString(value));
+ };
+ var width = function (value) {
+ return A2(stringProperty,
+ "width",
+ $Basics.toString(value));
+ };
+ var alt = function (value) {
+ return A2(stringProperty,
+ "alt",
+ value);
+ };
+ var preload = function (value) {
+ return A2(stringProperty,
+ "preload",
+ value);
+ };
+ var poster = function (value) {
+ return A2(stringProperty,
+ "poster",
+ value);
+ };
+ var kind = function (value) {
+ return A2(stringProperty,
+ "kind",
+ value);
+ };
+ var srclang = function (value) {
+ return A2(stringProperty,
+ "srclang",
+ value);
+ };
+ var sandbox = function (value) {
+ return A2(stringProperty,
+ "sandbox",
+ value);
+ };
+ var srcdoc = function (value) {
+ return A2(stringProperty,
+ "srcdoc",
+ value);
+ };
+ var type$ = function (value) {
+ return A2(stringProperty,
+ "type",
+ value);
+ };
+ var value = function (value) {
+ return A2(stringProperty,
+ "value",
+ value);
+ };
+ var placeholder = function (value) {
+ return A2(stringProperty,
+ "placeholder",
+ value);
+ };
+ var accept = function (value) {
+ return A2(stringProperty,
+ "accept",
+ value);
+ };
+ var acceptCharset = function (value) {
+ return A2(stringProperty,
+ "acceptCharset",
+ value);
+ };
+ var action = function (value) {
+ return A2(stringProperty,
+ "action",
+ value);
+ };
+ var autocomplete = function (bool) {
+ return A2(stringProperty,
+ "autocomplete",
+ bool ? "on" : "off");
+ };
+ var autosave = function (value) {
+ return A2(stringProperty,
+ "autosave",
+ value);
+ };
+ var enctype = function (value) {
+ return A2(stringProperty,
+ "enctype",
+ value);
+ };
+ var formaction = function (value) {
+ return A2(stringProperty,
+ "formaction",
+ value);
+ };
+ var list = function (value) {
+ return A2(stringProperty,
+ "list",
+ value);
+ };
+ var minlength = function (n) {
+ return A2(stringProperty,
+ "minLength",
+ $Basics.toString(n));
+ };
+ var maxlength = function (n) {
+ return A2(stringProperty,
+ "maxLength",
+ $Basics.toString(n));
+ };
+ var method = function (value) {
+ return A2(stringProperty,
+ "method",
+ value);
+ };
+ var name = function (value) {
+ return A2(stringProperty,
+ "name",
+ value);
+ };
+ var pattern = function (value) {
+ return A2(stringProperty,
+ "pattern",
+ value);
+ };
+ var size = function (n) {
+ return A2(stringProperty,
+ "size",
+ $Basics.toString(n));
+ };
+ var $for = function (value) {
+ return A2(stringProperty,
+ "htmlFor",
+ value);
+ };
+ var form = function (value) {
+ return A2(stringProperty,
+ "form",
+ value);
+ };
+ var max = function (value) {
+ return A2(stringProperty,
+ "max",
+ value);
+ };
+ var min = function (value) {
+ return A2(stringProperty,
+ "min",
+ value);
+ };
+ var step = function (n) {
+ return A2(stringProperty,
+ "step",
+ n);
+ };
+ var cols = function (n) {
+ return A2(stringProperty,
+ "cols",
+ $Basics.toString(n));
+ };
+ var rows = function (n) {
+ return A2(stringProperty,
+ "rows",
+ $Basics.toString(n));
+ };
+ var wrap = function (value) {
+ return A2(stringProperty,
+ "wrap",
+ value);
+ };
+ var usemap = function (value) {
+ return A2(stringProperty,
+ "useMap",
+ value);
+ };
+ var shape = function (value) {
+ return A2(stringProperty,
+ "shape",
+ value);
+ };
+ var coords = function (value) {
+ return A2(stringProperty,
+ "coords",
+ value);
+ };
+ var challenge = function (value) {
+ return A2(stringProperty,
+ "challenge",
+ value);
+ };
+ var keytype = function (value) {
+ return A2(stringProperty,
+ "keytype",
+ value);
+ };
+ var align = function (value) {
+ return A2(stringProperty,
+ "align",
+ value);
+ };
+ var cite = function (value) {
+ return A2(stringProperty,
+ "cite",
+ value);
+ };
+ var href = function (value) {
+ return A2(stringProperty,
+ "href",
+ value);
+ };
+ var target = function (value) {
+ return A2(stringProperty,
+ "target",
+ value);
+ };
+ var downloadAs = function (value) {
+ return A2(stringProperty,
+ "download",
+ value);
+ };
+ var hreflang = function (value) {
+ return A2(stringProperty,
+ "hreflang",
+ value);
+ };
+ var media = function (value) {
+ return A2(stringProperty,
+ "media",
+ value);
+ };
+ var ping = function (value) {
+ return A2(stringProperty,
+ "ping",
+ value);
+ };
+ var rel = function (value) {
+ return A2(stringProperty,
+ "rel",
+ value);
+ };
+ var datetime = function (value) {
+ return A2(stringProperty,
+ "datetime",
+ value);
+ };
+ var pubdate = function (value) {
+ return A2(stringProperty,
+ "pubdate",
+ value);
+ };
+ var start = function (n) {
+ return A2(stringProperty,
+ "start",
+ $Basics.toString(n));
+ };
+ var colspan = function (n) {
+ return A2(stringProperty,
+ "colSpan",
+ $Basics.toString(n));
+ };
+ var headers = function (value) {
+ return A2(stringProperty,
+ "headers",
+ value);
+ };
+ var rowspan = function (n) {
+ return A2(stringProperty,
+ "rowSpan",
+ $Basics.toString(n));
+ };
+ var scope = function (value) {
+ return A2(stringProperty,
+ "scope",
+ value);
+ };
+ var manifest = function (value) {
+ return A2(stringProperty,
+ "manifest",
+ value);
+ };
+ var boolProperty = F2(function (name,
+ bool) {
+ return A2(property,
+ name,
+ $Json$Encode.bool(bool));
+ });
+ var hidden = function (bool) {
+ return A2(boolProperty,
+ "hidden",
+ bool);
+ };
+ var contenteditable = function (bool) {
+ return A2(boolProperty,
+ "contentEditable",
+ bool);
+ };
+ var spellcheck = function (bool) {
+ return A2(boolProperty,
+ "spellcheck",
+ bool);
+ };
+ var async = function (bool) {
+ return A2(boolProperty,
+ "async",
+ bool);
+ };
+ var defer = function (bool) {
+ return A2(boolProperty,
+ "defer",
+ bool);
+ };
+ var scoped = function (bool) {
+ return A2(boolProperty,
+ "scoped",
+ bool);
+ };
+ var autoplay = function (bool) {
+ return A2(boolProperty,
+ "autoplay",
+ bool);
+ };
+ var controls = function (bool) {
+ return A2(boolProperty,
+ "controls",
+ bool);
+ };
+ var loop = function (bool) {
+ return A2(boolProperty,
+ "loop",
+ bool);
+ };
+ var $default = function (bool) {
+ return A2(boolProperty,
+ "default",
+ bool);
+ };
+ var seamless = function (bool) {
+ return A2(boolProperty,
+ "seamless",
+ bool);
+ };
+ var checked = function (bool) {
+ return A2(boolProperty,
+ "checked",
+ bool);
+ };
+ var selected = function (bool) {
+ return A2(boolProperty,
+ "selected",
+ bool);
+ };
+ var autofocus = function (bool) {
+ return A2(boolProperty,
+ "autofocus",
+ bool);
+ };
+ var disabled = function (bool) {
+ return A2(boolProperty,
+ "disabled",
+ bool);
+ };
+ var multiple = function (bool) {
+ return A2(boolProperty,
+ "multiple",
+ bool);
+ };
+ var novalidate = function (bool) {
+ return A2(boolProperty,
+ "noValidate",
+ bool);
+ };
+ var readonly = function (bool) {
+ return A2(boolProperty,
+ "readOnly",
+ bool);
+ };
+ var required = function (bool) {
+ return A2(boolProperty,
+ "required",
+ bool);
+ };
+ var ismap = function (value) {
+ return A2(boolProperty,
+ "isMap",
+ value);
+ };
+ var download = function (bool) {
+ return A2(boolProperty,
+ "download",
+ bool);
+ };
+ var reversed = function (bool) {
+ return A2(boolProperty,
+ "reversed",
+ bool);
+ };
+ var classList = function (list) {
+ return $class($String.join(" ")($List.map($Basics.fst)($List.filter($Basics.snd)(list))));
+ };
+ var style = function (props) {
+ return property("style")($Json$Encode.object($List.map(function (_v0) {
+ var $ = _v0,
+ key = $._0,
+ value = $._1;
+ return {ctor: "_Tuple2"
+ ,_0: key
+ ,_1: $Json$Encode.string(value)};
+ })(props)));
+ };
+ var key = function (k) {
+ return A2(stringProperty,
+ "key",
+ k);
+ };
+ _elm.Html.Attributes.values = {_op: _op
+ ,key: key
+ ,style: style
+ ,$class: $class
+ ,classList: classList
+ ,id: id
+ ,title: title
+ ,hidden: hidden
+ ,type$: type$
+ ,value: value
+ ,checked: checked
+ ,placeholder: placeholder
+ ,selected: selected
+ ,accept: accept
+ ,acceptCharset: acceptCharset
+ ,action: action
+ ,autocomplete: autocomplete
+ ,autofocus: autofocus
+ ,autosave: autosave
+ ,disabled: disabled
+ ,enctype: enctype
+ ,formaction: formaction
+ ,list: list
+ ,maxlength: maxlength
+ ,minlength: minlength
+ ,method: method
+ ,multiple: multiple
+ ,name: name
+ ,novalidate: novalidate
+ ,pattern: pattern
+ ,readonly: readonly
+ ,required: required
+ ,size: size
+ ,$for: $for
+ ,form: form
+ ,max: max
+ ,min: min
+ ,step: step
+ ,cols: cols
+ ,rows: rows
+ ,wrap: wrap
+ ,href: href
+ ,target: target
+ ,download: download
+ ,downloadAs: downloadAs
+ ,hreflang: hreflang
+ ,media: media
+ ,ping: ping
+ ,rel: rel
+ ,ismap: ismap
+ ,usemap: usemap
+ ,shape: shape
+ ,coords: coords
+ ,src: src
+ ,height: height
+ ,width: width
+ ,alt: alt
+ ,autoplay: autoplay
+ ,controls: controls
+ ,loop: loop
+ ,preload: preload
+ ,poster: poster
+ ,$default: $default
+ ,kind: kind
+ ,srclang: srclang
+ ,sandbox: sandbox
+ ,seamless: seamless
+ ,srcdoc: srcdoc
+ ,reversed: reversed
+ ,start: start
+ ,align: align
+ ,colspan: colspan
+ ,rowspan: rowspan
+ ,headers: headers
+ ,scope: scope
+ ,async: async
+ ,charset: charset
+ ,content: content
+ ,defer: defer
+ ,httpEquiv: httpEquiv
+ ,language: language
+ ,scoped: scoped
+ ,accesskey: accesskey
+ ,contenteditable: contenteditable
+ ,contextmenu: contextmenu
+ ,dir: dir
+ ,draggable: draggable
+ ,dropzone: dropzone
+ ,itemprop: itemprop
+ ,lang: lang
+ ,spellcheck: spellcheck
+ ,tabindex: tabindex
+ ,challenge: challenge
+ ,keytype: keytype
+ ,cite: cite
+ ,datetime: datetime
+ ,pubdate: pubdate
+ ,manifest: manifest
+ ,property: property
+ ,attribute: attribute};
+ return _elm.Html.Attributes.values;
+};
+Elm.Html = Elm.Html || {};
+Elm.Html.Events = Elm.Html.Events || {};
+Elm.Html.Events.make = function (_elm) {
+ "use strict";
+ _elm.Html = _elm.Html || {};
+ _elm.Html.Events = _elm.Html.Events || {};
+ if (_elm.Html.Events.values)
+ return _elm.Html.Events.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Html.Events",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $VirtualDom = Elm.VirtualDom.make(_elm);
+ var keyCode = A2($Json$Decode._op[":="],
+ "keyCode",
+ $Json$Decode.$int);
+ var targetChecked = A2($Json$Decode.at,
+ _L.fromArray(["target"
+ ,"checked"]),
+ $Json$Decode.bool);
+ var targetValue = A2($Json$Decode.at,
+ _L.fromArray(["target"
+ ,"value"]),
+ $Json$Decode.string);
+ var defaultOptions = $VirtualDom.defaultOptions;
+ var Options = F2(function (a,
+ b) {
+ return {_: {}
+ ,preventDefault: b
+ ,stopPropagation: a};
+ });
+ var onWithOptions = $VirtualDom.onWithOptions;
+ var on = $VirtualDom.on;
+ var messageOn = F3(function (name,
+ addr,
+ msg) {
+ return A3(on,
+ name,
+ $Json$Decode.value,
+ function (_v0) {
+ var _ = _v0;
+ return A2($Signal.message,
+ addr,
+ msg);
+ });
+ });
+ var onClick = messageOn("click");
+ var onDoubleClick = messageOn("dblclick");
+ var onMouseMove = messageOn("mousemove");
+ var onMouseDown = messageOn("mousedown");
+ var onMouseUp = messageOn("mouseup");
+ var onMouseEnter = messageOn("mouseenter");
+ var onMouseLeave = messageOn("mouseleave");
+ var onMouseOver = messageOn("mouseover");
+ var onMouseOut = messageOn("mouseout");
+ var onBlur = messageOn("blur");
+ var onFocus = messageOn("focus");
+ var onSubmit = messageOn("submit");
+ var onKey = F3(function (name,
+ addr,
+ handler) {
+ return A3(on,
+ name,
+ keyCode,
+ function (code) {
+ return A2($Signal.message,
+ addr,
+ handler(code));
+ });
+ });
+ var onKeyUp = onKey("keyup");
+ var onKeyDown = onKey("keydown");
+ var onKeyPress = onKey("keypress");
+ _elm.Html.Events.values = {_op: _op
+ ,onBlur: onBlur
+ ,onFocus: onFocus
+ ,onSubmit: onSubmit
+ ,onKeyUp: onKeyUp
+ ,onKeyDown: onKeyDown
+ ,onKeyPress: onKeyPress
+ ,onClick: onClick
+ ,onDoubleClick: onDoubleClick
+ ,onMouseMove: onMouseMove
+ ,onMouseDown: onMouseDown
+ ,onMouseUp: onMouseUp
+ ,onMouseEnter: onMouseEnter
+ ,onMouseLeave: onMouseLeave
+ ,onMouseOver: onMouseOver
+ ,onMouseOut: onMouseOut
+ ,on: on
+ ,onWithOptions: onWithOptions
+ ,defaultOptions: defaultOptions
+ ,targetValue: targetValue
+ ,targetChecked: targetChecked
+ ,keyCode: keyCode
+ ,Options: Options};
+ return _elm.Html.Events.values;
+};
+Elm.Http = Elm.Http || {};
+Elm.Http.make = function (_elm) {
+ "use strict";
+ _elm.Http = _elm.Http || {};
+ if (_elm.Http.values)
+ return _elm.Http.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Http",
+ $Basics = Elm.Basics.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Http = Elm.Native.Http.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm),
+ $Task = Elm.Task.make(_elm),
+ $Time = Elm.Time.make(_elm);
+ var send = $Native$Http.send;
+ var BadResponse = F2(function (a,
+ b) {
+ return {ctor: "BadResponse"
+ ,_0: a
+ ,_1: b};
+ });
+ var UnexpectedPayload = function (a) {
+ return {ctor: "UnexpectedPayload"
+ ,_0: a};
+ };
+ var handleResponse = F2(function (handle,
+ response) {
+ var _v0 = _U.cmp(200,
+ response.status) < 1 && _U.cmp(response.status,
+ 300) < 0;
+ switch (_v0)
+ {case false:
+ return $Task.fail(A2(BadResponse,
+ response.status,
+ response.statusText));
+ case true:
+ var _v1 = response.value;
+ switch (_v1.ctor)
+ {case "Text":
+ return handle(_v1._0);}
+ return $Task.fail(UnexpectedPayload("Response body is a blob, expecting a string."));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var NetworkError = {ctor: "NetworkError"};
+ var Timeout = {ctor: "Timeout"};
+ var promoteError = function (rawError) {
+ switch (rawError.ctor)
+ {case "RawNetworkError":
+ return NetworkError;
+ case "RawTimeout":
+ return Timeout;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var fromJson = F2(function (decoder,
+ response) {
+ var decode = function (str) {
+ var _v4 = A2($Json$Decode.decodeString,
+ decoder,
+ str);
+ switch (_v4.ctor)
+ {case "Err":
+ return $Task.fail(UnexpectedPayload(_v4._0));
+ case "Ok":
+ return $Task.succeed(_v4._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ return A2($Task.andThen,
+ A2($Task.mapError,
+ promoteError,
+ response),
+ handleResponse(decode));
+ });
+ var RawNetworkError = {ctor: "RawNetworkError"};
+ var RawTimeout = {ctor: "RawTimeout"};
+ var Blob = function (a) {
+ return {ctor: "Blob",_0: a};
+ };
+ var Text = function (a) {
+ return {ctor: "Text",_0: a};
+ };
+ var Response = F5(function (a,
+ b,
+ c,
+ d,
+ e) {
+ return {_: {}
+ ,headers: c
+ ,status: a
+ ,statusText: b
+ ,url: d
+ ,value: e};
+ });
+ var defaultSettings = {_: {}
+ ,desiredResponseType: $Maybe.Nothing
+ ,onProgress: $Maybe.Nothing
+ ,onStart: $Maybe.Nothing
+ ,timeout: 0};
+ var post = F3(function (decoder,
+ url,
+ body) {
+ var request = {_: {}
+ ,body: body
+ ,headers: _L.fromArray([])
+ ,url: url
+ ,verb: "POST"};
+ return A2(fromJson,
+ decoder,
+ A2(send,
+ defaultSettings,
+ request));
+ });
+ var Settings = F4(function (a,
+ b,
+ c,
+ d) {
+ return {_: {}
+ ,desiredResponseType: d
+ ,onProgress: c
+ ,onStart: b
+ ,timeout: a};
+ });
+ var multipart = $Native$Http.multipart;
+ var FileData = F3(function (a,
+ b,
+ c) {
+ return {ctor: "FileData"
+ ,_0: a
+ ,_1: b
+ ,_2: c};
+ });
+ var BlobData = F3(function (a,
+ b,
+ c) {
+ return {ctor: "BlobData"
+ ,_0: a
+ ,_1: b
+ ,_2: c};
+ });
+ var blobData = BlobData;
+ var StringData = F2(function (a,
+ b) {
+ return {ctor: "StringData"
+ ,_0: a
+ ,_1: b};
+ });
+ var stringData = StringData;
+ var BodyBlob = function (a) {
+ return {ctor: "BodyBlob"
+ ,_0: a};
+ };
+ var BodyFormData = {ctor: "BodyFormData"};
+ var ArrayBuffer = {ctor: "ArrayBuffer"};
+ var BodyString = function (a) {
+ return {ctor: "BodyString"
+ ,_0: a};
+ };
+ var string = BodyString;
+ var Empty = {ctor: "Empty"};
+ var empty = Empty;
+ var getString = function (url) {
+ var request = {_: {}
+ ,body: empty
+ ,headers: _L.fromArray([])
+ ,url: url
+ ,verb: "GET"};
+ return A2($Task.andThen,
+ A2($Task.mapError,
+ promoteError,
+ A2(send,
+ defaultSettings,
+ request)),
+ handleResponse($Task.succeed));
+ };
+ var get = F2(function (decoder,
+ url) {
+ var request = {_: {}
+ ,body: empty
+ ,headers: _L.fromArray([])
+ ,url: url
+ ,verb: "GET"};
+ return A2(fromJson,
+ decoder,
+ A2(send,
+ defaultSettings,
+ request));
+ });
+ var Request = F4(function (a,
+ b,
+ c,
+ d) {
+ return {_: {}
+ ,body: d
+ ,headers: b
+ ,url: c
+ ,verb: a};
+ });
+ var uriDecode = $Native$Http.uriDecode;
+ var uriEncode = $Native$Http.uriEncode;
+ var queryEscape = function (string) {
+ return A2($String.join,
+ "+",
+ A2($String.split,
+ "%20",
+ uriEncode(string)));
+ };
+ var queryPair = function (_v7) {
+ var $ = _v7,
+ key = $._0,
+ value = $._1;
+ return A2($Basics._op["++"],
+ queryEscape(key),
+ A2($Basics._op["++"],
+ "=",
+ queryEscape(value)));
+ };
+ var url = F2(function (domain,
+ args) {
+ switch (args.ctor)
+ {case "[]": return domain;}
+ return A2($Basics._op["++"],
+ domain,
+ A2($Basics._op["++"],
+ "?",
+ A2($String.join,
+ "&",
+ A2($List.map,queryPair,args))));
+ });
+ var TODO_implement_file_in_another_library = {ctor: "TODO_implement_file_in_another_library"};
+ var TODO_implement_blob_in_another_library = {ctor: "TODO_implement_blob_in_another_library"};
+ _elm.Http.values = {_op: _op
+ ,getString: getString
+ ,get: get
+ ,post: post
+ ,send: send
+ ,url: url
+ ,uriEncode: uriEncode
+ ,uriDecode: uriDecode
+ ,empty: empty
+ ,string: string
+ ,multipart: multipart
+ ,stringData: stringData
+ ,blobData: blobData
+ ,defaultSettings: defaultSettings
+ ,fromJson: fromJson
+ ,Request: Request
+ ,Settings: Settings
+ ,Response: Response
+ ,Text: Text
+ ,Blob: Blob
+ ,Timeout: Timeout
+ ,NetworkError: NetworkError
+ ,UnexpectedPayload: UnexpectedPayload
+ ,BadResponse: BadResponse
+ ,RawTimeout: RawTimeout
+ ,RawNetworkError: RawNetworkError};
+ return _elm.Http.values;
+};
+Elm.InitViewAction = Elm.InitViewAction || {};
+Elm.InitViewAction.make = function (_elm) {
+ "use strict";
+ _elm.InitViewAction = _elm.InitViewAction || {};
+ if (_elm.InitViewAction.values)
+ return _elm.InitViewAction.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "InitViewAction",
+ $Basics = Elm.Basics.make(_elm),
+ $Http = Elm.Http.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payer = Elm.Model.Payer.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Task = Elm.Task.make(_elm),
+ $Update = Elm.Update.make(_elm);
+ var loggedInView = A2($Task.andMap,
+ A2($Task.andMap,
+ A2($Task.andMap,
+ A2($Task.andMap,
+ A2($Task.andMap,
+ A2($Task.map,
+ $Update.GoLoggedInView,
+ A2($Http.get,
+ $Model$User.usersDecoder,
+ "/users")),
+ A2($Http.get,
+ A2($Json$Decode._op[":="],
+ "id",
+ $Model$User.userIdDecoder),
+ "/whoAmI")),
+ A2($Http.get,
+ $Model$Payment.paymentsDecoder,
+ "/monthlyPayments")),
+ A2($Http.get,
+ $Model$Payment.paymentsDecoder,
+ A2($Basics._op["++"],
+ "/payments?page=1&perPage=",
+ $Basics.toString($Model$Payment.perPage)))),
+ A2($Http.get,
+ A2($Json$Decode._op[":="],
+ "number",
+ $Json$Decode.$int),
+ "/payments/count")),
+ A2($Http.get,
+ $Model$Payer.payersDecoder,
+ "/payers"));
+ var initViewAction = A2($Task.onError,
+ loggedInView,
+ $Basics.always($Task.succeed($Update.GoSignInView)));
+ _elm.InitViewAction.values = {_op: _op
+ ,initViewAction: initViewAction};
+ return _elm.InitViewAction.values;
+};
+Elm.Json = Elm.Json || {};
+Elm.Json.Decode = Elm.Json.Decode || {};
+Elm.Json.Decode.make = function (_elm) {
+ "use strict";
+ _elm.Json = _elm.Json || {};
+ _elm.Json.Decode = _elm.Json.Decode || {};
+ if (_elm.Json.Decode.values)
+ return _elm.Json.Decode.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Json.Decode",
+ $Array = Elm.Array.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $Json$Encode = Elm.Json.Encode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Json = Elm.Native.Json.make(_elm),
+ $Result = Elm.Result.make(_elm);
+ var tuple8 = $Native$Json.decodeTuple8;
+ var tuple7 = $Native$Json.decodeTuple7;
+ var tuple6 = $Native$Json.decodeTuple6;
+ var tuple5 = $Native$Json.decodeTuple5;
+ var tuple4 = $Native$Json.decodeTuple4;
+ var tuple3 = $Native$Json.decodeTuple3;
+ var tuple2 = $Native$Json.decodeTuple2;
+ var tuple1 = $Native$Json.decodeTuple1;
+ var succeed = $Native$Json.succeed;
+ var fail = $Native$Json.fail;
+ var andThen = $Native$Json.andThen;
+ var customDecoder = $Native$Json.customDecoder;
+ var decodeValue = $Native$Json.runDecoderValue;
+ var value = $Native$Json.decodeValue;
+ var maybe = $Native$Json.decodeMaybe;
+ var $null = $Native$Json.decodeNull;
+ var array = $Native$Json.decodeArray;
+ var list = $Native$Json.decodeList;
+ var bool = $Native$Json.decodeBool;
+ var $int = $Native$Json.decodeInt;
+ var $float = $Native$Json.decodeFloat;
+ var string = $Native$Json.decodeString;
+ var oneOf = $Native$Json.oneOf;
+ var keyValuePairs = $Native$Json.decodeKeyValuePairs;
+ var object8 = $Native$Json.decodeObject8;
+ var object7 = $Native$Json.decodeObject7;
+ var object6 = $Native$Json.decodeObject6;
+ var object5 = $Native$Json.decodeObject5;
+ var object4 = $Native$Json.decodeObject4;
+ var object3 = $Native$Json.decodeObject3;
+ var object2 = $Native$Json.decodeObject2;
+ var object1 = $Native$Json.decodeObject1;
+ _op[":="] = $Native$Json.decodeField;
+ var at = F2(function (fields,
+ decoder) {
+ return A3($List.foldr,
+ F2(function (x,y) {
+ return A2(_op[":="],x,y);
+ }),
+ decoder,
+ fields);
+ });
+ var decodeString = $Native$Json.runDecoderString;
+ var map = $Native$Json.decodeObject1;
+ var dict = function (decoder) {
+ return A2(map,
+ $Dict.fromList,
+ keyValuePairs(decoder));
+ };
+ var Decoder = {ctor: "Decoder"};
+ _elm.Json.Decode.values = {_op: _op
+ ,decodeString: decodeString
+ ,decodeValue: decodeValue
+ ,string: string
+ ,$int: $int
+ ,$float: $float
+ ,bool: bool
+ ,$null: $null
+ ,list: list
+ ,array: array
+ ,tuple1: tuple1
+ ,tuple2: tuple2
+ ,tuple3: tuple3
+ ,tuple4: tuple4
+ ,tuple5: tuple5
+ ,tuple6: tuple6
+ ,tuple7: tuple7
+ ,tuple8: tuple8
+ ,at: at
+ ,object1: object1
+ ,object2: object2
+ ,object3: object3
+ ,object4: object4
+ ,object5: object5
+ ,object6: object6
+ ,object7: object7
+ ,object8: object8
+ ,keyValuePairs: keyValuePairs
+ ,dict: dict
+ ,maybe: maybe
+ ,oneOf: oneOf
+ ,map: map
+ ,fail: fail
+ ,succeed: succeed
+ ,andThen: andThen
+ ,value: value
+ ,customDecoder: customDecoder
+ ,Decoder: Decoder};
+ return _elm.Json.Decode.values;
+};
+Elm.Json = Elm.Json || {};
+Elm.Json.Encode = Elm.Json.Encode || {};
+Elm.Json.Encode.make = function (_elm) {
+ "use strict";
+ _elm.Json = _elm.Json || {};
+ _elm.Json.Encode = _elm.Json.Encode || {};
+ if (_elm.Json.Encode.values)
+ return _elm.Json.Encode.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Json.Encode",
+ $Array = Elm.Array.make(_elm),
+ $Native$Json = Elm.Native.Json.make(_elm);
+ var list = $Native$Json.encodeList;
+ var array = $Native$Json.encodeArray;
+ var object = $Native$Json.encodeObject;
+ var $null = $Native$Json.encodeNull;
+ var bool = $Native$Json.identity;
+ var $float = $Native$Json.identity;
+ var $int = $Native$Json.identity;
+ var string = $Native$Json.identity;
+ var encode = $Native$Json.encode;
+ var Value = {ctor: "Value"};
+ _elm.Json.Encode.values = {_op: _op
+ ,encode: encode
+ ,string: string
+ ,$int: $int
+ ,$float: $float
+ ,bool: bool
+ ,$null: $null
+ ,list: list
+ ,array: array
+ ,object: object
+ ,Value: Value};
+ return _elm.Json.Encode.values;
+};
+Elm.List = Elm.List || {};
+Elm.List.make = function (_elm) {
+ "use strict";
+ _elm.List = _elm.List || {};
+ if (_elm.List.values)
+ return _elm.List.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "List",
+ $Basics = Elm.Basics.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$List = Elm.Native.List.make(_elm);
+ var sortWith = $Native$List.sortWith;
+ var sortBy = $Native$List.sortBy;
+ var sort = function (xs) {
+ return A2(sortBy,
+ $Basics.identity,
+ xs);
+ };
+ var repeat = $Native$List.repeat;
+ var drop = $Native$List.drop;
+ var take = $Native$List.take;
+ var map5 = $Native$List.map5;
+ var map4 = $Native$List.map4;
+ var map3 = $Native$List.map3;
+ var map2 = $Native$List.map2;
+ var any = $Native$List.any;
+ var all = F2(function (pred,
+ xs) {
+ return $Basics.not(A2(any,
+ function ($) {
+ return $Basics.not(pred($));
+ },
+ xs));
+ });
+ var foldr = $Native$List.foldr;
+ var foldl = $Native$List.foldl;
+ var length = function (xs) {
+ return A3(foldl,
+ F2(function (_v0,i) {
+ var _ = _v0;
+ return i + 1;
+ }),
+ 0,
+ xs);
+ };
+ var sum = function (numbers) {
+ return A3(foldl,
+ F2(function (x,y) {
+ return x + y;
+ }),
+ 0,
+ numbers);
+ };
+ var product = function (numbers) {
+ return A3(foldl,
+ F2(function (x,y) {
+ return x * y;
+ }),
+ 1,
+ numbers);
+ };
+ var maximum = function (list) {
+ switch (list.ctor)
+ {case "::":
+ return $Maybe.Just(A3(foldl,
+ $Basics.max,
+ list._0,
+ list._1));}
+ return $Maybe.Nothing;
+ };
+ var minimum = function (list) {
+ switch (list.ctor)
+ {case "::":
+ return $Maybe.Just(A3(foldl,
+ $Basics.min,
+ list._0,
+ list._1));}
+ return $Maybe.Nothing;
+ };
+ var indexedMap = F2(function (f,
+ xs) {
+ return A3(map2,
+ f,
+ _L.range(0,length(xs) - 1),
+ xs);
+ });
+ var member = F2(function (x,
+ xs) {
+ return A2(any,
+ function (a) {
+ return _U.eq(a,x);
+ },
+ xs);
+ });
+ var isEmpty = function (xs) {
+ switch (xs.ctor)
+ {case "[]": return true;}
+ return false;
+ };
+ var tail = function (list) {
+ switch (list.ctor)
+ {case "::":
+ return $Maybe.Just(list._1);
+ case "[]":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var head = function (list) {
+ switch (list.ctor)
+ {case "::":
+ return $Maybe.Just(list._0);
+ case "[]":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ _op["::"] = $Native$List.cons;
+ var map = F2(function (f,xs) {
+ return A3(foldr,
+ F2(function (x,acc) {
+ return A2(_op["::"],
+ f(x),
+ acc);
+ }),
+ _L.fromArray([]),
+ xs);
+ });
+ var filter = F2(function (pred,
+ xs) {
+ var conditionalCons = F2(function (x,
+ xs$) {
+ return pred(x) ? A2(_op["::"],
+ x,
+ xs$) : xs$;
+ });
+ return A3(foldr,
+ conditionalCons,
+ _L.fromArray([]),
+ xs);
+ });
+ var maybeCons = F3(function (f,
+ mx,
+ xs) {
+ var _v14 = f(mx);
+ switch (_v14.ctor)
+ {case "Just":
+ return A2(_op["::"],_v14._0,xs);
+ case "Nothing": return xs;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var filterMap = F2(function (f,
+ xs) {
+ return A3(foldr,
+ maybeCons(f),
+ _L.fromArray([]),
+ xs);
+ });
+ var reverse = function (list) {
+ return A3(foldl,
+ F2(function (x,y) {
+ return A2(_op["::"],x,y);
+ }),
+ _L.fromArray([]),
+ list);
+ };
+ var scanl = F3(function (f,
+ b,
+ xs) {
+ var scan1 = F2(function (x,
+ accAcc) {
+ switch (accAcc.ctor)
+ {case "::": return A2(_op["::"],
+ A2(f,x,accAcc._0),
+ accAcc);
+ case "[]":
+ return _L.fromArray([]);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ return reverse(A3(foldl,
+ scan1,
+ _L.fromArray([b]),
+ xs));
+ });
+ var append = F2(function (xs,
+ ys) {
+ switch (ys.ctor)
+ {case "[]": return xs;}
+ return A3(foldr,
+ F2(function (x,y) {
+ return A2(_op["::"],x,y);
+ }),
+ ys,
+ xs);
+ });
+ var concat = function (lists) {
+ return A3(foldr,
+ append,
+ _L.fromArray([]),
+ lists);
+ };
+ var concatMap = F2(function (f,
+ list) {
+ return concat(A2(map,
+ f,
+ list));
+ });
+ var partition = F2(function (pred,
+ list) {
+ var step = F2(function (x,
+ _v20) {
+ var $ = _v20,
+ trues = $._0,
+ falses = $._1;
+ return pred(x) ? {ctor: "_Tuple2"
+ ,_0: A2(_op["::"],x,trues)
+ ,_1: falses} : {ctor: "_Tuple2"
+ ,_0: trues
+ ,_1: A2(_op["::"],x,falses)};
+ });
+ return A3(foldr,
+ step,
+ {ctor: "_Tuple2"
+ ,_0: _L.fromArray([])
+ ,_1: _L.fromArray([])},
+ list);
+ });
+ var unzip = function (pairs) {
+ var step = F2(function (_v21,
+ _v22) {
+ var $ = _v21,
+ x = $._0,
+ y = $._1;
+ var $ = _v22,
+ xs = $._0,
+ ys = $._1;
+ return {ctor: "_Tuple2"
+ ,_0: A2(_op["::"],x,xs)
+ ,_1: A2(_op["::"],y,ys)};
+ });
+ return A3(foldr,
+ step,
+ {ctor: "_Tuple2"
+ ,_0: _L.fromArray([])
+ ,_1: _L.fromArray([])},
+ pairs);
+ };
+ var intersperse = F2(function (sep,
+ xs) {
+ switch (xs.ctor)
+ {case "::":
+ var step = F2(function (x,
+ rest) {
+ return A2(_op["::"],
+ sep,
+ A2(_op["::"],x,rest));
+ });
+ var spersed = A3(foldr,
+ step,
+ _L.fromArray([]),
+ xs._1);
+ return A2(_op["::"],
+ xs._0,
+ spersed);
+ case "[]":
+ return _L.fromArray([]);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ _elm.List.values = {_op: _op
+ ,isEmpty: isEmpty
+ ,length: length
+ ,reverse: reverse
+ ,member: member
+ ,head: head
+ ,tail: tail
+ ,filter: filter
+ ,take: take
+ ,drop: drop
+ ,repeat: repeat
+ ,append: append
+ ,concat: concat
+ ,intersperse: intersperse
+ ,partition: partition
+ ,unzip: unzip
+ ,map: map
+ ,map2: map2
+ ,map3: map3
+ ,map4: map4
+ ,map5: map5
+ ,filterMap: filterMap
+ ,concatMap: concatMap
+ ,indexedMap: indexedMap
+ ,foldr: foldr
+ ,foldl: foldl
+ ,sum: sum
+ ,product: product
+ ,maximum: maximum
+ ,minimum: minimum
+ ,all: all
+ ,any: any
+ ,scanl: scanl
+ ,sort: sort
+ ,sortBy: sortBy
+ ,sortWith: sortWith};
+ return _elm.List.values;
+};
+Elm.Main = Elm.Main || {};
+Elm.Main.make = function (_elm) {
+ "use strict";
+ _elm.Main = _elm.Main || {};
+ if (_elm.Main.values)
+ return _elm.Main.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Main",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Http = Elm.Http.make(_elm),
+ $InitViewAction = Elm.InitViewAction.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Persona = Elm.Persona.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Sign = Elm.Sign.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Task = Elm.Task.make(_elm),
+ $Time = Elm.Time.make(_elm),
+ $Update = Elm.Update.make(_elm),
+ $View$Page = Elm.View.Page.make(_elm);
+ var sign = Elm.Native.Port.make(_elm).inboundSignal("sign",
+ "Json.Decode.Value",
+ function (v) {
+ return v;
+ });
+ var signCommunication = A2($Signal.map,
+ function ($) {
+ return $Sign.toServerCommunication($Sign.decodeOperation($));
+ },
+ sign);
+ var persona = Elm.Native.Port.make(_elm).outboundSignal("persona",
+ function (v) {
+ return v;
+ },
+ A2($Signal.map,
+ $Persona.toString,
+ $Persona.operations.signal));
+ var serverCommunicationsPort = Elm.Native.Task.make(_elm).performSignal("serverCommunicationsPort",
+ A2($Signal.map,
+ function (comm) {
+ return A2($Basics.flip,
+ $Task.andThen,
+ function (action) {
+ return A2($Signal.send,
+ $Update.actions.address,
+ action);
+ })($ServerCommunication.sendRequest(comm));
+ },
+ A2($Signal.merge,
+ signCommunication,
+ $ServerCommunication.serverCommunications.signal)));
+ var initView = Elm.Native.Task.make(_elm).perform(A2($Task.andThen,
+ $InitViewAction.initViewAction,
+ $Signal.send($Update.actions.address)));
+ var ready = Elm.Native.Port.make(_elm).outboundSignal("ready",
+ function (v) {
+ return v;
+ },
+ $Signal.constant("ready"));
+ var config = Elm.Native.Port.make(_elm).inbound("config",
+ "String",
+ function (v) {
+ return typeof v === "string" || typeof v === "object" && v instanceof String ? v : _U.badPort("a string",
+ v);
+ });
+ var translations = Elm.Native.Port.make(_elm).inbound("translations",
+ "String",
+ function (v) {
+ return typeof v === "string" || typeof v === "object" && v instanceof String ? v : _U.badPort("a string",
+ v);
+ });
+ var initialTime = Elm.Native.Port.make(_elm).inbound("initialTime",
+ "Time.Time",
+ function (v) {
+ return typeof v === "number" ? v : _U.badPort("a number",
+ v);
+ });
+ var update = $Signal.mergeMany(_L.fromArray([A2($Signal.map,
+ $Update.UpdateTime,
+ $Time.every(1000))
+ ,$Update.actions.signal]));
+ var model = A3($Signal.foldp,
+ $Update.updateModel,
+ A3($Model.initialModel,
+ initialTime,
+ translations,
+ config),
+ update);
+ var main = A2($Signal.map,
+ $View$Page.renderPage,
+ model);
+ _elm.Main.values = {_op: _op
+ ,main: main};
+ return _elm.Main.values;
+};
+Elm.Maybe = Elm.Maybe || {};
+Elm.Maybe.make = function (_elm) {
+ "use strict";
+ _elm.Maybe = _elm.Maybe || {};
+ if (_elm.Maybe.values)
+ return _elm.Maybe.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Maybe";
+ var withDefault = F2(function ($default,
+ maybe) {
+ switch (maybe.ctor)
+ {case "Just": return maybe._0;
+ case "Nothing":
+ return $default;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var Nothing = {ctor: "Nothing"};
+ var oneOf = function (maybes) {
+ _v2: while (true) {
+ switch (maybes.ctor)
+ {case "::":
+ switch (maybes._0.ctor)
+ {case "Just": return maybes._0;
+ case "Nothing":
+ var _v8 = maybes._1;
+ maybes = _v8;
+ continue _v2;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "[]": return Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ };
+ var andThen = F2(function (maybeValue,
+ callback) {
+ switch (maybeValue.ctor)
+ {case "Just":
+ return callback(maybeValue._0);
+ case "Nothing": return Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var Just = function (a) {
+ return {ctor: "Just",_0: a};
+ };
+ var map = F2(function (f,
+ maybe) {
+ switch (maybe.ctor)
+ {case "Just":
+ return Just(f(maybe._0));
+ case "Nothing": return Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ _elm.Maybe.values = {_op: _op
+ ,andThen: andThen
+ ,map: map
+ ,withDefault: withDefault
+ ,oneOf: oneOf
+ ,Just: Just
+ ,Nothing: Nothing};
+ return _elm.Maybe.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ if (_elm.Model.values)
+ return _elm.Model.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model",
+ $Basics = Elm.Basics.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Config = Elm.Model.Config.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$View = Elm.Model.View.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Time = Elm.Time.make(_elm);
+ var initialModel = F3(function (initialTime,
+ translationsValue,
+ configValue) {
+ return {_: {}
+ ,config: function () {
+ var _v3 = A2($Json$Decode.decodeString,
+ $Model$Config.configDecoder,
+ configValue);
+ switch (_v3.ctor)
+ {case "Err": return {_: {}
+ ,currency: ""};
+ case "Ok": return _v3._0;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()
+ ,currentTime: initialTime
+ ,translations: function () {
+ var _v0 = A2($Json$Decode.decodeString,
+ $Model$Translations.translationsDecoder,
+ translationsValue);
+ switch (_v0.ctor)
+ {case "Err":
+ return _L.fromArray([]);
+ case "Ok": return _v0._0;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()
+ ,view: $Model$View.LoadingView};
+ });
+ var Model = F4(function (a,
+ b,
+ c,
+ d) {
+ return {_: {}
+ ,config: d
+ ,currentTime: b
+ ,translations: c
+ ,view: a};
+ });
+ _elm.Model.values = {_op: _op
+ ,initialModel: initialModel
+ ,Model: Model};
+ return _elm.Model.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.Config = Elm.Model.Config || {};
+Elm.Model.Config.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.Config = _elm.Model.Config || {};
+ if (_elm.Model.Config.values)
+ return _elm.Model.Config.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.Config",
+ $Basics = Elm.Basics.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var defaultConfig = {_: {}
+ ,currency: "€"};
+ var Config = function (a) {
+ return {_: {},currency: a};
+ };
+ var configDecoder = A2($Json$Decode.object1,
+ Config,
+ A2($Json$Decode._op[":="],
+ "currency",
+ $Json$Decode.string));
+ _elm.Model.Config.values = {_op: _op
+ ,configDecoder: configDecoder
+ ,Config: Config};
+ return _elm.Model.Config.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.Date = Elm.Model.Date || {};
+Elm.Model.Date.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.Date = _elm.Model.Date || {};
+ if (_elm.Model.Date.values)
+ return _elm.Model.Date.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.Date",
+ $Basics = Elm.Basics.make(_elm),
+ $Date = Elm.Date.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Time = Elm.Time.make(_elm);
+ var dateDecoder = A2($Json$Decode.customDecoder,
+ $Json$Decode.string,
+ $Date.fromString);
+ var timeDecoder = A2($Json$Decode.map,
+ $Date.toTime,
+ dateDecoder);
+ _elm.Model.Date.values = {_op: _op
+ ,timeDecoder: timeDecoder
+ ,dateDecoder: dateDecoder};
+ return _elm.Model.Date.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.Income = Elm.Model.Income || {};
+Elm.Model.Income.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.Income = _elm.Model.Income || {};
+ if (_elm.Model.Income.values)
+ return _elm.Model.Income.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.Income",
+ $Basics = Elm.Basics.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Date = Elm.Model.Date.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Time = Elm.Time.make(_elm),
+ $Utils$Maybe = Elm.Utils.Maybe.make(_elm);
+ var durationIncome = function (_v0) {
+ var $ = _v0,
+ duration = $._0,
+ income = $._1;
+ return $Basics.truncate(duration * $Basics.toFloat(income) / ($Time.hour * 24 * 365 / 12));
+ };
+ var getIncomesWithDuration = function (incomes) {
+ switch (incomes.ctor)
+ {case "::":
+ switch (incomes._1.ctor)
+ {case "::":
+ return A2($List._op["::"],
+ {ctor: "_Tuple2"
+ ,_0: incomes._1._0.creation - incomes._0.creation
+ ,_1: incomes._0.amount},
+ getIncomesWithDuration(A2($List._op["::"],
+ incomes._1._0,
+ incomes._1._1)));}
+ break;}
+ return _L.fromArray([]);
+ };
+ var cumulativeIncome = F2(function (currentTime,
+ incomes) {
+ return $List.sum($List.map(durationIncome)(getIncomesWithDuration(A2($Basics._op["++"],
+ incomes,
+ _L.fromArray([{_: {}
+ ,amount: 0
+ ,creation: currentTime}])))));
+ });
+ var getIncomesAt = F2(function (time,
+ incomes) {
+ _v6: while (true) {
+ switch (incomes.ctor)
+ {case "::":
+ switch (incomes._1.ctor)
+ {case "::":
+ if (_U.cmp(incomes._0.creation,
+ time) < 0 && _U.cmp(incomes._1._0.creation,
+ time) > 0)
+ return $Maybe.Just({_: {}
+ ,amount: incomes._1._0.amount
+ ,creation: time}); else {
+ var _v12 = time,
+ _v13 = A2($List._op["::"],
+ incomes._1._0,
+ incomes._1._1);
+ time = _v12;
+ incomes = _v13;
+ continue _v6;
+ }
+ case "[]":
+ return _U.cmp(incomes._0.creation,
+ time) < 0 ? $Maybe.Just({_: {}
+ ,amount: incomes._0.amount
+ ,creation: time}) : $Maybe.Nothing;}
+ break;
+ case "[]":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }
+ });
+ var getOrderedIncomesSince = F2(function (time,
+ incomes) {
+ var orderedIncomesSince = A2($List.filter,
+ function (income) {
+ return _U.cmp(income.creation,
+ time) > -1;
+ },
+ incomes);
+ var mbStarterIncome = A2(getIncomesAt,
+ time,
+ incomes);
+ return A2($Basics._op["++"],
+ $Utils$Maybe.maybeToList(mbStarterIncome),
+ orderedIncomesSince);
+ });
+ var cumulativeIncomesSince = F3(function (currentTime,
+ since,
+ incomes) {
+ return A2(cumulativeIncome,
+ currentTime,
+ A2(getOrderedIncomesSince,
+ since,
+ incomes));
+ });
+ var incomeDefinedForAll = function (usersIncomes) {
+ var firstIncomes = A2($List.map,
+ function ($) {
+ return $List.head($List.sortBy(function (_) {
+ return _.creation;
+ })($));
+ },
+ usersIncomes);
+ return A2($List.all,
+ $Utils$Maybe.isJust,
+ firstIncomes) ? function ($) {
+ return $List.head($List.reverse($List.sort($List.map(function (_) {
+ return _.creation;
+ })($Utils$Maybe.catMaybes($)))));
+ }(firstIncomes) : $Maybe.Nothing;
+ };
+ var Income = F2(function (a,b) {
+ return {_: {}
+ ,amount: b
+ ,creation: a};
+ });
+ var incomeDecoder = A3($Json$Decode.object2,
+ Income,
+ A2($Json$Decode._op[":="],
+ "creation",
+ $Model$Date.timeDecoder),
+ A2($Json$Decode._op[":="],
+ "amount",
+ $Json$Decode.$int));
+ _elm.Model.Income.values = {_op: _op
+ ,incomeDecoder: incomeDecoder
+ ,incomeDefinedForAll: incomeDefinedForAll
+ ,cumulativeIncomesSince: cumulativeIncomesSince
+ ,Income: Income};
+ return _elm.Model.Income.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.Payer = Elm.Model.Payer || {};
+Elm.Model.Payer.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.Payer = _elm.Model.Payer || {};
+ if (_elm.Model.Payer.values)
+ return _elm.Model.Payer.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.Payer",
+ $Basics = Elm.Basics.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Income = Elm.Model.Income.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Time = Elm.Time.make(_elm),
+ $Utils$Dict = Elm.Utils.Dict.make(_elm);
+ var getFinalDiff = F2(function (maxRatio,
+ payer) {
+ var postIncomeDiff = $Basics.truncate(-1 * (maxRatio - payer.ratio) * $Basics.toFloat(payer.cumulativeIncome));
+ return postIncomeDiff + payer.preIncomePaymentSum;
+ });
+ var getPostPaymentPayer = F3(function (currentTime,
+ since,
+ payer) {
+ var cumulativeIncome = A3($Model$Income.cumulativeIncomesSince,
+ currentTime,
+ since,
+ payer.incomes);
+ return {_: {}
+ ,cumulativeIncome: cumulativeIncome
+ ,preIncomePaymentSum: payer.preIncomePaymentSum
+ ,ratio: $Basics.toFloat(payer.postIncomePaymentSum) / $Basics.toFloat(cumulativeIncome)};
+ });
+ var PostPaymentPayer = F3(function (a,
+ b,
+ c) {
+ return {_: {}
+ ,cumulativeIncome: b
+ ,preIncomePaymentSum: a
+ ,ratio: c};
+ });
+ var exceedingPayersFromAmounts = function (userAmounts) {
+ var mbMinAmount = function ($) {
+ return $List.minimum($List.map($Basics.snd)($));
+ }(userAmounts);
+ switch (mbMinAmount.ctor)
+ {case "Just":
+ return $List.filter(function (payer) {
+ return _U.cmp(payer.amount,
+ 0) > 0;
+ })($List.map(function (userAmount) {
+ return {_: {}
+ ,amount: $Basics.snd(userAmount) - mbMinAmount._0
+ ,userId: $Basics.fst(userAmount)};
+ })(userAmounts));
+ case "Nothing":
+ return _L.fromArray([]);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var payersIncomeDefinedForAll = function (payers) {
+ return $Model$Income.incomeDefinedForAll(function ($) {
+ return $List.map(function ($) {
+ return function (_) {
+ return _.incomes;
+ }($Basics.snd($));
+ })($Dict.toList($));
+ }(payers));
+ };
+ var getOrderedExceedingPayers = F2(function (currentTime,
+ payers) {
+ var exceedingPayersOnPreIncome = exceedingPayersFromAmounts($Dict.toList($Utils$Dict.mapValues(function (_) {
+ return _.preIncomePaymentSum;
+ })(payers)));
+ var _v2 = payersIncomeDefinedForAll(payers);
+ switch (_v2.ctor)
+ {case "Just":
+ var postPaymentPayers = $Utils$Dict.mapValues(A2(getPostPaymentPayer,
+ currentTime,
+ _v2._0))(payers);
+ var mbMaxRatio = $List.maximum($List.map(function ($) {
+ return function (_) {
+ return _.ratio;
+ }($Basics.snd($));
+ })($Dict.toList(postPaymentPayers)));
+ switch (mbMaxRatio.ctor)
+ {case "Just":
+ return exceedingPayersFromAmounts($Dict.toList($Utils$Dict.mapValues(getFinalDiff(mbMaxRatio._0))(postPaymentPayers)));
+ case "Nothing":
+ return exceedingPayersOnPreIncome;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "Nothing":
+ return exceedingPayersOnPreIncome;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var ExceedingPayer = F2(function (a,
+ b) {
+ return {_: {}
+ ,amount: b
+ ,userId: a};
+ });
+ var updatePayers = F4(function (payers,
+ userId,
+ creation,
+ amountDiff) {
+ return A2($Dict.update,
+ userId,
+ function (mbPayer) {
+ switch (mbPayer.ctor)
+ {case "Just":
+ var postIncome = $Maybe.withDefault(false)($Maybe.map(function (date) {
+ return _U.cmp(creation,
+ date) > 0;
+ })(payersIncomeDefinedForAll(payers)));
+ return postIncome ? $Maybe.Just(_U.replace([["postIncomePaymentSum"
+ ,mbPayer._0.postIncomePaymentSum + amountDiff]],
+ mbPayer._0)) : $Maybe.Just(_U.replace([["preIncomePaymentSum"
+ ,mbPayer._0.preIncomePaymentSum + amountDiff]],
+ mbPayer._0));
+ case "Nothing":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ })(payers);
+ });
+ var Payer = F3(function (a,
+ b,
+ c) {
+ return {_: {}
+ ,incomes: c
+ ,postIncomePaymentSum: b
+ ,preIncomePaymentSum: a};
+ });
+ var payerDecoder = A3($Json$Decode.object2,
+ F2(function (v0,v1) {
+ return {ctor: "_Tuple2"
+ ,_0: v0
+ ,_1: v1};
+ }),
+ A2($Json$Decode._op[":="],
+ "userId",
+ $Model$User.userIdDecoder),
+ A4($Json$Decode.object3,
+ Payer,
+ A2($Json$Decode._op[":="],
+ "preIncomePaymentSum",
+ $Json$Decode.$int),
+ A2($Json$Decode._op[":="],
+ "postIncomePaymentSum",
+ $Json$Decode.$int),
+ A2($Json$Decode._op[":="],
+ "incomes",
+ $Json$Decode.list($Model$Income.incomeDecoder))));
+ var payersDecoder = A2($Json$Decode.map,
+ $Dict.fromList,
+ $Json$Decode.list(payerDecoder));
+ _elm.Model.Payer.values = {_op: _op
+ ,payersDecoder: payersDecoder
+ ,updatePayers: updatePayers
+ ,getOrderedExceedingPayers: getOrderedExceedingPayers
+ ,Payer: Payer
+ ,ExceedingPayer: ExceedingPayer};
+ return _elm.Model.Payer.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.Payment = Elm.Model.Payment || {};
+Elm.Model.Payment.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.Payment = _elm.Model.Payment || {};
+ if (_elm.Model.Payment.values)
+ return _elm.Model.Payment.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.Payment",
+ $Basics = Elm.Basics.make(_elm),
+ $Date = Elm.Date.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Date = Elm.Model.Date.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var paymentIdDecoder = $Json$Decode.$int;
+ var Payment = F5(function (a,
+ b,
+ c,
+ d,
+ e) {
+ return {_: {}
+ ,cost: d
+ ,creation: b
+ ,id: a
+ ,name: c
+ ,userId: e};
+ });
+ var paymentDecoder = A6($Json$Decode.object5,
+ Payment,
+ A2($Json$Decode._op[":="],
+ "id",
+ paymentIdDecoder),
+ A2($Json$Decode._op[":="],
+ "creation",
+ $Model$Date.dateDecoder),
+ A2($Json$Decode._op[":="],
+ "name",
+ $Json$Decode.string),
+ A2($Json$Decode._op[":="],
+ "cost",
+ $Json$Decode.$int),
+ A2($Json$Decode._op[":="],
+ "userId",
+ $Model$User.userIdDecoder));
+ var paymentsDecoder = $Json$Decode.list(paymentDecoder);
+ var perPage = 8;
+ _elm.Model.Payment.values = {_op: _op
+ ,perPage: perPage
+ ,paymentsDecoder: paymentsDecoder
+ ,paymentIdDecoder: paymentIdDecoder
+ ,Payment: Payment};
+ return _elm.Model.Payment.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.Translations = Elm.Model.Translations || {};
+Elm.Model.Translations.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.Translations = _elm.Model.Translations || {};
+ if (_elm.Model.Translations.values)
+ return _elm.Model.Translations.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.Translations",
+ $Basics = Elm.Basics.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm);
+ var replacePart = F2(function (values,
+ part) {
+ switch (part.ctor)
+ {case "Order":
+ return $Maybe.withDefault(A2($Basics._op["++"],
+ "{",
+ A2($Basics._op["++"],
+ $Basics.toString(part._0),
+ "}")))($List.head($List.drop(part._0 - 1)(values)));
+ case "Str": return part._0;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var Str = function (a) {
+ return {ctor: "Str",_0: a};
+ };
+ var Order = function (a) {
+ return {ctor: "Order",_0: a};
+ };
+ var partDecoderWithTag = function (tag) {
+ switch (tag)
+ {case "Order":
+ return A2($Json$Decode.object1,
+ Order,
+ A2($Json$Decode._op[":="],
+ "contents",
+ $Json$Decode.$int));
+ case "Str":
+ return A2($Json$Decode.object1,
+ Str,
+ A2($Json$Decode._op[":="],
+ "contents",
+ $Json$Decode.string));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var partDecoder = A2($Json$Decode.andThen,
+ A2($Json$Decode._op[":="],
+ "tag",
+ $Json$Decode.string),
+ partDecoderWithTag);
+ var getTranslation = F2(function (key,
+ translations) {
+ return $Maybe.map(function (_) {
+ return _.message;
+ })($List.head($List.filter(function (translation) {
+ return _U.eq(translation.key,
+ key);
+ })(translations)));
+ });
+ var getParamMessage = F3(function (values,
+ key,
+ translations) {
+ return $Maybe.withDefault(key)($Maybe.map(function (parts) {
+ return $String.concat(A2($List.map,
+ replacePart(values),
+ parts));
+ })(A2(getTranslation,
+ key,
+ translations)));
+ });
+ var getMessage = getParamMessage(_L.fromArray([]));
+ var Translation = F2(function (a,
+ b) {
+ return {_: {}
+ ,key: a
+ ,message: b};
+ });
+ var translationDecoder = A3($Json$Decode.object2,
+ Translation,
+ A2($Json$Decode._op[":="],
+ "key",
+ $Json$Decode.string),
+ A2($Json$Decode._op[":="],
+ "message",
+ $Json$Decode.list(partDecoder)));
+ var translationsDecoder = $Json$Decode.list(translationDecoder);
+ _elm.Model.Translations.values = {_op: _op
+ ,translationsDecoder: translationsDecoder
+ ,getMessage: getMessage
+ ,getParamMessage: getParamMessage
+ ,Translation: Translation};
+ return _elm.Model.Translations.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.User = Elm.Model.User || {};
+Elm.Model.User.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.User = _elm.Model.User || {};
+ if (_elm.Model.User.values)
+ return _elm.Model.User.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.User",
+ $Basics = Elm.Basics.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var getUserName = F2(function (users,
+ userId) {
+ return $Maybe.map(function (_) {
+ return _.name;
+ })(A2($Dict.get,userId,users));
+ });
+ var userIdDecoder = $Json$Decode.$int;
+ var User = F2(function (a,b) {
+ return {_: {}
+ ,email: b
+ ,name: a};
+ });
+ var userDecoder = A3($Json$Decode.object2,
+ User,
+ A2($Json$Decode._op[":="],
+ "name",
+ $Json$Decode.string),
+ A2($Json$Decode._op[":="],
+ "email",
+ $Json$Decode.string));
+ var userWithIdDecoder = A3($Json$Decode.object2,
+ F2(function (v0,v1) {
+ return {ctor: "_Tuple2"
+ ,_0: v0
+ ,_1: v1};
+ }),
+ A2($Json$Decode._op[":="],
+ "id",
+ userIdDecoder),
+ userDecoder);
+ var usersDecoder = A2($Json$Decode.map,
+ $Dict.fromList,
+ $Json$Decode.list(userWithIdDecoder));
+ _elm.Model.User.values = {_op: _op
+ ,usersDecoder: usersDecoder
+ ,userDecoder: userDecoder
+ ,userIdDecoder: userIdDecoder
+ ,getUserName: getUserName
+ ,User: User};
+ return _elm.Model.User.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ if (_elm.Model.View.values)
+ return _elm.Model.View.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Model$View$SignInView = Elm.Model.View.SignInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var LoggedInView = function (a) {
+ return {ctor: "LoggedInView"
+ ,_0: a};
+ };
+ var SignInView = function (a) {
+ return {ctor: "SignInView"
+ ,_0: a};
+ };
+ var LoadingView = {ctor: "LoadingView"};
+ _elm.Model.View.values = {_op: _op
+ ,LoadingView: LoadingView
+ ,SignInView: SignInView
+ ,LoggedInView: LoggedInView};
+ return _elm.Model.View.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.LoggedIn = Elm.Model.View.LoggedIn || {};
+Elm.Model.View.LoggedIn.Account = Elm.Model.View.LoggedIn.Account || {};
+Elm.Model.View.LoggedIn.Account.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ _elm.Model.View.LoggedIn = _elm.Model.View.LoggedIn || {};
+ _elm.Model.View.LoggedIn.Account = _elm.Model.View.LoggedIn.Account || {};
+ if (_elm.Model.View.LoggedIn.Account.values)
+ return _elm.Model.View.LoggedIn.Account.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View.LoggedIn.Account",
+ $Basics = Elm.Basics.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payer = Elm.Model.Payer.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Utils$Dict = Elm.Utils.Dict.make(_elm),
+ $Utils$Validation = Elm.Utils.Validation.make(_elm);
+ var validateIncome = F2(function (amount,
+ translations) {
+ return A2($Basics.flip,
+ $Result.andThen,
+ A2($Utils$Validation.validateNumber,
+ A2($Model$Translations.getMessage,
+ "IncomeMustBePositiveNumber",
+ translations),
+ function (number) {
+ return _U.cmp(number,0) > 0;
+ }))($Utils$Validation.validateNonEmpty(A2($Model$Translations.getMessage,
+ "IncomeRequired",
+ translations))(amount));
+ });
+ var initIncomeEdition = function (income) {
+ return {_: {}
+ ,error: $Maybe.Nothing
+ ,income: $Basics.toString(income)};
+ };
+ var IncomeEdition = F2(function (a,
+ b) {
+ return {_: {}
+ ,error: b
+ ,income: a};
+ });
+ var getCurrentIncome = function (account) {
+ var _v0 = A2($Dict.get,
+ account.me,
+ account.payers);
+ switch (_v0.ctor)
+ {case "Just":
+ return $Maybe.map(function (_) {
+ return _.amount;
+ })($List.head($List.reverse($List.sortBy(function (_) {
+ return _.creation;
+ })(_v0._0.incomes))));
+ case "Nothing":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var initAccount = F2(function (me,
+ payers) {
+ return {_: {}
+ ,incomeEdition: $Maybe.Nothing
+ ,me: me
+ ,payers: $Utils$Dict.mapValues(function (payer) {
+ return _U.replace([["incomes"
+ ,A2($List.sortBy,
+ function (_) {
+ return _.creation;
+ },
+ payer.incomes)]],
+ payer);
+ })(payers)
+ ,visibleDetail: false};
+ });
+ var Account = F4(function (a,
+ b,
+ c,
+ d) {
+ return {_: {}
+ ,incomeEdition: d
+ ,me: a
+ ,payers: b
+ ,visibleDetail: c};
+ });
+ _elm.Model.View.LoggedIn.Account.values = {_op: _op
+ ,initAccount: initAccount
+ ,initIncomeEdition: initIncomeEdition
+ ,getCurrentIncome: getCurrentIncome
+ ,validateIncome: validateIncome
+ ,Account: Account
+ ,IncomeEdition: IncomeEdition};
+ return _elm.Model.View.LoggedIn.Account.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.LoggedIn = Elm.Model.View.LoggedIn || {};
+Elm.Model.View.LoggedIn.Add = Elm.Model.View.LoggedIn.Add || {};
+Elm.Model.View.LoggedIn.Add.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ _elm.Model.View.LoggedIn = _elm.Model.View.LoggedIn || {};
+ _elm.Model.View.LoggedIn.Add = _elm.Model.View.LoggedIn.Add || {};
+ if (_elm.Model.View.LoggedIn.Add.values)
+ return _elm.Model.View.LoggedIn.Add.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View.LoggedIn.Add",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Utils$Validation = Elm.Utils.Validation.make(_elm);
+ var Monthly = {ctor: "Monthly"};
+ var Punctual = {ctor: "Punctual"};
+ var validateCost = F2(function (cost,
+ translations) {
+ return A2($Basics.flip,
+ $Result.andThen,
+ A2($Utils$Validation.validateNumber,
+ A2($Model$Translations.getMessage,
+ "CostMustBeNonNullNumber",
+ translations),
+ F2(function (x,y) {
+ return !_U.eq(x,y);
+ })(0)))($Utils$Validation.validateNonEmpty(A2($Model$Translations.getMessage,
+ "CostRequired",
+ translations))(cost));
+ });
+ var validateName = F2(function (name,
+ translations) {
+ return $Utils$Validation.validateNonEmpty(A2($Model$Translations.getMessage,
+ "CategoryRequired",
+ translations))(name);
+ });
+ var initAddPayment = function (frequency) {
+ return {_: {}
+ ,cost: ""
+ ,costError: $Maybe.Nothing
+ ,frequency: frequency
+ ,name: ""
+ ,nameError: $Maybe.Nothing};
+ };
+ var AddPayment = F5(function (a,
+ b,
+ c,
+ d,
+ e) {
+ return {_: {}
+ ,cost: c
+ ,costError: d
+ ,frequency: e
+ ,name: a
+ ,nameError: b};
+ });
+ _elm.Model.View.LoggedIn.Add.values = {_op: _op
+ ,initAddPayment: initAddPayment
+ ,validateName: validateName
+ ,validateCost: validateCost
+ ,AddPayment: AddPayment
+ ,Punctual: Punctual
+ ,Monthly: Monthly};
+ return _elm.Model.View.LoggedIn.Add.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.LoggedIn = Elm.Model.View.LoggedIn || {};
+Elm.Model.View.LoggedIn.Edition = Elm.Model.View.LoggedIn.Edition || {};
+Elm.Model.View.LoggedIn.Edition.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ _elm.Model.View.LoggedIn = _elm.Model.View.LoggedIn || {};
+ _elm.Model.View.LoggedIn.Edition = _elm.Model.View.LoggedIn.Edition || {};
+ if (_elm.Model.View.LoggedIn.Edition.values)
+ return _elm.Model.View.LoggedIn.Edition.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View.LoggedIn.Edition",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ _elm.Model.View.LoggedIn.Edition.values = {_op: _op};
+ return _elm.Model.View.LoggedIn.Edition.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.LoggedIn = Elm.Model.View.LoggedIn || {};
+Elm.Model.View.LoggedIn.Monthly = Elm.Model.View.LoggedIn.Monthly || {};
+Elm.Model.View.LoggedIn.Monthly.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ _elm.Model.View.LoggedIn = _elm.Model.View.LoggedIn || {};
+ _elm.Model.View.LoggedIn.Monthly = _elm.Model.View.LoggedIn.Monthly || {};
+ if (_elm.Model.View.LoggedIn.Monthly.values)
+ return _elm.Model.View.LoggedIn.Monthly.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View.LoggedIn.Monthly",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var initMonthly = function (payments) {
+ return {_: {}
+ ,payments: payments
+ ,visibleDetail: false};
+ };
+ var Monthly = F2(function (a,
+ b) {
+ return {_: {}
+ ,payments: a
+ ,visibleDetail: b};
+ });
+ _elm.Model.View.LoggedIn.Monthly.values = {_op: _op
+ ,initMonthly: initMonthly
+ ,Monthly: Monthly};
+ return _elm.Model.View.LoggedIn.Monthly.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.LoggedInView = Elm.Model.View.LoggedInView || {};
+Elm.Model.View.LoggedInView.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ _elm.Model.View.LoggedInView = _elm.Model.View.LoggedInView || {};
+ if (_elm.Model.View.LoggedInView.values)
+ return _elm.Model.View.LoggedInView.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View.LoggedInView",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payer = Elm.Model.Payer.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View$LoggedIn$Account = Elm.Model.View.LoggedIn.Account.make(_elm),
+ $Model$View$LoggedIn$Add = Elm.Model.View.LoggedIn.Add.make(_elm),
+ $Model$View$LoggedIn$Edition = Elm.Model.View.LoggedIn.Edition.make(_elm),
+ $Model$View$LoggedIn$Monthly = Elm.Model.View.LoggedIn.Monthly.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var initLoggedInView = F6(function (users,
+ me,
+ monthlyPayments,
+ payments,
+ paymentsCount,
+ payers) {
+ return {_: {}
+ ,account: A2($Model$View$LoggedIn$Account.initAccount,
+ me,
+ payers)
+ ,add: $Model$View$LoggedIn$Add.initAddPayment($Model$View$LoggedIn$Add.Punctual)
+ ,currentPage: 1
+ ,monthly: $Model$View$LoggedIn$Monthly.initMonthly(monthlyPayments)
+ ,paymentEdition: $Maybe.Nothing
+ ,payments: payments
+ ,paymentsCount: paymentsCount
+ ,users: users};
+ });
+ var LoggedInView = F8(function (a,
+ b,
+ c,
+ d,
+ e,
+ f,
+ g,
+ h) {
+ return {_: {}
+ ,account: d
+ ,add: b
+ ,currentPage: h
+ ,monthly: c
+ ,paymentEdition: g
+ ,payments: e
+ ,paymentsCount: f
+ ,users: a};
+ });
+ _elm.Model.View.LoggedInView.values = {_op: _op
+ ,initLoggedInView: initLoggedInView
+ ,LoggedInView: LoggedInView};
+ return _elm.Model.View.LoggedInView.values;
+};
+Elm.Model = Elm.Model || {};
+Elm.Model.View = Elm.Model.View || {};
+Elm.Model.View.SignInView = Elm.Model.View.SignInView || {};
+Elm.Model.View.SignInView.make = function (_elm) {
+ "use strict";
+ _elm.Model = _elm.Model || {};
+ _elm.Model.View = _elm.Model.View || {};
+ _elm.Model.View.SignInView = _elm.Model.View.SignInView || {};
+ if (_elm.Model.View.SignInView.values)
+ return _elm.Model.View.SignInView.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Model.View.SignInView",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var initSignInView = {_: {}
+ ,login: ""
+ ,result: $Maybe.Nothing};
+ var SignInView = F2(function (a,
+ b) {
+ return {_: {}
+ ,login: a
+ ,result: b};
+ });
+ _elm.Model.View.SignInView.values = {_op: _op
+ ,initSignInView: initSignInView
+ ,SignInView: SignInView};
+ return _elm.Model.View.SignInView.values;
+};
+Elm.Native.Array = {};
+Elm.Native.Array.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Array = localRuntime.Native.Array || {};
+ if (localRuntime.Native.Array.values)
+ {
+ return localRuntime.Native.Array.values;
+ }
+ if ('values' in Elm.Native.Array)
+ {
+ return localRuntime.Native.Array.values = Elm.Native.Array.values;
+ }
+
+ var List = Elm.Native.List.make(localRuntime);
+
+ // A RRB-Tree has two distinct data types.
+ // Leaf -> "height" is always 0
+ // "table" is an array of elements
+ // Node -> "height" is always greater than 0
+ // "table" is an array of child nodes
+ // "lengths" is an array of accumulated lengths of the child nodes
+
+ // M is the maximal table size. 32 seems fast. E is the allowed increase
+ // of search steps when concatting to find an index. Lower values will
+ // decrease balancing, but will increase search steps.
+ var M = 32;
+ var E = 2;
+
+ // An empty array.
+ var empty = {
+ ctor: "_Array",
+ height: 0,
+ table: new Array()
+ };
+
+
+ function get(i, array)
+ {
+ if (i < 0 || i >= length(array))
+ {
+ throw new Error(
+ "Index " + i + " is out of range. Check the length of " +
+ "your array first or use getMaybe or getWithDefault.");
+ }
+ return unsafeGet(i, array);
+ }
+
+
+ function unsafeGet(i, array)
+ {
+ for (var x = array.height; x > 0; x--)
+ {
+ var slot = i >> (x * 5);
+ while (array.lengths[slot] <= i)
+ {
+ slot++;
+ }
+ if (slot > 0)
+ {
+ i -= array.lengths[slot - 1];
+ }
+ array = array.table[slot];
+ }
+ return array.table[i];
+ }
+
+
+ // Sets the value at the index i. Only the nodes leading to i will get
+ // copied and updated.
+ function set(i, item, array)
+ {
+ if (i < 0 || length(array) <= i)
+ {
+ return array;
+ }
+ return unsafeSet(i, item, array);
+ }
+
+
+ function unsafeSet(i, item, array)
+ {
+ array = nodeCopy(array);
+
+ if (array.height == 0)
+ {
+ array.table[i] = item;
+ }
+ else
+ {
+ var slot = getSlot(i, array);
+ if (slot > 0)
+ {
+ i -= array.lengths[slot - 1];
+ }
+ array.table[slot] = unsafeSet(i, item, array.table[slot]);
+ }
+ return array;
+ }
+
+
+ function initialize(len, f)
+ {
+ if (len == 0)
+ {
+ return empty;
+ }
+ var h = Math.floor( Math.log(len) / Math.log(M) );
+ return initialize_(f, h, 0, len);
+ }
+
+ function initialize_(f, h, from, to)
+ {
+ if (h == 0)
+ {
+ var table = new Array((to - from) % (M + 1));
+ for (var i = 0; i < table.length; i++)
+ {
+ table[i] = f(from + i);
+ }
+ return {
+ ctor: "_Array",
+ height: 0,
+ table: table
+ };
+ }
+
+ var step = Math.pow(M, h);
+ var table = new Array(Math.ceil((to - from) / step));
+ var lengths = new Array(table.length);
+ for (var i = 0; i < table.length; i++)
+ {
+ table[i] = initialize_(f, h - 1, from + (i * step), Math.min(from + ((i + 1) * step), to));
+ lengths[i] = length(table[i]) + (i > 0 ? lengths[i-1] : 0);
+ }
+ return {
+ ctor: "_Array",
+ height: h,
+ table: table,
+ lengths: lengths
+ };
+ }
+
+ function fromList(list)
+ {
+ if (list == List.Nil)
+ {
+ return empty;
+ }
+
+ // Allocate M sized blocks (table) and write list elements to it.
+ var table = new Array(M);
+ var nodes = new Array();
+ var i = 0;
+
+ while (list.ctor !== '[]')
+ {
+ table[i] = list._0;
+ list = list._1;
+ i++;
+
+ // table is full, so we can push a leaf containing it into the
+ // next node.
+ if (i == M)
+ {
+ var leaf = {
+ ctor: "_Array",
+ height: 0,
+ table: table
+ };
+ fromListPush(leaf, nodes);
+ table = new Array(M);
+ i = 0;
+ }
+ }
+
+ // Maybe there is something left on the table.
+ if (i > 0)
+ {
+ var leaf = {
+ ctor: "_Array",
+ height: 0,
+ table: table.splice(0,i)
+ };
+ fromListPush(leaf, nodes);
+ }
+
+ // Go through all of the nodes and eventually push them into higher nodes.
+ for (var h = 0; h < nodes.length - 1; h++)
+ {
+ if (nodes[h].table.length > 0)
+ {
+ fromListPush(nodes[h], nodes);
+ }
+ }
+
+ var head = nodes[nodes.length - 1];
+ if (head.height > 0 && head.table.length == 1)
+ {
+ return head.table[0];
+ }
+ else
+ {
+ return head;
+ }
+ }
+
+ // Push a node into a higher node as a child.
+ function fromListPush(toPush, nodes)
+ {
+ var h = toPush.height;
+
+ // Maybe the node on this height does not exist.
+ if (nodes.length == h)
+ {
+ var node = {
+ ctor: "_Array",
+ height: h + 1,
+ table: new Array(),
+ lengths: new Array()
+ };
+ nodes.push(node);
+ }
+
+ nodes[h].table.push(toPush);
+ var len = length(toPush);
+ if (nodes[h].lengths.length > 0)
+ {
+ len += nodes[h].lengths[nodes[h].lengths.length - 1];
+ }
+ nodes[h].lengths.push(len);
+
+ if (nodes[h].table.length == M)
+ {
+ fromListPush(nodes[h], nodes);
+ nodes[h] = {
+ ctor: "_Array",
+ height: h + 1,
+ table: new Array(),
+ lengths: new Array()
+ };
+ }
+ }
+
+ // Pushes an item via push_ to the bottom right of a tree.
+ function push(item, a)
+ {
+ var pushed = push_(item, a);
+ if (pushed !== null)
+ {
+ return pushed;
+ }
+
+ var newTree = create(item, a.height);
+ return siblise(a, newTree);
+ }
+
+ // Recursively tries to push an item to the bottom-right most
+ // tree possible. If there is no space left for the item,
+ // null will be returned.
+ function push_(item, a)
+ {
+ // Handle resursion stop at leaf level.
+ if (a.height == 0)
+ {
+ if (a.table.length < M)
+ {
+ var newA = {
+ ctor: "_Array",
+ height: 0,
+ table: a.table.slice()
+ };
+ newA.table.push(item);
+ return newA;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ // Recursively push
+ var pushed = push_(item, botRight(a));
+
+ // There was space in the bottom right tree, so the slot will
+ // be updated.
+ if (pushed != null)
+ {
+ var newA = nodeCopy(a);
+ newA.table[newA.table.length - 1] = pushed;
+ newA.lengths[newA.lengths.length - 1]++;
+ return newA;
+ }
+
+ // When there was no space left, check if there is space left
+ // for a new slot with a tree which contains only the item
+ // at the bottom.
+ if (a.table.length < M)
+ {
+ var newSlot = create(item, a.height - 1);
+ var newA = nodeCopy(a);
+ newA.table.push(newSlot);
+ newA.lengths.push(newA.lengths[newA.lengths.length - 1] + length(newSlot));
+ return newA;
+ }
+ else
+ {
+ return null;
+ }
+ }
+
+ // Converts an array into a list of elements.
+ function toList(a)
+ {
+ return toList_(List.Nil, a);
+ }
+
+ function toList_(list, a)
+ {
+ for (var i = a.table.length - 1; i >= 0; i--)
+ {
+ list =
+ a.height == 0
+ ? List.Cons(a.table[i], list)
+ : toList_(list, a.table[i]);
+ }
+ return list;
+ }
+
+ // Maps a function over the elements of an array.
+ function map(f, a)
+ {
+ var newA = {
+ ctor: "_Array",
+ height: a.height,
+ table: new Array(a.table.length)
+ };
+ if (a.height > 0)
+ {
+ newA.lengths = a.lengths;
+ }
+ for (var i = 0; i < a.table.length; i++)
+ {
+ newA.table[i] =
+ a.height == 0
+ ? f(a.table[i])
+ : map(f, a.table[i]);
+ }
+ return newA;
+ }
+
+ // Maps a function over the elements with their index as first argument.
+ function indexedMap(f, a)
+ {
+ return indexedMap_(f, a, 0);
+ }
+
+ function indexedMap_(f, a, from)
+ {
+ var newA = {
+ ctor: "_Array",
+ height: a.height,
+ table: new Array(a.table.length)
+ };
+ if (a.height > 0)
+ {
+ newA.lengths = a.lengths;
+ }
+ for (var i = 0; i < a.table.length; i++)
+ {
+ newA.table[i] =
+ a.height == 0
+ ? A2(f, from + i, a.table[i])
+ : indexedMap_(f, a.table[i], i == 0 ? 0 : a.lengths[i - 1]);
+ }
+ return newA;
+ }
+
+ function foldl(f, b, a)
+ {
+ if (a.height == 0)
+ {
+ for (var i = 0; i < a.table.length; i++)
+ {
+ b = A2(f, a.table[i], b);
+ }
+ }
+ else
+ {
+ for (var i = 0; i < a.table.length; i++)
+ {
+ b = foldl(f, b, a.table[i]);
+ }
+ }
+ return b;
+ }
+
+ function foldr(f, b, a)
+ {
+ if (a.height == 0)
+ {
+ for (var i = a.table.length; i--; )
+ {
+ b = A2(f, a.table[i], b);
+ }
+ }
+ else
+ {
+ for (var i = a.table.length; i--; )
+ {
+ b = foldr(f, b, a.table[i]);
+ }
+ }
+ return b;
+ }
+
+ // TODO: currently, it slices the right, then the left. This can be
+ // optimized.
+ function slice(from, to, a)
+ {
+ if (from < 0)
+ {
+ from += length(a);
+ }
+ if (to < 0)
+ {
+ to += length(a);
+ }
+ return sliceLeft(from, sliceRight(to, a));
+ }
+
+ function sliceRight(to, a)
+ {
+ if (to == length(a))
+ {
+ return a;
+ }
+
+ // Handle leaf level.
+ if (a.height == 0)
+ {
+ var newA = { ctor:"_Array", height:0 };
+ newA.table = a.table.slice(0, to);
+ return newA;
+ }
+
+ // Slice the right recursively.
+ var right = getSlot(to, a);
+ var sliced = sliceRight(to - (right > 0 ? a.lengths[right - 1] : 0), a.table[right]);
+
+ // Maybe the a node is not even needed, as sliced contains the whole slice.
+ if (right == 0)
+ {
+ return sliced;
+ }
+
+ // Create new node.
+ var newA = {
+ ctor: "_Array",
+ height: a.height,
+ table: a.table.slice(0, right),
+ lengths: a.lengths.slice(0, right)
+ };
+ if (sliced.table.length > 0)
+ {
+ newA.table[right] = sliced;
+ newA.lengths[right] = length(sliced) + (right > 0 ? newA.lengths[right - 1] : 0);
+ }
+ return newA;
+ }
+
+ function sliceLeft(from, a)
+ {
+ if (from == 0)
+ {
+ return a;
+ }
+
+ // Handle leaf level.
+ if (a.height == 0)
+ {
+ var newA = { ctor:"_Array", height:0 };
+ newA.table = a.table.slice(from, a.table.length + 1);
+ return newA;
+ }
+
+ // Slice the left recursively.
+ var left = getSlot(from, a);
+ var sliced = sliceLeft(from - (left > 0 ? a.lengths[left - 1] : 0), a.table[left]);
+
+ // Maybe the a node is not even needed, as sliced contains the whole slice.
+ if (left == a.table.length - 1)
+ {
+ return sliced;
+ }
+
+ // Create new node.
+ var newA = {
+ ctor: "_Array",
+ height: a.height,
+ table: a.table.slice(left, a.table.length + 1),
+ lengths: new Array(a.table.length - left)
+ };
+ newA.table[0] = sliced;
+ var len = 0;
+ for (var i = 0; i < newA.table.length; i++)
+ {
+ len += length(newA.table[i]);
+ newA.lengths[i] = len;
+ }
+
+ return newA;
+ }
+
+ // Appends two trees.
+ function append(a,b)
+ {
+ if (a.table.length === 0)
+ {
+ return b;
+ }
+ if (b.table.length === 0)
+ {
+ return a;
+ }
+
+ var c = append_(a, b);
+
+ // Check if both nodes can be crunshed together.
+ if (c[0].table.length + c[1].table.length <= M)
+ {
+ if (c[0].table.length === 0)
+ {
+ return c[1];
+ }
+ if (c[1].table.length === 0)
+ {
+ return c[0];
+ }
+
+ // Adjust .table and .lengths
+ c[0].table = c[0].table.concat(c[1].table);
+ if (c[0].height > 0)
+ {
+ var len = length(c[0]);
+ for (var i = 0; i < c[1].lengths.length; i++)
+ {
+ c[1].lengths[i] += len;
+ }
+ c[0].lengths = c[0].lengths.concat(c[1].lengths);
+ }
+
+ return c[0];
+ }
+
+ if (c[0].height > 0)
+ {
+ var toRemove = calcToRemove(a, b);
+ if (toRemove > E)
+ {
+ c = shuffle(c[0], c[1], toRemove);
+ }
+ }
+
+ return siblise(c[0], c[1]);
+ }
+
+ // Returns an array of two nodes; right and left. One node _may_ be empty.
+ function append_(a, b)
+ {
+ if (a.height === 0 && b.height === 0)
+ {
+ return [a, b];
+ }
+
+ if (a.height !== 1 || b.height !== 1)
+ {
+ if (a.height === b.height)
+ {
+ a = nodeCopy(a);
+ b = nodeCopy(b);
+ var appended = append_(botRight(a), botLeft(b));
+
+ insertRight(a, appended[1]);
+ insertLeft(b, appended[0]);
+ }
+ else if (a.height > b.height)
+ {
+ a = nodeCopy(a);
+ var appended = append_(botRight(a), b);
+
+ insertRight(a, appended[0]);
+ b = parentise(appended[1], appended[1].height + 1);
+ }
+ else
+ {
+ b = nodeCopy(b);
+ var appended = append_(a, botLeft(b));
+
+ var left = appended[0].table.length === 0 ? 0 : 1;
+ var right = left === 0 ? 1 : 0;
+ insertLeft(b, appended[left]);
+ a = parentise(appended[right], appended[right].height + 1);
+ }
+ }
+
+ // Check if balancing is needed and return based on that.
+ if (a.table.length === 0 || b.table.length === 0)
+ {
+ return [a,b];
+ }
+
+ var toRemove = calcToRemove(a, b);
+ if (toRemove <= E)
+ {
+ return [a,b];
+ }
+ return shuffle(a, b, toRemove);
+ }
+
+ // Helperfunctions for append_. Replaces a child node at the side of the parent.
+ function insertRight(parent, node)
+ {
+ var index = parent.table.length - 1;
+ parent.table[index] = node;
+ parent.lengths[index] = length(node)
+ parent.lengths[index] += index > 0 ? parent.lengths[index - 1] : 0;
+ }
+
+ function insertLeft(parent, node)
+ {
+ if (node.table.length > 0)
+ {
+ parent.table[0] = node;
+ parent.lengths[0] = length(node);
+
+ var len = length(parent.table[0]);
+ for (var i = 1; i < parent.lengths.length; i++)
+ {
+ len += length(parent.table[i]);
+ parent.lengths[i] = len;
+ }
+ }
+ else
+ {
+ parent.table.shift();
+ for (var i = 1; i < parent.lengths.length; i++)
+ {
+ parent.lengths[i] = parent.lengths[i] - parent.lengths[0];
+ }
+ parent.lengths.shift();
+ }
+ }
+
+ // Returns the extra search steps for E. Refer to the paper.
+ function calcToRemove(a, b)
+ {
+ var subLengths = 0;
+ for (var i = 0; i < a.table.length; i++)
+ {
+ subLengths += a.table[i].table.length;
+ }
+ for (var i = 0; i < b.table.length; i++)
+ {
+ subLengths += b.table[i].table.length;
+ }
+
+ var toRemove = a.table.length + b.table.length
+ return toRemove - (Math.floor((subLengths - 1) / M) + 1);
+ }
+
+ // get2, set2 and saveSlot are helpers for accessing elements over two arrays.
+ function get2(a, b, index)
+ {
+ return index < a.length
+ ? a[index]
+ : b[index - a.length];
+ }
+
+ function set2(a, b, index, value)
+ {
+ if (index < a.length)
+ {
+ a[index] = value;
+ }
+ else
+ {
+ b[index - a.length] = value;
+ }
+ }
+
+ function saveSlot(a, b, index, slot)
+ {
+ set2(a.table, b.table, index, slot);
+
+ var l = (index == 0 || index == a.lengths.length)
+ ? 0
+ : get2(a.lengths, a.lengths, index - 1);
+
+ set2(a.lengths, b.lengths, index, l + length(slot));
+ }
+
+ // Creates a node or leaf with a given length at their arrays for perfomance.
+ // Is only used by shuffle.
+ function createNode(h, length)
+ {
+ if (length < 0)
+ {
+ length = 0;
+ }
+ var a = {
+ ctor: "_Array",
+ height: h,
+ table: new Array(length)
+ };
+ if (h > 0)
+ {
+ a.lengths = new Array(length);
+ }
+ return a;
+ }
+
+ // Returns an array of two balanced nodes.
+ function shuffle(a, b, toRemove)
+ {
+ var newA = createNode(a.height, Math.min(M, a.table.length + b.table.length - toRemove));
+ var newB = createNode(a.height, newA.table.length - (a.table.length + b.table.length - toRemove));
+
+ // Skip the slots with size M. More precise: copy the slot references
+ // to the new node
+ var read = 0;
+ while (get2(a.table, b.table, read).table.length % M == 0)
+ {
+ set2(newA.table, newB.table, read, get2(a.table, b.table, read));
+ set2(newA.lengths, newB.lengths, read, get2(a.lengths, b.lengths, read));
+ read++;
+ }
+
+ // Pulling items from left to right, caching in a slot before writing
+ // it into the new nodes.
+ var write = read;
+ var slot = new createNode(a.height - 1, 0);
+ var from = 0;
+
+ // If the current slot is still containing data, then there will be at
+ // least one more write, so we do not break this loop yet.
+ while (read - write - (slot.table.length > 0 ? 1 : 0) < toRemove)
+ {
+ // Find out the max possible items for copying.
+ var source = get2(a.table, b.table, read);
+ var to = Math.min(M - slot.table.length, source.table.length)
+
+ // Copy and adjust size table.
+ slot.table = slot.table.concat(source.table.slice(from, to));
+ if (slot.height > 0)
+ {
+ var len = slot.lengths.length;
+ for (var i = len; i < len + to - from; i++)
+ {
+ slot.lengths[i] = length(slot.table[i]);
+ slot.lengths[i] += (i > 0 ? slot.lengths[i - 1] : 0);
+ }
+ }
+
+ from += to;
+
+ // Only proceed to next slots[i] if the current one was
+ // fully copied.
+ if (source.table.length <= to)
+ {
+ read++; from = 0;
+ }
+
+ // Only create a new slot if the current one is filled up.
+ if (slot.table.length == M)
+ {
+ saveSlot(newA, newB, write, slot);
+ slot = createNode(a.height - 1,0);
+ write++;
+ }
+ }
+
+ // Cleanup after the loop. Copy the last slot into the new nodes.
+ if (slot.table.length > 0)
+ {
+ saveSlot(newA, newB, write, slot);
+ write++;
+ }
+
+ // Shift the untouched slots to the left
+ while (read < a.table.length + b.table.length )
+ {
+ saveSlot(newA, newB, write, get2(a.table, b.table, read));
+ read++;
+ write++;
+ }
+
+ return [newA, newB];
+ }
+
+ // Navigation functions
+ function botRight(a)
+ {
+ return a.table[a.table.length - 1];
+ }
+ function botLeft(a)
+ {
+ return a.table[0];
+ }
+
+ // Copies a node for updating. Note that you should not use this if
+ // only updating only one of "table" or "lengths" for performance reasons.
+ function nodeCopy(a)
+ {
+ var newA = {
+ ctor: "_Array",
+ height: a.height,
+ table: a.table.slice()
+ };
+ if (a.height > 0)
+ {
+ newA.lengths = a.lengths.slice();
+ }
+ return newA;
+ }
+
+ // Returns how many items are in the tree.
+ function length(array)
+ {
+ if (array.height == 0)
+ {
+ return array.table.length;
+ }
+ else
+ {
+ return array.lengths[array.lengths.length - 1];
+ }
+ }
+
+ // Calculates in which slot of "table" the item probably is, then
+ // find the exact slot via forward searching in "lengths". Returns the index.
+ function getSlot(i, a)
+ {
+ var slot = i >> (5 * a.height);
+ while (a.lengths[slot] <= i)
+ {
+ slot++;
+ }
+ return slot;
+ }
+
+ // Recursively creates a tree with a given height containing
+ // only the given item.
+ function create(item, h)
+ {
+ if (h == 0)
+ {
+ return {
+ ctor: "_Array",
+ height: 0,
+ table: [item]
+ };
+ }
+ return {
+ ctor: "_Array",
+ height: h,
+ table: [create(item, h - 1)],
+ lengths: [1]
+ };
+ }
+
+ // Recursively creates a tree that contains the given tree.
+ function parentise(tree, h)
+ {
+ if (h == tree.height)
+ {
+ return tree;
+ }
+
+ return {
+ ctor: "_Array",
+ height: h,
+ table: [parentise(tree, h - 1)],
+ lengths: [length(tree)]
+ };
+ }
+
+ // Emphasizes blood brotherhood beneath two trees.
+ function siblise(a, b)
+ {
+ return {
+ ctor: "_Array",
+ height: a.height + 1,
+ table: [a, b],
+ lengths: [length(a), length(a) + length(b)]
+ };
+ }
+
+ function toJSArray(a)
+ {
+ var jsArray = new Array(length(a));
+ toJSArray_(jsArray, 0, a);
+ return jsArray;
+ }
+
+ function toJSArray_(jsArray, i, a)
+ {
+ for (var t = 0; t < a.table.length; t++)
+ {
+ if (a.height == 0)
+ {
+ jsArray[i + t] = a.table[t];
+ }
+ else
+ {
+ var inc = t == 0 ? 0 : a.lengths[t - 1];
+ toJSArray_(jsArray, i + inc, a.table[t]);
+ }
+ }
+ }
+
+ function fromJSArray(jsArray)
+ {
+ if (jsArray.length == 0)
+ {
+ return empty;
+ }
+ var h = Math.floor(Math.log(jsArray.length) / Math.log(M));
+ return fromJSArray_(jsArray, h, 0, jsArray.length);
+ }
+
+ function fromJSArray_(jsArray, h, from, to)
+ {
+ if (h == 0)
+ {
+ return {
+ ctor: "_Array",
+ height: 0,
+ table: jsArray.slice(from, to)
+ };
+ }
+
+ var step = Math.pow(M, h);
+ var table = new Array(Math.ceil((to - from) / step));
+ var lengths = new Array(table.length);
+ for (var i = 0; i < table.length; i++)
+ {
+ table[i] = fromJSArray_(jsArray, h - 1, from + (i * step), Math.min(from + ((i + 1) * step), to));
+ lengths[i] = length(table[i]) + (i > 0 ? lengths[i-1] : 0);
+ }
+ return {
+ ctor: "_Array",
+ height: h,
+ table: table,
+ lengths: lengths
+ };
+ }
+
+ Elm.Native.Array.values = {
+ empty: empty,
+ fromList: fromList,
+ toList: toList,
+ initialize: F2(initialize),
+ append: F2(append),
+ push: F2(push),
+ slice: F3(slice),
+ get: F2(get),
+ set: F3(set),
+ map: F2(map),
+ indexedMap: F2(indexedMap),
+ foldl: F3(foldl),
+ foldr: F3(foldr),
+ length: length,
+
+ toJSArray:toJSArray,
+ fromJSArray:fromJSArray
+ };
+
+ return localRuntime.Native.Array.values = Elm.Native.Array.values;
+
+}
+
+Elm.Native.Basics = {};
+Elm.Native.Basics.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Basics = localRuntime.Native.Basics || {};
+ if (localRuntime.Native.Basics.values)
+ {
+ return localRuntime.Native.Basics.values;
+ }
+
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+ function div(a, b)
+ {
+ return (a/b)|0;
+ }
+ function rem(a, b)
+ {
+ return a % b;
+ }
+ function mod(a, b)
+ {
+ if (b === 0)
+ {
+ throw new Error("Cannot perform mod 0. Division by zero error.");
+ }
+ var r = a % b;
+ var m = a === 0 ? 0 : (b > 0 ? (a >= 0 ? r : r+b) : -mod(-a,-b));
+
+ return m === b ? 0 : m;
+ }
+ function logBase(base, n)
+ {
+ return Math.log(n) / Math.log(base);
+ }
+ function negate(n)
+ {
+ return -n;
+ }
+ function abs(n)
+ {
+ return n < 0 ? -n : n;
+ }
+
+ function min(a, b)
+ {
+ return Utils.cmp(a,b) < 0 ? a : b;
+ }
+ function max(a, b)
+ {
+ return Utils.cmp(a,b) > 0 ? a : b;
+ }
+ function clamp(lo, hi, n)
+ {
+ return Utils.cmp(n,lo) < 0 ? lo : Utils.cmp(n,hi) > 0 ? hi : n;
+ }
+
+ function xor(a, b)
+ {
+ return a !== b;
+ }
+ function not(b)
+ {
+ return !b;
+ }
+ function isInfinite(n)
+ {
+ return n === Infinity || n === -Infinity
+ }
+
+ function truncate(n)
+ {
+ return n|0;
+ }
+
+ function degrees(d)
+ {
+ return d * Math.PI / 180;
+ }
+ function turns(t)
+ {
+ return 2 * Math.PI * t;
+ }
+ function fromPolar(point)
+ {
+ var r = point._0;
+ var t = point._1;
+ return Utils.Tuple2(r * Math.cos(t), r * Math.sin(t));
+ }
+ function toPolar(point)
+ {
+ var x = point._0;
+ var y = point._1;
+ return Utils.Tuple2(Math.sqrt(x * x + y * y), Math.atan2(y,x));
+ }
+
+ return localRuntime.Native.Basics.values = {
+ div: F2(div),
+ rem: F2(rem),
+ mod: F2(mod),
+
+ pi: Math.PI,
+ e: Math.E,
+ cos: Math.cos,
+ sin: Math.sin,
+ tan: Math.tan,
+ acos: Math.acos,
+ asin: Math.asin,
+ atan: Math.atan,
+ atan2: F2(Math.atan2),
+
+ degrees: degrees,
+ turns: turns,
+ fromPolar: fromPolar,
+ toPolar: toPolar,
+
+ sqrt: Math.sqrt,
+ logBase: F2(logBase),
+ negate: negate,
+ abs: abs,
+ min: F2(min),
+ max: F2(max),
+ clamp: F3(clamp),
+ compare: Utils.compare,
+
+ xor: F2(xor),
+ not: not,
+
+ truncate: truncate,
+ ceiling: Math.ceil,
+ floor: Math.floor,
+ round: Math.round,
+ toFloat: function(x) { return x; },
+ isNaN: isNaN,
+ isInfinite: isInfinite
+ };
+};
+
+Elm.Native.Char = {};
+Elm.Native.Char.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Char = localRuntime.Native.Char || {};
+ if (localRuntime.Native.Char.values)
+ {
+ return localRuntime.Native.Char.values;
+ }
+
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+ return localRuntime.Native.Char.values = {
+ fromCode : function(c) { return Utils.chr(String.fromCharCode(c)); },
+ toCode : function(c) { return c.charCodeAt(0); },
+ toUpper : function(c) { return Utils.chr(c.toUpperCase()); },
+ toLower : function(c) { return Utils.chr(c.toLowerCase()); },
+ toLocaleUpper : function(c) { return Utils.chr(c.toLocaleUpperCase()); },
+ toLocaleLower : function(c) { return Utils.chr(c.toLocaleLowerCase()); },
+ };
+};
+
+Elm.Native.Color = {};
+Elm.Native.Color.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Color = localRuntime.Native.Color || {};
+ if (localRuntime.Native.Color.values)
+ {
+ return localRuntime.Native.Color.values;
+ }
+
+ function toCss(c)
+ {
+ var format = '';
+ var colors = '';
+ if (c.ctor === 'RGBA')
+ {
+ format = 'rgb';
+ colors = c._0 + ', ' + c._1 + ', ' + c._2;
+ }
+ else
+ {
+ format = 'hsl';
+ colors = (c._0 * 180 / Math.PI) + ', ' +
+ (c._1 * 100) + '%, ' +
+ (c._2 * 100) + '%';
+ }
+ if (c._3 === 1)
+ {
+ return format + '(' + colors + ')';
+ }
+ else
+ {
+ return format + 'a(' + colors + ', ' + c._3 + ')';
+ }
+ }
+
+ return localRuntime.Native.Color.values = {
+ toCss: toCss
+ };
+
+};
+
+Elm.Native.Date = {};
+Elm.Native.Date.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Date = localRuntime.Native.Date || {};
+ if (localRuntime.Native.Date.values)
+ {
+ return localRuntime.Native.Date.values;
+ }
+
+ var Result = Elm.Result.make(localRuntime);
+
+ function dateNow()
+ {
+ return new window.Date;
+ }
+
+ function readDate(str)
+ {
+ var date = new window.Date(str);
+ return isNaN(date.getTime())
+ ? Result.Err("unable to parse '" + str + "' as a date")
+ : Result.Ok(date);
+ }
+
+ var dayTable = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"];
+ var monthTable =
+ ["Jan", "Feb", "Mar", "Apr", "May", "Jun",
+ "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"];
+
+
+ return localRuntime.Native.Date.values = {
+ read : readDate,
+ year : function(d) { return d.getFullYear(); },
+ month : function(d) { return { ctor:monthTable[d.getMonth()] }; },
+ day : function(d) { return d.getDate(); },
+ hour : function(d) { return d.getHours(); },
+ minute : function(d) { return d.getMinutes(); },
+ second : function(d) { return d.getSeconds(); },
+ millisecond: function (d) { return d.getMilliseconds(); },
+ toTime : function(d) { return d.getTime(); },
+ fromTime: function(t) { return new window.Date(t); },
+ dayOfWeek : function(d) { return { ctor:dayTable[d.getDay()] }; }
+ };
+
+};
+
+Elm.Native.Debug = {};
+Elm.Native.Debug.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Debug = localRuntime.Native.Debug || {};
+ if (localRuntime.Native.Debug.values)
+ {
+ return localRuntime.Native.Debug.values;
+ }
+
+ var toString = Elm.Native.Show.make(localRuntime).toString;
+
+ function log(tag, value)
+ {
+ var msg = tag + ': ' + toString(value);
+ var process = process || {};
+ if (process.stdout)
+ {
+ process.stdout.write(msg);
+ }
+ else
+ {
+ console.log(msg);
+ }
+ return value;
+ }
+
+ function crash(message)
+ {
+ throw new Error(message);
+ }
+
+ function tracePath(tag, form)
+ {
+ if (localRuntime.debug)
+ {
+ return localRuntime.debug.trace(tag, form);
+ }
+ return form;
+ }
+
+ function watch(tag, value)
+ {
+ if (localRuntime.debug)
+ {
+ localRuntime.debug.watch(tag, value);
+ }
+ return value;
+ }
+
+ function watchSummary(tag, summarize, value)
+ {
+ if (localRuntime.debug)
+ {
+ localRuntime.debug.watch(tag, summarize(value));
+ }
+ return value;
+ }
+
+ return localRuntime.Native.Debug.values = {
+ crash: crash,
+ tracePath: F2(tracePath),
+ log: F2(log),
+ watch: F2(watch),
+ watchSummary:F3(watchSummary),
+ };
+};
+
+
+// setup
+Elm.Native = Elm.Native || {};
+Elm.Native.Graphics = Elm.Native.Graphics || {};
+Elm.Native.Graphics.Collage = Elm.Native.Graphics.Collage || {};
+
+// definition
+Elm.Native.Graphics.Collage.make = function(localRuntime) {
+ 'use strict';
+
+ // attempt to short-circuit
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Graphics = localRuntime.Native.Graphics || {};
+ localRuntime.Native.Graphics.Collage = localRuntime.Native.Graphics.Collage || {};
+ if ('values' in localRuntime.Native.Graphics.Collage)
+ {
+ return localRuntime.Native.Graphics.Collage.values;
+ }
+
+ // okay, we cannot short-ciruit, so now we define everything
+ var Color = Elm.Native.Color.make(localRuntime);
+ var List = Elm.Native.List.make(localRuntime);
+ var NativeElement = Elm.Native.Graphics.Element.make(localRuntime);
+ var Transform = Elm.Transform2D.make(localRuntime);
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+ function setStrokeStyle(ctx, style)
+ {
+ ctx.lineWidth = style.width;
+
+ var cap = style.cap.ctor;
+ ctx.lineCap = cap === 'Flat'
+ ? 'butt'
+ : cap === 'Round'
+ ? 'round'
+ : 'square';
+
+ var join = style.join.ctor;
+ ctx.lineJoin = join === 'Smooth'
+ ? 'round'
+ : join === 'Sharp'
+ ? 'miter'
+ : 'bevel';
+
+ ctx.miterLimit = style.join._0 || 10;
+ ctx.strokeStyle = Color.toCss(style.color);
+ }
+
+ function setFillStyle(ctx, style)
+ {
+ var sty = style.ctor;
+ ctx.fillStyle = sty === 'Solid'
+ ? Color.toCss(style._0)
+ : sty === 'Texture'
+ ? texture(redo, ctx, style._0)
+ : gradient(ctx, style._0);
+ }
+
+ function trace(ctx, path)
+ {
+ var points = List.toArray(path);
+ var i = points.length - 1;
+ if (i <= 0)
+ {
+ return;
+ }
+ ctx.moveTo(points[i]._0, points[i]._1);
+ while (i--)
+ {
+ ctx.lineTo(points[i]._0, points[i]._1);
+ }
+ if (path.closed)
+ {
+ i = points.length - 1;
+ ctx.lineTo(points[i]._0, points[i]._1);
+ }
+ }
+
+ function line(ctx,style,path)
+ {
+ (style.dashing.ctor === '[]')
+ ? trace(ctx, path)
+ : customLineHelp(ctx, style, path);
+ ctx.scale(1,-1);
+ ctx.stroke();
+ }
+
+ function customLineHelp(ctx, style, path)
+ {
+ var points = List.toArray(path);
+ if (path.closed)
+ {
+ points.push(points[0]);
+ }
+ var pattern = List.toArray(style.dashing);
+ var i = points.length - 1;
+ if (i <= 0)
+ {
+ return;
+ }
+ var x0 = points[i]._0, y0 = points[i]._1;
+ var x1=0, y1=0, dx=0, dy=0, remaining=0, nx=0, ny=0;
+ var pindex = 0, plen = pattern.length;
+ var draw = true, segmentLength = pattern[0];
+ ctx.moveTo(x0,y0);
+ while (i--)
+ {
+ x1 = points[i]._0;
+ y1 = points[i]._1;
+ dx = x1 - x0;
+ dy = y1 - y0;
+ remaining = Math.sqrt(dx * dx + dy * dy);
+ while (segmentLength <= remaining)
+ {
+ x0 += dx * segmentLength / remaining;
+ y0 += dy * segmentLength / remaining;
+ ctx[draw ? 'lineTo' : 'moveTo'](x0, y0);
+ // update starting position
+ dx = x1 - x0;
+ dy = y1 - y0;
+ remaining = Math.sqrt(dx * dx + dy * dy);
+ // update pattern
+ draw = !draw;
+ pindex = (pindex + 1) % plen;
+ segmentLength = pattern[pindex];
+ }
+ if (remaining > 0)
+ {
+ ctx[draw ? 'lineTo' : 'moveTo'](x1, y1);
+ segmentLength -= remaining;
+ }
+ x0 = x1;
+ y0 = y1;
+ }
+ }
+
+ function drawLine(ctx, style, path)
+ {
+ setStrokeStyle(ctx, style);
+ return line(ctx, style, path);
+ }
+
+ function texture(redo, ctx, src)
+ {
+ var img = new Image();
+ img.src = src;
+ img.onload = redo;
+ return ctx.createPattern(img, 'repeat');
+ }
+
+ function gradient(ctx, grad)
+ {
+ var g;
+ var stops = [];
+ if (grad.ctor === 'Linear')
+ {
+ var p0 = grad._0, p1 = grad._1;
+ g = ctx.createLinearGradient(p0._0, -p0._1, p1._0, -p1._1);
+ stops = List.toArray(grad._2);
+ }
+ else
+ {
+ var p0 = grad._0, p2 = grad._2;
+ g = ctx.createRadialGradient(p0._0, -p0._1, grad._1, p2._0, -p2._1, grad._3);
+ stops = List.toArray(grad._4);
+ }
+ var len = stops.length;
+ for (var i = 0; i < len; ++i)
+ {
+ var stop = stops[i];
+ g.addColorStop(stop._0, Color.toCss(stop._1));
+ }
+ return g;
+ }
+
+ function drawShape(redo, ctx, style, path)
+ {
+ trace(ctx, path);
+ setFillStyle(ctx, style);
+ ctx.scale(1,-1);
+ ctx.fill();
+ }
+
+
+ // TEXT RENDERING
+
+ function fillText(redo, ctx, text)
+ {
+ drawText(ctx, text, ctx.fillText);
+ }
+
+ function strokeText(redo, ctx, style, text)
+ {
+ setStrokeStyle(ctx, style);
+ // Use native canvas API for dashes only for text for now
+ // Degrades to non-dashed on IE 9 + 10
+ if (style.dashing.ctor !== '[]' && ctx.setLineDash)
+ {
+ var pattern = List.toArray(style.dashing);
+ ctx.setLineDash(pattern);
+ }
+ drawText(ctx, text, ctx.strokeText);
+ }
+
+ function drawText(ctx, text, canvasDrawFn)
+ {
+ var textChunks = chunkText(defaultContext, text);
+
+ var totalWidth = 0;
+ var maxHeight = 0;
+ var numChunks = textChunks.length;
+
+ ctx.scale(1,-1);
+
+ for (var i = numChunks; i--; )
+ {
+ var chunk = textChunks[i];
+ ctx.font = chunk.font;
+ var metrics = ctx.measureText(chunk.text);
+ chunk.width = metrics.width;
+ totalWidth += chunk.width;
+ if (chunk.height > maxHeight)
+ {
+ maxHeight = chunk.height;
+ }
+ }
+
+ var x = -totalWidth / 2.0;
+ for (var i = 0; i < numChunks; ++i)
+ {
+ var chunk = textChunks[i];
+ ctx.font = chunk.font;
+ ctx.fillStyle = chunk.color;
+ canvasDrawFn.call(ctx, chunk.text, x, maxHeight / 2);
+ x += chunk.width;
+ }
+ }
+
+ function toFont(props)
+ {
+ return [
+ props['font-style'],
+ props['font-variant'],
+ props['font-weight'],
+ props['font-size'],
+ props['font-family']
+ ].join(' ');
+ }
+
+
+ // Convert the object returned by the text module
+ // into something we can use for styling canvas text
+ function chunkText(context, text)
+ {
+ var tag = text.ctor;
+ if (tag === 'Text:Append')
+ {
+ var leftChunks = chunkText(context, text._0);
+ var rightChunks = chunkText(context, text._1);
+ return leftChunks.concat(rightChunks);
+ }
+ if (tag === 'Text:Text')
+ {
+ return [{
+ text: text._0,
+ color: context.color,
+ height: context['font-size'].slice(0,-2) | 0,
+ font: toFont(context)
+ }];
+ }
+ if (tag === 'Text:Meta')
+ {
+ var newContext = freshContext(text._0, context);
+ return chunkText(newContext, text._1);
+ }
+ }
+
+ function freshContext(props, ctx)
+ {
+ return {
+ 'font-style': props['font-style'] || ctx['font-style'],
+ 'font-variant': props['font-variant'] || ctx['font-variant'],
+ 'font-weight': props['font-weight'] || ctx['font-weight'],
+ 'font-size': props['font-size'] || ctx['font-size'],
+ 'font-family': props['font-family'] || ctx['font-family'],
+ 'color': props['color'] || ctx['color']
+ };
+ }
+
+ var defaultContext = {
+ 'font-style': 'normal',
+ 'font-variant': 'normal',
+ 'font-weight': 'normal',
+ 'font-size': '12px',
+ 'font-family': 'sans-serif',
+ 'color': 'black'
+ };
+
+
+ // IMAGES
+
+ function drawImage(redo, ctx, form)
+ {
+ var img = new Image();
+ img.onload = redo;
+ img.src = form._3;
+ var w = form._0,
+ h = form._1,
+ pos = form._2,
+ srcX = pos._0,
+ srcY = pos._1,
+ srcW = w,
+ srcH = h,
+ destX = -w/2,
+ destY = -h/2,
+ destW = w,
+ destH = h;
+
+ ctx.scale(1,-1);
+ ctx.drawImage(img, srcX, srcY, srcW, srcH, destX, destY, destW, destH);
+ }
+
+ function renderForm(redo, ctx, form)
+ {
+ ctx.save();
+
+ var x = form.x,
+ y = form.y,
+ theta = form.theta,
+ scale = form.scale;
+
+ if (x !== 0 || y !== 0)
+ {
+ ctx.translate(x, y);
+ }
+ if (theta !== 0)
+ {
+ ctx.rotate(theta);
+ }
+ if (scale !== 1)
+ {
+ ctx.scale(scale,scale);
+ }
+ if (form.alpha !== 1)
+ {
+ ctx.globalAlpha = ctx.globalAlpha * form.alpha;
+ }
+
+ ctx.beginPath();
+ var f = form.form;
+ switch (f.ctor)
+ {
+ case 'FPath':
+ drawLine(ctx, f._0, f._1);
+ break;
+
+ case 'FImage':
+ drawImage(redo, ctx, f);
+ break;
+
+ case 'FShape':
+ if (f._0.ctor === 'Line')
+ {
+ f._1.closed = true;
+ drawLine(ctx, f._0._0, f._1);
+ }
+ else
+ {
+ drawShape(redo, ctx, f._0._0, f._1);
+ }
+ break;
+
+ case 'FText':
+ fillText(redo, ctx, f._0);
+ break;
+
+ case 'FOutlinedText':
+ strokeText(redo, ctx, f._0, f._1);
+ break;
+ }
+ ctx.restore();
+ }
+
+ function formToMatrix(form)
+ {
+ var scale = form.scale;
+ var matrix = A6( Transform.matrix, scale, 0, 0, scale, form.x, form.y );
+
+ var theta = form.theta
+ if (theta !== 0)
+ {
+ matrix = A2( Transform.multiply, matrix, Transform.rotation(theta) );
+ }
+
+ return matrix;
+ }
+
+ function str(n)
+ {
+ if (n < 0.00001 && n > -0.00001)
+ {
+ return 0;
+ }
+ return n;
+ }
+
+ function makeTransform(w, h, form, matrices)
+ {
+ var props = form.form._0.props;
+ var m = A6( Transform.matrix, 1, 0, 0, -1,
+ (w - props.width ) / 2,
+ (h - props.height) / 2 );
+ var len = matrices.length;
+ for (var i = 0; i < len; ++i)
+ {
+ m = A2( Transform.multiply, m, matrices[i] );
+ }
+ m = A2( Transform.multiply, m, formToMatrix(form) );
+
+ return 'matrix(' +
+ str( m[0]) + ', ' + str( m[3]) + ', ' +
+ str(-m[1]) + ', ' + str(-m[4]) + ', ' +
+ str( m[2]) + ', ' + str( m[5]) + ')';
+ }
+
+ function stepperHelp(list)
+ {
+ var arr = List.toArray(list);
+ var i = 0;
+ function peekNext()
+ {
+ return i < arr.length ? arr[i].form.ctor : '';
+ }
+ // assumes that there is a next element
+ function next()
+ {
+ var out = arr[i];
+ ++i;
+ return out;
+ }
+ return {
+ peekNext: peekNext,
+ next: next
+ };
+ }
+
+ function formStepper(forms)
+ {
+ var ps = [stepperHelp(forms)];
+ var matrices = [];
+ var alphas = [];
+ function peekNext()
+ {
+ var len = ps.length;
+ var formType = '';
+ for (var i = 0; i < len; ++i )
+ {
+ if (formType = ps[i].peekNext()) return formType;
+ }
+ return '';
+ }
+ // assumes that there is a next element
+ function next(ctx)
+ {
+ while (!ps[0].peekNext())
+ {
+ ps.shift();
+ matrices.pop();
+ alphas.shift();
+ if (ctx)
+ {
+ ctx.restore();
+ }
+ }
+ var out = ps[0].next();
+ var f = out.form;
+ if (f.ctor === 'FGroup')
+ {
+ ps.unshift(stepperHelp(f._1));
+ var m = A2(Transform.multiply, f._0, formToMatrix(out));
+ ctx.save();
+ ctx.transform(m[0], m[3], m[1], m[4], m[2], m[5]);
+ matrices.push(m);
+
+ var alpha = (alphas[0] || 1) * out.alpha;
+ alphas.unshift(alpha);
+ ctx.globalAlpha = alpha;
+ }
+ return out;
+ }
+ function transforms()
+ {
+ return matrices;
+ }
+ function alpha()
+ {
+ return alphas[0] || 1;
+ }
+ return {
+ peekNext: peekNext,
+ next: next,
+ transforms: transforms,
+ alpha: alpha
+ };
+ }
+
+ function makeCanvas(w,h)
+ {
+ var canvas = NativeElement.createNode('canvas');
+ canvas.style.width = w + 'px';
+ canvas.style.height = h + 'px';
+ canvas.style.display = "block";
+ canvas.style.position = "absolute";
+ var ratio = window.devicePixelRatio || 1;
+ canvas.width = w * ratio;
+ canvas.height = h * ratio;
+ return canvas;
+ }
+
+ function render(model)
+ {
+ var div = NativeElement.createNode('div');
+ div.style.overflow = 'hidden';
+ div.style.position = 'relative';
+ update(div, model, model);
+ return div;
+ }
+
+ function nodeStepper(w,h,div)
+ {
+ var kids = div.childNodes;
+ var i = 0;
+ var ratio = window.devicePixelRatio || 1;
+
+ function transform(transforms, ctx)
+ {
+ ctx.translate( w / 2 * ratio, h / 2 * ratio );
+ ctx.scale( ratio, -ratio );
+ var len = transforms.length;
+ for (var i = 0; i < len; ++i)
+ {
+ var m = transforms[i];
+ ctx.save();
+ ctx.transform(m[0], m[3], m[1], m[4], m[2], m[5]);
+ }
+ return ctx;
+ }
+ function nextContext(transforms)
+ {
+ while (i < kids.length)
+ {
+ var node = kids[i];
+ if (node.getContext)
+ {
+ node.width = w * ratio;
+ node.height = h * ratio;
+ node.style.width = w + 'px';
+ node.style.height = h + 'px';
+ ++i;
+ return transform(transforms, node.getContext('2d'));
+ }
+ div.removeChild(node);
+ }
+ var canvas = makeCanvas(w,h);
+ div.appendChild(canvas);
+ // we have added a new node, so we must step our position
+ ++i;
+ return transform(transforms, canvas.getContext('2d'));
+ }
+ function addElement(matrices, alpha, form)
+ {
+ var kid = kids[i];
+ var elem = form.form._0;
+
+ var node = (!kid || kid.getContext)
+ ? NativeElement.render(elem)
+ : NativeElement.update(kid, kid.oldElement, elem);
+
+ node.style.position = 'absolute';
+ node.style.opacity = alpha * form.alpha * elem.props.opacity;
+ NativeElement.addTransform(node.style, makeTransform(w, h, form, matrices));
+ node.oldElement = elem;
+ ++i;
+ if (!kid)
+ {
+ div.appendChild(node);
+ }
+ else
+ {
+ div.insertBefore(node, kid);
+ }
+ }
+ function clearRest()
+ {
+ while (i < kids.length)
+ {
+ div.removeChild(kids[i]);
+ }
+ }
+ return {
+ nextContext: nextContext,
+ addElement: addElement,
+ clearRest: clearRest
+ };
+ }
+
+
+ function update(div, _, model)
+ {
+ var w = model.w;
+ var h = model.h;
+
+ var forms = formStepper(model.forms);
+ var nodes = nodeStepper(w,h,div);
+ var ctx = null;
+ var formType = '';
+
+ while (formType = forms.peekNext())
+ {
+ // make sure we have context if we need it
+ if (ctx === null && formType !== 'FElement')
+ {
+ ctx = nodes.nextContext(forms.transforms());
+ ctx.globalAlpha = forms.alpha();
+ }
+
+ var form = forms.next(ctx);
+ // if it is FGroup, all updates are made within formStepper when next is called.
+ if (formType === 'FElement')
+ {
+ // update or insert an element, get a new context
+ nodes.addElement(forms.transforms(), forms.alpha(), form);
+ ctx = null;
+ }
+ else if (formType !== 'FGroup')
+ {
+ renderForm(function() { update(div, model, model); }, ctx, form);
+ }
+ }
+ nodes.clearRest();
+ return div;
+ }
+
+
+ function collage(w,h,forms)
+ {
+ return A3(NativeElement.newElement, w, h, {
+ ctor: 'Custom',
+ type: 'Collage',
+ render: render,
+ update: update,
+ model: {w:w, h:h, forms:forms}
+ });
+ }
+
+ return localRuntime.Native.Graphics.Collage.values = {
+ collage: F3(collage)
+ };
+
+};
+
+
+// setup
+Elm.Native = Elm.Native || {};
+Elm.Native.Graphics = Elm.Native.Graphics || {};
+Elm.Native.Graphics.Element = Elm.Native.Graphics.Element || {};
+
+// definition
+Elm.Native.Graphics.Element.make = function(localRuntime) {
+ 'use strict';
+
+ // attempt to short-circuit
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Graphics = localRuntime.Native.Graphics || {};
+ localRuntime.Native.Graphics.Element = localRuntime.Native.Graphics.Element || {};
+ if ('values' in localRuntime.Native.Graphics.Element)
+ {
+ return localRuntime.Native.Graphics.Element.values;
+ }
+
+ var Color = Elm.Native.Color.make(localRuntime);
+ var List = Elm.Native.List.make(localRuntime);
+ var Maybe = Elm.Maybe.make(localRuntime);
+ var Text = Elm.Native.Text.make(localRuntime);
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+
+ // CREATION
+
+ function createNode(elementType)
+ {
+ var node = document.createElement(elementType);
+ node.style.padding = "0";
+ node.style.margin = "0";
+ return node;
+ }
+
+
+ function newElement(width, height, elementPrim)
+ {
+ return {
+ _: {},
+ element: elementPrim,
+ props: {
+ _: {},
+ id: Utils.guid(),
+ width: width,
+ height: height,
+ opacity: 1,
+ color: Maybe.Nothing,
+ href: "",
+ tag: "",
+ hover: Utils.Tuple0,
+ click: Utils.Tuple0
+ }
+ };
+ }
+
+
+ // PROPERTIES
+
+ function setProps(elem, node)
+ {
+ var props = elem.props;
+
+ var element = elem.element;
+ var width = props.width - (element.adjustWidth || 0);
+ var height = props.height - (element.adjustHeight || 0);
+ node.style.width = (width |0) + 'px';
+ node.style.height = (height|0) + 'px';
+
+ if (props.opacity !== 1)
+ {
+ node.style.opacity = props.opacity;
+ }
+
+ if (props.color.ctor === 'Just')
+ {
+ node.style.backgroundColor = Color.toCss(props.color._0);
+ }
+
+ if (props.tag !== '')
+ {
+ node.id = props.tag;
+ }
+
+ if (props.hover.ctor !== '_Tuple0')
+ {
+ addHover(node, props.hover);
+ }
+
+ if (props.click.ctor !== '_Tuple0')
+ {
+ addClick(node, props.click);
+ }
+
+ if (props.href !== '')
+ {
+ var anchor = createNode('a');
+ anchor.href = props.href;
+ anchor.style.display = 'block';
+ anchor.style.pointerEvents = 'auto';
+ anchor.appendChild(node);
+ node = anchor;
+ }
+
+ return node;
+ }
+
+ function addClick(e, handler)
+ {
+ e.style.pointerEvents = 'auto';
+ e.elm_click_handler = handler;
+ function trigger(ev)
+ {
+ e.elm_click_handler(Utils.Tuple0);
+ ev.stopPropagation();
+ }
+ e.elm_click_trigger = trigger;
+ e.addEventListener('click', trigger);
+ }
+
+ function removeClick(e, handler)
+ {
+ if (e.elm_click_trigger)
+ {
+ e.removeEventListener('click', e.elm_click_trigger);
+ e.elm_click_trigger = null;
+ e.elm_click_handler = null;
+ }
+ }
+
+ function addHover(e, handler)
+ {
+ e.style.pointerEvents = 'auto';
+ e.elm_hover_handler = handler;
+ e.elm_hover_count = 0;
+
+ function over(evt)
+ {
+ if (e.elm_hover_count++ > 0) return;
+ e.elm_hover_handler(true);
+ evt.stopPropagation();
+ }
+ function out(evt)
+ {
+ if (e.contains(evt.toElement || evt.relatedTarget)) return;
+ e.elm_hover_count = 0;
+ e.elm_hover_handler(false);
+ evt.stopPropagation();
+ }
+ e.elm_hover_over = over;
+ e.elm_hover_out = out;
+ e.addEventListener('mouseover', over);
+ e.addEventListener('mouseout', out);
+ }
+
+ function removeHover(e)
+ {
+ e.elm_hover_handler = null;
+ if (e.elm_hover_over)
+ {
+ e.removeEventListener('mouseover', e.elm_hover_over);
+ e.elm_hover_over = null;
+ }
+ if (e.elm_hover_out)
+ {
+ e.removeEventListener('mouseout', e.elm_hover_out);
+ e.elm_hover_out = null;
+ }
+ }
+
+
+ // IMAGES
+
+ function image(props, img)
+ {
+ switch (img._0.ctor)
+ {
+ case 'Plain':
+ return plainImage(img._3);
+
+ case 'Fitted':
+ return fittedImage(props.width, props.height, img._3);
+
+ case 'Cropped':
+ return croppedImage(img,props.width,props.height,img._3);
+
+ case 'Tiled':
+ return tiledImage(img._3);
+ }
+ }
+
+ function plainImage(src)
+ {
+ var img = createNode('img');
+ img.src = src;
+ img.name = src;
+ img.style.display = "block";
+ return img;
+ }
+
+ function tiledImage(src)
+ {
+ var div = createNode('div');
+ div.style.backgroundImage = 'url(' + src + ')';
+ return div;
+ }
+
+ function fittedImage(w, h, src)
+ {
+ var div = createNode('div');
+ div.style.background = 'url(' + src + ') no-repeat center';
+ div.style.webkitBackgroundSize = 'cover';
+ div.style.MozBackgroundSize = 'cover';
+ div.style.OBackgroundSize = 'cover';
+ div.style.backgroundSize = 'cover';
+ return div;
+ }
+
+ function croppedImage(elem, w, h, src)
+ {
+ var pos = elem._0._0;
+ var e = createNode('div');
+ e.style.overflow = "hidden";
+
+ var img = createNode('img');
+ img.onload = function() {
+ var sw = w / elem._1, sh = h / elem._2;
+ img.style.width = ((this.width * sw)|0) + 'px';
+ img.style.height = ((this.height * sh)|0) + 'px';
+ img.style.marginLeft = ((- pos._0 * sw)|0) + 'px';
+ img.style.marginTop = ((- pos._1 * sh)|0) + 'px';
+ };
+ img.src = src;
+ img.name = src;
+ e.appendChild(img);
+ return e;
+ }
+
+
+ // FLOW
+
+ function goOut(node)
+ {
+ node.style.position = 'absolute';
+ return node;
+ }
+ function goDown(node)
+ {
+ return node;
+ }
+ function goRight(node)
+ {
+ node.style.styleFloat = 'left';
+ node.style.cssFloat = 'left';
+ return node;
+ }
+
+ var directionTable = {
+ DUp : goDown,
+ DDown : goDown,
+ DLeft : goRight,
+ DRight : goRight,
+ DIn : goOut,
+ DOut : goOut
+ };
+ function needsReversal(dir)
+ {
+ return dir == 'DUp' || dir == 'DLeft' || dir == 'DIn';
+ }
+
+ function flow(dir,elist)
+ {
+ var array = List.toArray(elist);
+ var container = createNode('div');
+ var goDir = directionTable[dir];
+ if (goDir == goOut)
+ {
+ container.style.pointerEvents = 'none';
+ }
+ if (needsReversal(dir))
+ {
+ array.reverse();
+ }
+ var len = array.length;
+ for (var i = 0; i < len; ++i)
+ {
+ container.appendChild(goDir(render(array[i])));
+ }
+ return container;
+ }
+
+
+ // CONTAINER
+
+ function toPos(pos)
+ {
+ return pos.ctor === "Absolute"
+ ? pos._0 + "px"
+ : (pos._0 * 100) + "%";
+ }
+
+ // must clear right, left, top, bottom, and transform
+ // before calling this function
+ function setPos(pos,elem,e)
+ {
+ var element = elem.element;
+ var props = elem.props;
+ var w = props.width + (element.adjustWidth ? element.adjustWidth : 0);
+ var h = props.height + (element.adjustHeight ? element.adjustHeight : 0);
+
+ e.style.position = 'absolute';
+ e.style.margin = 'auto';
+ var transform = '';
+
+ switch (pos.horizontal.ctor)
+ {
+ case 'P':
+ e.style.right = toPos(pos.x);
+ e.style.removeProperty('left');
+ break;
+
+ case 'Z':
+ transform = 'translateX(' + ((-w/2)|0) + 'px) ';
+
+ case 'N':
+ e.style.left = toPos(pos.x);
+ e.style.removeProperty('right');
+ break;
+ }
+ switch (pos.vertical.ctor)
+ {
+ case 'N':
+ e.style.bottom = toPos(pos.y);
+ e.style.removeProperty('top');
+ break;
+
+ case 'Z':
+ transform += 'translateY(' + ((-h/2)|0) + 'px)';
+
+ case 'P':
+ e.style.top = toPos(pos.y);
+ e.style.removeProperty('bottom');
+ break;
+ }
+ if (transform !== '')
+ {
+ addTransform(e.style, transform);
+ }
+ return e;
+ }
+
+ function addTransform(style, transform)
+ {
+ style.transform = transform;
+ style.msTransform = transform;
+ style.MozTransform = transform;
+ style.webkitTransform = transform;
+ style.OTransform = transform;
+ }
+
+ function container(pos,elem)
+ {
+ var e = render(elem);
+ setPos(pos, elem, e);
+ var div = createNode('div');
+ div.style.position = 'relative';
+ div.style.overflow = 'hidden';
+ div.appendChild(e);
+ return div;
+ }
+
+
+ function rawHtml(elem)
+ {
+ var html = elem.html;
+ var guid = elem.guid;
+ var align = elem.align;
+
+ var div = createNode('div');
+ div.innerHTML = html;
+ div.style.visibility = "hidden";
+ if (align)
+ {
+ div.style.textAlign = align;
+ }
+ div.style.visibility = 'visible';
+ div.style.pointerEvents = 'auto';
+ return div;
+ }
+
+
+ // RENDER
+
+ function render(elem)
+ {
+ return setProps(elem, makeElement(elem));
+ }
+ function makeElement(e)
+ {
+ var elem = e.element;
+ switch(elem.ctor)
+ {
+ case 'Image':
+ return image(e.props, elem);
+
+ case 'Flow':
+ return flow(elem._0.ctor, elem._1);
+
+ case 'Container':
+ return container(elem._0, elem._1);
+
+ case 'Spacer':
+ return createNode('div');
+
+ case 'RawHtml':
+ return rawHtml(elem);
+
+ case 'Custom':
+ return elem.render(elem.model);
+ }
+ }
+
+ function updateAndReplace(node, curr, next)
+ {
+ var newNode = update(node, curr, next);
+ if (newNode !== node)
+ {
+ node.parentNode.replaceChild(newNode, node);
+ }
+ return newNode;
+ }
+
+
+ // UPDATE
+
+ function update(node, curr, next)
+ {
+ var rootNode = node;
+ if (node.tagName === 'A')
+ {
+ node = node.firstChild;
+ }
+ if (curr.props.id === next.props.id)
+ {
+ updateProps(node, curr, next);
+ return rootNode;
+ }
+ if (curr.element.ctor !== next.element.ctor)
+ {
+ return render(next);
+ }
+ var nextE = next.element;
+ var currE = curr.element;
+ switch(nextE.ctor)
+ {
+ case "Spacer":
+ updateProps(node, curr, next);
+ return rootNode;
+
+ case "RawHtml":
+ if(currE.html.valueOf() !== nextE.html.valueOf())
+ {
+ node.innerHTML = nextE.html;
+ }
+ updateProps(node, curr, next);
+ return rootNode;
+
+ case "Image":
+ if (nextE._0.ctor === 'Plain')
+ {
+ if (nextE._3 !== currE._3)
+ {
+ node.src = nextE._3;
+ }
+ }
+ else if (!Utils.eq(nextE,currE)
+ || next.props.width !== curr.props.width
+ || next.props.height !== curr.props.height)
+ {
+ return render(next);
+ }
+ updateProps(node, curr, next);
+ return rootNode;
+
+ case "Flow":
+ var arr = List.toArray(nextE._1);
+ for (var i = arr.length; i--; )
+ {
+ arr[i] = arr[i].element.ctor;
+ }
+ if (nextE._0.ctor !== currE._0.ctor)
+ {
+ return render(next);
+ }
+ var nexts = List.toArray(nextE._1);
+ var kids = node.childNodes;
+ if (nexts.length !== kids.length)
+ {
+ return render(next);
+ }
+ var currs = List.toArray(currE._1);
+ var dir = nextE._0.ctor;
+ var goDir = directionTable[dir];
+ var toReverse = needsReversal(dir);
+ var len = kids.length;
+ for (var i = len; i-- ;)
+ {
+ var subNode = kids[toReverse ? len - i - 1 : i];
+ goDir(updateAndReplace(subNode, currs[i], nexts[i]));
+ }
+ updateProps(node, curr, next);
+ return rootNode;
+
+ case "Container":
+ var subNode = node.firstChild;
+ var newSubNode = updateAndReplace(subNode, currE._1, nextE._1);
+ setPos(nextE._0, nextE._1, newSubNode);
+ updateProps(node, curr, next);
+ return rootNode;
+
+ case "Custom":
+ if (currE.type === nextE.type)
+ {
+ var updatedNode = nextE.update(node, currE.model, nextE.model);
+ updateProps(updatedNode, curr, next);
+ return updatedNode;
+ }
+ return render(next);
+ }
+ }
+
+ function updateProps(node, curr, next)
+ {
+ var nextProps = next.props;
+ var currProps = curr.props;
+
+ var element = next.element;
+ var width = nextProps.width - (element.adjustWidth || 0);
+ var height = nextProps.height - (element.adjustHeight || 0);
+ if (width !== currProps.width)
+ {
+ node.style.width = (width|0) + 'px';
+ }
+ if (height !== currProps.height)
+ {
+ node.style.height = (height|0) + 'px';
+ }
+
+ if (nextProps.opacity !== currProps.opacity)
+ {
+ node.style.opacity = nextProps.opacity;
+ }
+
+ var nextColor = nextProps.color.ctor === 'Just'
+ ? Color.toCss(nextProps.color._0)
+ : '';
+ if (node.style.backgroundColor !== nextColor)
+ {
+ node.style.backgroundColor = nextColor;
+ }
+
+ if (nextProps.tag !== currProps.tag)
+ {
+ node.id = nextProps.tag;
+ }
+
+ if (nextProps.href !== currProps.href)
+ {
+ if (currProps.href === '')
+ {
+ // add a surrounding href
+ var anchor = createNode('a');
+ anchor.href = nextProps.href;
+ anchor.style.display = 'block';
+ anchor.style.pointerEvents = 'auto';
+
+ node.parentNode.replaceChild(anchor, node);
+ anchor.appendChild(node);
+ }
+ else if (nextProps.href === '')
+ {
+ // remove the surrounding href
+ var anchor = node.parentNode;
+ anchor.parentNode.replaceChild(node, anchor);
+ }
+ else
+ {
+ // just update the link
+ node.parentNode.href = nextProps.href;
+ }
+ }
+
+ // update click and hover handlers
+ var removed = false;
+
+ // update hover handlers
+ if (currProps.hover.ctor === '_Tuple0')
+ {
+ if (nextProps.hover.ctor !== '_Tuple0')
+ {
+ addHover(node, nextProps.hover);
+ }
+ }
+ else
+ {
+ if (nextProps.hover.ctor === '_Tuple0')
+ {
+ removed = true;
+ removeHover(node);
+ }
+ else
+ {
+ node.elm_hover_handler = nextProps.hover;
+ }
+ }
+
+ // update click handlers
+ if (currProps.click.ctor === '_Tuple0')
+ {
+ if (nextProps.click.ctor !== '_Tuple0')
+ {
+ addClick(node, nextProps.click);
+ }
+ }
+ else
+ {
+ if (nextProps.click.ctor === '_Tuple0')
+ {
+ removed = true;
+ removeClick(node);
+ }
+ else
+ {
+ node.elm_click_handler = nextProps.click;
+ }
+ }
+
+ // stop capturing clicks if
+ if (removed
+ && nextProps.hover.ctor === '_Tuple0'
+ && nextProps.click.ctor === '_Tuple0')
+ {
+ node.style.pointerEvents = 'none';
+ }
+ }
+
+
+ // TEXT
+
+ function block(align)
+ {
+ return function(text)
+ {
+ var raw = {
+ ctor :'RawHtml',
+ html : Text.renderHtml(text),
+ align: align
+ };
+ var pos = htmlHeight(0, raw);
+ return newElement(pos._0, pos._1, raw);
+ }
+ }
+
+ function markdown(text)
+ {
+ var raw = {
+ ctor:'RawHtml',
+ html: text,
+ align: null
+ };
+ var pos = htmlHeight(0, raw);
+ return newElement(pos._0, pos._1, raw);
+ }
+
+ function htmlHeight(width, rawHtml)
+ {
+ // create dummy node
+ var temp = document.createElement('div');
+ temp.innerHTML = rawHtml.html;
+ if (width > 0)
+ {
+ temp.style.width = width + "px";
+ }
+ temp.style.visibility = "hidden";
+ temp.style.styleFloat = "left";
+ temp.style.cssFloat = "left";
+
+ document.body.appendChild(temp);
+
+ // get dimensions
+ var style = window.getComputedStyle(temp, null);
+ var w = Math.ceil(style.getPropertyValue("width").slice(0,-2) - 0);
+ var h = Math.ceil(style.getPropertyValue("height").slice(0,-2) - 0);
+ document.body.removeChild(temp);
+ return Utils.Tuple2(w,h);
+ }
+
+
+ return localRuntime.Native.Graphics.Element.values = {
+ render: render,
+ update: update,
+ updateAndReplace: updateAndReplace,
+
+ createNode: createNode,
+ newElement: F3(newElement),
+ addTransform: addTransform,
+ htmlHeight: F2(htmlHeight),
+ guid: Utils.guid,
+
+ block: block,
+ markdown: markdown
+ };
+
+};
+
+Elm.Native.Http = {};
+Elm.Native.Http.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Http = localRuntime.Native.Http || {};
+ if (localRuntime.Native.Http.values)
+ {
+ return localRuntime.Native.Http.values;
+ }
+
+ var Dict = Elm.Dict.make(localRuntime);
+ var List = Elm.List.make(localRuntime);
+ var Maybe = Elm.Maybe.make(localRuntime);
+ var Task = Elm.Native.Task.make(localRuntime);
+
+
+ function send(settings, request)
+ {
+ return Task.asyncFunction(function(callback) {
+ var req = new XMLHttpRequest();
+
+ // start
+ if (settings.onStart.ctor === 'Just')
+ {
+ req.addEventListener('loadStart', function() {
+ var task = settings.onStart._0;
+ Task.spawn(task);
+ });
+ }
+
+ // progress
+ if (settings.onProgress.ctor === 'Just')
+ {
+ req.addEventListener('progress', function(event) {
+ var progress = !event.lengthComputable
+ ? Maybe.Nothing
+ : Maybe.Just({
+ _: {},
+ loaded: event.loaded,
+ total: event.total
+ });
+ var task = settings.onProgress._0(progress);
+ Task.spawn(task);
+ });
+ }
+
+ // end
+ req.addEventListener('error', function() {
+ return callback(Task.fail({ ctor: 'RawNetworkError' }));
+ });
+
+ req.addEventListener('timeout', function() {
+ return callback(Task.fail({ ctor: 'RawTimeout' }));
+ });
+
+ req.addEventListener('load', function() {
+ return callback(Task.succeed(toResponse(req)));
+ });
+
+ req.open(request.verb, request.url, true);
+
+ // set all the headers
+ function setHeader(pair) {
+ req.setRequestHeader(pair._0, pair._1);
+ }
+ A2(List.map, setHeader, request.headers);
+
+ // set the timeout
+ req.timeout = settings.timeout;
+
+ // ask for a specific MIME type for the response
+ if (settings.desiredResponseType.ctor === 'Just')
+ {
+ req.overrideMimeType(settings.desiredResponseType._0);
+ }
+
+ req.send(request.body._0);
+ });
+ }
+
+
+ // deal with responses
+
+ function toResponse(req)
+ {
+ var tag = typeof req.response === 'string' ? 'Text' : 'Blob';
+ return {
+ _: {},
+ status: req.status,
+ statusText: req.statusText,
+ headers: parseHeaders(req.getAllResponseHeaders()),
+ url: req.responseURL,
+ value: { ctor: tag, _0: req.response }
+ };
+ }
+
+
+ function parseHeaders(rawHeaders)
+ {
+ var headers = Dict.empty;
+
+ if (!rawHeaders)
+ {
+ return headers;
+ }
+
+ var headerPairs = rawHeaders.split('\u000d\u000a');
+ for (var i = headerPairs.length; i--; )
+ {
+ var headerPair = headerPairs[i];
+ var index = headerPair.indexOf('\u003a\u0020');
+ if (index > 0)
+ {
+ var key = headerPair.substring(0, index);
+ var value = headerPair.substring(index + 2);
+
+ headers = A3(Dict.update, key, function(oldValue) {
+ if (oldValue.ctor === 'Just')
+ {
+ return Maybe.Just(value + ', ' + oldValue._0);
+ }
+ return Maybe.Just(value);
+ }, headers);
+ }
+ }
+
+ return headers;
+ }
+
+
+ function multipart(dataList)
+ {
+ var formData = new FormData();
+
+ while (dataList.ctor !== '[]')
+ {
+ var data = dataList._0;
+ if (type === 'StringData')
+ {
+ formData.append(data._0, data._1);
+ }
+ else
+ {
+ var fileName = data._1.ctor === 'Nothing'
+ ? undefined
+ : data._1._0;
+ formData.append(data._0, data._2, fileName);
+ }
+ dataList = dataList._1;
+ }
+
+ return { ctor: 'FormData', formData: formData };
+ }
+
+
+ function uriEncode(string)
+ {
+ return encodeURIComponent(string);
+ }
+
+ function uriDecode(string)
+ {
+ return decodeURIComponent(string);
+ }
+
+ return localRuntime.Native.Http.values = {
+ send: F2(send),
+ multipart: multipart,
+ uriEncode: uriEncode,
+ uriDecode: uriDecode
+ };
+};
+
+Elm.Native.Json = {};
+Elm.Native.Json.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Json = localRuntime.Native.Json || {};
+ if (localRuntime.Native.Json.values) {
+ return localRuntime.Native.Json.values;
+ }
+
+ var ElmArray = Elm.Native.Array.make(localRuntime);
+ var List = Elm.Native.List.make(localRuntime);
+ var Maybe = Elm.Maybe.make(localRuntime);
+ var Result = Elm.Result.make(localRuntime);
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+
+ function crash(expected, actual) {
+ throw new Error(
+ 'expecting ' + expected + ' but got ' + JSON.stringify(actual)
+ );
+ }
+
+
+ // PRIMITIVE VALUES
+
+ function decodeNull(successValue) {
+ return function(value) {
+ if (value === null) {
+ return successValue;
+ }
+ crash('null', value);
+ };
+ }
+
+
+ function decodeString(value) {
+ if (typeof value === 'string' || value instanceof String) {
+ return value;
+ }
+ crash('a String', value);
+ }
+
+
+ function decodeFloat(value) {
+ if (typeof value === 'number') {
+ return value;
+ }
+ crash('a Float', value);
+ }
+
+
+ function decodeInt(value) {
+ if (typeof value === 'number' && (value|0) === value) {
+ return value;
+ }
+ crash('an Int', value);
+ }
+
+
+ function decodeBool(value) {
+ if (typeof value === 'boolean') {
+ return value;
+ }
+ crash('a Bool', value);
+ }
+
+
+ // ARRAY
+
+ function decodeArray(decoder) {
+ return function(value) {
+ if (value instanceof Array) {
+ var len = value.length;
+ var array = new Array(len);
+ for (var i = len; i-- ; ) {
+ array[i] = decoder(value[i]);
+ }
+ return ElmArray.fromJSArray(array);
+ }
+ crash('an Array', value);
+ };
+ }
+
+
+ // LIST
+
+ function decodeList(decoder) {
+ return function(value) {
+ if (value instanceof Array) {
+ var len = value.length;
+ var list = List.Nil;
+ for (var i = len; i-- ; ) {
+ list = List.Cons( decoder(value[i]), list );
+ }
+ return list;
+ }
+ crash('a List', value);
+ };
+ }
+
+
+ // MAYBE
+
+ function decodeMaybe(decoder) {
+ return function(value) {
+ try {
+ return Maybe.Just(decoder(value));
+ } catch(e) {
+ return Maybe.Nothing;
+ }
+ };
+ }
+
+
+ // FIELDS
+
+ function decodeField(field, decoder) {
+ return function(value) {
+ var subValue = value[field];
+ if (subValue !== undefined) {
+ return decoder(subValue);
+ }
+ crash("an object with field '" + field + "'", value);
+ };
+ }
+
+
+ // OBJECTS
+
+ function decodeKeyValuePairs(decoder) {
+ return function(value) {
+ var isObject =
+ typeof value === 'object'
+ && value !== null
+ && !(value instanceof Array);
+
+ if (isObject) {
+ var keyValuePairs = List.Nil;
+ for (var key in value) {
+ var elmValue = decoder(value[key]);
+ var pair = Utils.Tuple2(key, elmValue);
+ keyValuePairs = List.Cons(pair, keyValuePairs);
+ }
+ return keyValuePairs;
+ }
+
+ crash("an object", value);
+ };
+ }
+
+ function decodeObject1(f, d1) {
+ return function(value) {
+ return f(d1(value));
+ };
+ }
+
+ function decodeObject2(f, d1, d2) {
+ return function(value) {
+ return A2( f, d1(value), d2(value) );
+ };
+ }
+
+ function decodeObject3(f, d1, d2, d3) {
+ return function(value) {
+ return A3( f, d1(value), d2(value), d3(value) );
+ };
+ }
+
+ function decodeObject4(f, d1, d2, d3, d4) {
+ return function(value) {
+ return A4( f, d1(value), d2(value), d3(value), d4(value) );
+ };
+ }
+
+ function decodeObject5(f, d1, d2, d3, d4, d5) {
+ return function(value) {
+ return A5( f, d1(value), d2(value), d3(value), d4(value), d5(value) );
+ };
+ }
+
+ function decodeObject6(f, d1, d2, d3, d4, d5, d6) {
+ return function(value) {
+ return A6( f,
+ d1(value),
+ d2(value),
+ d3(value),
+ d4(value),
+ d5(value),
+ d6(value)
+ );
+ };
+ }
+
+ function decodeObject7(f, d1, d2, d3, d4, d5, d6, d7) {
+ return function(value) {
+ return A7( f,
+ d1(value),
+ d2(value),
+ d3(value),
+ d4(value),
+ d5(value),
+ d6(value),
+ d7(value)
+ );
+ };
+ }
+
+ function decodeObject8(f, d1, d2, d3, d4, d5, d6, d7, d8) {
+ return function(value) {
+ return A8( f,
+ d1(value),
+ d2(value),
+ d3(value),
+ d4(value),
+ d5(value),
+ d6(value),
+ d7(value),
+ d8(value)
+ );
+ };
+ }
+
+
+ // TUPLES
+
+ function decodeTuple1(f, d1) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 1 ) {
+ crash('a Tuple of length 1', value);
+ }
+ return f( d1(value[0]) );
+ };
+ }
+
+ function decodeTuple2(f, d1, d2) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 2 ) {
+ crash('a Tuple of length 2', value);
+ }
+ return A2( f, d1(value[0]), d2(value[1]) );
+ };
+ }
+
+ function decodeTuple3(f, d1, d2, d3) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 3 ) {
+ crash('a Tuple of length 3', value);
+ }
+ return A3( f, d1(value[0]), d2(value[1]), d3(value[2]) );
+ };
+ }
+
+
+ function decodeTuple4(f, d1, d2, d3, d4) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 4 ) {
+ crash('a Tuple of length 4', value);
+ }
+ return A4( f, d1(value[0]), d2(value[1]), d3(value[2]), d4(value[3]) );
+ };
+ }
+
+
+ function decodeTuple5(f, d1, d2, d3, d4, d5) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 5 ) {
+ crash('a Tuple of length 5', value);
+ }
+ return A5( f,
+ d1(value[0]),
+ d2(value[1]),
+ d3(value[2]),
+ d4(value[3]),
+ d5(value[4])
+ );
+ };
+ }
+
+
+ function decodeTuple6(f, d1, d2, d3, d4, d5, d6) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 6 ) {
+ crash('a Tuple of length 6', value);
+ }
+ return A6( f,
+ d1(value[0]),
+ d2(value[1]),
+ d3(value[2]),
+ d4(value[3]),
+ d5(value[4]),
+ d6(value[5])
+ );
+ };
+ }
+
+ function decodeTuple7(f, d1, d2, d3, d4, d5, d6, d7) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 7 ) {
+ crash('a Tuple of length 7', value);
+ }
+ return A7( f,
+ d1(value[0]),
+ d2(value[1]),
+ d3(value[2]),
+ d4(value[3]),
+ d5(value[4]),
+ d6(value[5]),
+ d7(value[6])
+ );
+ };
+ }
+
+
+ function decodeTuple8(f, d1, d2, d3, d4, d5, d6, d7, d8) {
+ return function(value) {
+ if ( !(value instanceof Array) || value.length !== 8 ) {
+ crash('a Tuple of length 8', value);
+ }
+ return A8( f,
+ d1(value[0]),
+ d2(value[1]),
+ d3(value[2]),
+ d4(value[3]),
+ d5(value[4]),
+ d6(value[5]),
+ d7(value[6]),
+ d8(value[7])
+ );
+ };
+ }
+
+
+ // CUSTOM DECODERS
+
+ function decodeValue(value) {
+ return value;
+ }
+
+ function runDecoderValue(decoder, value) {
+ try {
+ return Result.Ok(decoder(value));
+ } catch(e) {
+ return Result.Err(e.message);
+ }
+ }
+
+ function customDecoder(decoder, callback) {
+ return function(value) {
+ var result = callback(decoder(value));
+ if (result.ctor === 'Err') {
+ throw new Error('custom decoder failed: ' + result._0);
+ }
+ return result._0;
+ }
+ }
+
+ function andThen(decode, callback) {
+ return function(value) {
+ var result = decode(value);
+ return callback(result)(value);
+ }
+ }
+
+ function fail(msg) {
+ return function(value) {
+ throw new Error(msg);
+ }
+ }
+
+ function succeed(successValue) {
+ return function(value) {
+ return successValue;
+ }
+ }
+
+
+ // ONE OF MANY
+
+ function oneOf(decoders) {
+ return function(value) {
+ var errors = [];
+ var temp = decoders;
+ while (temp.ctor !== '[]') {
+ try {
+ return temp._0(value);
+ } catch(e) {
+ errors.push(e.message);
+ }
+ temp = temp._1;
+ }
+ throw new Error('expecting one of the following:\n ' + errors.join('\n '));
+ }
+ }
+
+ function get(decoder, value) {
+ try {
+ return Result.Ok(decoder(value));
+ } catch(e) {
+ return Result.Err(e.message);
+ }
+ }
+
+
+ // ENCODE / DECODE
+
+ function runDecoderString(decoder, string) {
+ try {
+ return Result.Ok(decoder(JSON.parse(string)));
+ } catch(e) {
+ return Result.Err(e.message);
+ }
+ }
+
+ function encode(indentLevel, value) {
+ return JSON.stringify(value, null, indentLevel);
+ }
+
+ function identity(value) {
+ return value;
+ }
+
+ function encodeObject(keyValuePairs) {
+ var obj = {};
+ while (keyValuePairs.ctor !== '[]') {
+ var pair = keyValuePairs._0;
+ obj[pair._0] = pair._1;
+ keyValuePairs = keyValuePairs._1;
+ }
+ return obj;
+ }
+
+ return localRuntime.Native.Json.values = {
+ encode: F2(encode),
+ runDecoderString: F2(runDecoderString),
+ runDecoderValue: F2(runDecoderValue),
+
+ get: F2(get),
+ oneOf: oneOf,
+
+ decodeNull: decodeNull,
+ decodeInt: decodeInt,
+ decodeFloat: decodeFloat,
+ decodeString: decodeString,
+ decodeBool: decodeBool,
+
+ decodeMaybe: decodeMaybe,
+
+ decodeList: decodeList,
+ decodeArray: decodeArray,
+
+ decodeField: F2(decodeField),
+
+ decodeObject1: F2(decodeObject1),
+ decodeObject2: F3(decodeObject2),
+ decodeObject3: F4(decodeObject3),
+ decodeObject4: F5(decodeObject4),
+ decodeObject5: F6(decodeObject5),
+ decodeObject6: F7(decodeObject6),
+ decodeObject7: F8(decodeObject7),
+ decodeObject8: F9(decodeObject8),
+ decodeKeyValuePairs: decodeKeyValuePairs,
+
+ decodeTuple1: F2(decodeTuple1),
+ decodeTuple2: F3(decodeTuple2),
+ decodeTuple3: F4(decodeTuple3),
+ decodeTuple4: F5(decodeTuple4),
+ decodeTuple5: F6(decodeTuple5),
+ decodeTuple6: F7(decodeTuple6),
+ decodeTuple7: F8(decodeTuple7),
+ decodeTuple8: F9(decodeTuple8),
+
+ andThen: F2(andThen),
+ decodeValue: decodeValue,
+ customDecoder: F2(customDecoder),
+ fail: fail,
+ succeed: succeed,
+
+ identity: identity,
+ encodeNull: null,
+ encodeArray: ElmArray.toJSArray,
+ encodeList: List.toArray,
+ encodeObject: encodeObject
+
+ };
+
+};
+
+Elm.Native.List = {};
+Elm.Native.List.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.List = localRuntime.Native.List || {};
+ if (localRuntime.Native.List.values)
+ {
+ return localRuntime.Native.List.values;
+ }
+ if ('values' in Elm.Native.List)
+ {
+ return localRuntime.Native.List.values = Elm.Native.List.values;
+ }
+
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+ var Nil = Utils.Nil;
+ var Cons = Utils.Cons;
+
+ function toArray(xs)
+ {
+ var out = [];
+ while (xs.ctor !== '[]')
+ {
+ out.push(xs._0);
+ xs = xs._1;
+ }
+ return out;
+ }
+
+ function fromArray(arr)
+ {
+ var out = Nil;
+ for (var i = arr.length; i--; )
+ {
+ out = Cons(arr[i], out);
+ }
+ return out;
+ }
+
+ function range(lo,hi)
+ {
+ var lst = Nil;
+ if (lo <= hi)
+ {
+ do { lst = Cons(hi,lst) } while (hi-->lo);
+ }
+ return lst
+ }
+
+ // f defined similarly for both foldl and foldr (NB: different from Haskell)
+ // ie, foldl : (a -> b -> b) -> b -> [a] -> b
+ function foldl(f, b, xs)
+ {
+ var acc = b;
+ while (xs.ctor !== '[]')
+ {
+ acc = A2(f, xs._0, acc);
+ xs = xs._1;
+ }
+ return acc;
+ }
+
+ function foldr(f, b, xs)
+ {
+ var arr = toArray(xs);
+ var acc = b;
+ for (var i = arr.length; i--; )
+ {
+ acc = A2(f, arr[i], acc);
+ }
+ return acc;
+ }
+
+ function any(pred, xs)
+ {
+ while (xs.ctor !== '[]')
+ {
+ if (pred(xs._0))
+ {
+ return true;
+ }
+ xs = xs._1;
+ }
+ return false;
+ }
+
+ function map2(f, xs, ys)
+ {
+ var arr = [];
+ while (xs.ctor !== '[]' && ys.ctor !== '[]')
+ {
+ arr.push(A2(f, xs._0, ys._0));
+ xs = xs._1;
+ ys = ys._1;
+ }
+ return fromArray(arr);
+ }
+
+ function map3(f, xs, ys, zs)
+ {
+ var arr = [];
+ while (xs.ctor !== '[]' && ys.ctor !== '[]' && zs.ctor !== '[]')
+ {
+ arr.push(A3(f, xs._0, ys._0, zs._0));
+ xs = xs._1;
+ ys = ys._1;
+ zs = zs._1;
+ }
+ return fromArray(arr);
+ }
+
+ function map4(f, ws, xs, ys, zs)
+ {
+ var arr = [];
+ while ( ws.ctor !== '[]'
+ && xs.ctor !== '[]'
+ && ys.ctor !== '[]'
+ && zs.ctor !== '[]')
+ {
+ arr.push(A4(f, ws._0, xs._0, ys._0, zs._0));
+ ws = ws._1;
+ xs = xs._1;
+ ys = ys._1;
+ zs = zs._1;
+ }
+ return fromArray(arr);
+ }
+
+ function map5(f, vs, ws, xs, ys, zs)
+ {
+ var arr = [];
+ while ( vs.ctor !== '[]'
+ && ws.ctor !== '[]'
+ && xs.ctor !== '[]'
+ && ys.ctor !== '[]'
+ && zs.ctor !== '[]')
+ {
+ arr.push(A5(f, vs._0, ws._0, xs._0, ys._0, zs._0));
+ vs = vs._1;
+ ws = ws._1;
+ xs = xs._1;
+ ys = ys._1;
+ zs = zs._1;
+ }
+ return fromArray(arr);
+ }
+
+ function sortBy(f, xs)
+ {
+ return fromArray(toArray(xs).sort(function(a,b){
+ return Utils.cmp(f(a), f(b));
+ }));
+ }
+
+ function sortWith(f, xs)
+ {
+ return fromArray(toArray(xs).sort(function(a,b){
+ var ord = f(a)(b).ctor;
+ return ord === 'EQ' ? 0 : ord === 'LT' ? -1 : 1;
+ }));
+ }
+
+ function take(n, xs)
+ {
+ var arr = [];
+ while (xs.ctor !== '[]' && n > 0)
+ {
+ arr.push(xs._0);
+ xs = xs._1;
+ --n;
+ }
+ return fromArray(arr);
+ }
+
+ function drop(n, xs)
+ {
+ while (xs.ctor !== '[]' && n > 0)
+ {
+ xs = xs._1;
+ --n;
+ }
+ return xs;
+ }
+
+ function repeat(n, x)
+ {
+ var arr = [];
+ var pattern = [x];
+ while (n > 0)
+ {
+ if (n & 1)
+ {
+ arr = arr.concat(pattern);
+ }
+ n >>= 1, pattern = pattern.concat(pattern);
+ }
+ return fromArray(arr);
+ }
+
+
+ Elm.Native.List.values = {
+ Nil:Nil,
+ Cons:Cons,
+ cons:F2(Cons),
+ toArray:toArray,
+ fromArray:fromArray,
+ range:range,
+
+ foldl:F3(foldl),
+ foldr:F3(foldr),
+
+ any:F2(any),
+ map2:F3(map2),
+ map3:F4(map3),
+ map4:F5(map4),
+ map5:F6(map5),
+ sortBy:F2(sortBy),
+ sortWith:F2(sortWith),
+ take:F2(take),
+ drop:F2(drop),
+ repeat:F2(repeat)
+ };
+ return localRuntime.Native.List.values = Elm.Native.List.values;
+
+};
+
+Elm.Native.Port = {};
+Elm.Native.Port.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Port = localRuntime.Native.Port || {};
+ if (localRuntime.Native.Port.values)
+ {
+ return localRuntime.Native.Port.values;
+ }
+
+ var NS;
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+
+ // INBOUND
+
+ function inbound(name, type, converter)
+ {
+ if (!localRuntime.argsTracker[name])
+ {
+ throw new Error(
+ "Port Error:\n" +
+ "No argument was given for the port named '" + name + "' with type:\n\n" +
+ " " + type.split('\n').join('\n ') + "\n\n" +
+ "You need to provide an initial value!\n\n" +
+ "Find out more about ports here <http://elm-lang.org/learn/Ports.elm>"
+ );
+ }
+ var arg = localRuntime.argsTracker[name];
+ arg.used = true;
+
+ return jsToElm(name, type, converter, arg.value);
+ }
+
+
+ function inboundSignal(name, type, converter)
+ {
+ var initialValue = inbound(name, type, converter);
+
+ if (!NS)
+ {
+ NS = Elm.Native.Signal.make(localRuntime);
+ }
+ var signal = NS.input('inbound-port-' + name, initialValue);
+
+ function send(jsValue)
+ {
+ var elmValue = jsToElm(name, type, converter, jsValue);
+ setTimeout(function() {
+ localRuntime.notify(signal.id, elmValue);
+ }, 0);
+ }
+
+ localRuntime.ports[name] = { send: send };
+
+ return signal;
+ }
+
+
+ function jsToElm(name, type, converter, value)
+ {
+ try
+ {
+ return converter(value);
+ }
+ catch(e)
+ {
+ throw new Error(
+ "Port Error:\n" +
+ "Regarding the port named '" + name + "' with type:\n\n" +
+ " " + type.split('\n').join('\n ') + "\n\n" +
+ "You just sent the value:\n\n" +
+ " " + JSON.stringify(value) + "\n\n" +
+ "but it cannot be converted to the necessary type.\n" +
+ e.message
+ );
+ }
+ }
+
+
+ // OUTBOUND
+
+ function outbound(name, converter, elmValue)
+ {
+ localRuntime.ports[name] = converter(elmValue);
+ }
+
+
+ function outboundSignal(name, converter, signal)
+ {
+ var subscribers = [];
+
+ function subscribe(handler)
+ {
+ subscribers.push(handler);
+ }
+ function unsubscribe(handler)
+ {
+ subscribers.pop(subscribers.indexOf(handler));
+ }
+
+ function notify(elmValue)
+ {
+ var jsValue = converter(elmValue);
+ var len = subscribers.length;
+ for (var i = 0; i < len; ++i)
+ {
+ subscribers[i](jsValue);
+ }
+ }
+
+ if (!NS)
+ {
+ NS = Elm.Native.Signal.make(localRuntime);
+ }
+ NS.output('outbound-port-' + name, notify, signal);
+
+ localRuntime.ports[name] = {
+ subscribe: subscribe,
+ unsubscribe: unsubscribe
+ };
+
+ return signal;
+ }
+
+
+ return localRuntime.Native.Port.values = {
+ inbound: inbound,
+ outbound: outbound,
+ inboundSignal: inboundSignal,
+ outboundSignal: outboundSignal
+ };
+};
+
+Elm.Native.Reads = {};
+Elm.Native.Reads.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Reads = localRuntime.Native.Reads || {};
+ if(localRuntime.Native.Reads.values) {
+ return localRuntime.Native.Reads.values;
+ }
+
+ var Maybe = Elm.Maybe.make(localRuntime);
+
+ function readInt(str) {
+ var number = Number(str);
+ return isNaN(number) || str === ''
+ ? Maybe.Nothing
+ : Maybe.Just(number);
+ }
+
+ return localRuntime.Native.Reads.values = {
+ readInt: readInt
+ };
+};
+
+
+if (!Elm.fullscreen) {
+
+ (function() {
+ 'use strict';
+
+ var Display = {
+ FULLSCREEN: 0,
+ COMPONENT: 1,
+ NONE: 2
+ };
+
+ Elm.fullscreen = function(module, args)
+ {
+ var container = document.createElement('div');
+ document.body.appendChild(container);
+ return init(Display.FULLSCREEN, container, module, args || {});
+ };
+
+ Elm.embed = function(module, container, args)
+ {
+ var tag = container.tagName;
+ if (tag !== 'DIV')
+ {
+ throw new Error('Elm.node must be given a DIV, not a ' + tag + '.');
+ }
+ return init(Display.COMPONENT, container, module, args || {});
+ };
+
+ Elm.worker = function(module, args)
+ {
+ return init(Display.NONE, {}, module, args || {});
+ };
+
+ function init(display, container, module, args, moduleToReplace)
+ {
+ // defining state needed for an instance of the Elm RTS
+ var inputs = [];
+
+ /* OFFSET
+ * Elm's time traveling debugger lets you pause time. This means
+ * "now" may be shifted a bit into the past. By wrapping Date.now()
+ * we can manage this.
+ */
+ var timer = {
+ programStart: Date.now(),
+ now: function()
+ {
+ return Date.now();
+ }
+ };
+
+ var updateInProgress = false;
+ function notify(id, v)
+ {
+ if (updateInProgress)
+ {
+ throw new Error(
+ 'The notify function has been called synchronously!\n' +
+ 'This can lead to frames being dropped.\n' +
+ 'Definitely report this to <https://github.com/elm-lang/Elm/issues>\n');
+ }
+ updateInProgress = true;
+ var timestep = timer.now();
+ for (var i = inputs.length; i--; )
+ {
+ inputs[i].notify(timestep, id, v);
+ }
+ updateInProgress = false;
+ }
+ function setTimeout(func, delay)
+ {
+ return window.setTimeout(func, delay);
+ }
+
+ var listeners = [];
+ function addListener(relevantInputs, domNode, eventName, func)
+ {
+ domNode.addEventListener(eventName, func);
+ var listener = {
+ relevantInputs: relevantInputs,
+ domNode: domNode,
+ eventName: eventName,
+ func: func
+ };
+ listeners.push(listener);
+ }
+
+ var argsTracker = {};
+ for (var name in args)
+ {
+ argsTracker[name] = {
+ value: args[name],
+ used: false
+ };
+ }
+
+ // create the actual RTS. Any impure modules will attach themselves to this
+ // object. This permits many Elm programs to be embedded per document.
+ var elm = {
+ notify: notify,
+ setTimeout: setTimeout,
+ node: container,
+ addListener: addListener,
+ inputs: inputs,
+ timer: timer,
+ argsTracker: argsTracker,
+ ports: {},
+
+ isFullscreen: function() { return display === Display.FULLSCREEN; },
+ isEmbed: function() { return display === Display.COMPONENT; },
+ isWorker: function() { return display === Display.NONE; }
+ };
+
+ function swap(newModule)
+ {
+ removeListeners(listeners);
+ var div = document.createElement('div');
+ var newElm = init(display, div, newModule, args, elm);
+ inputs = [];
+ // elm.swap = newElm.swap;
+ return newElm;
+ }
+
+ function dispose()
+ {
+ removeListeners(listeners);
+ inputs = [];
+ }
+
+ var Module = {};
+ try
+ {
+ Module = module.make(elm);
+ checkInputs(elm);
+ }
+ catch (error)
+ {
+ if (typeof container.appendChild == 'undefined')
+ {
+ console.log(error.message);
+ }
+ else
+ {
+ container.appendChild(errorNode(error.message));
+ }
+ throw error;
+ }
+
+ if (display !== Display.NONE)
+ {
+ var graphicsNode = initGraphics(elm, Module);
+ }
+
+ var rootNode = { kids: inputs };
+ trimDeadNodes(rootNode);
+ inputs = rootNode.kids;
+ filterListeners(inputs, listeners);
+
+ addReceivers(elm.ports);
+
+ if (typeof moduleToReplace !== 'undefined')
+ {
+ hotSwap(moduleToReplace, elm);
+
+ // rerender scene if graphics are enabled.
+ if (typeof graphicsNode !== 'undefined')
+ {
+ graphicsNode.notify(0, true, 0);
+ }
+ }
+
+ return {
+ swap: swap,
+ ports: elm.ports,
+ dispose: dispose
+ };
+ };
+
+ function checkInputs(elm)
+ {
+ var argsTracker = elm.argsTracker;
+ for (var name in argsTracker)
+ {
+ if (!argsTracker[name].used)
+ {
+ throw new Error(
+ "Port Error:\nYou provided an argument named '" + name +
+ "' but there is no corresponding port!\n\n" +
+ "Maybe add a port '" + name + "' to your Elm module?\n" +
+ "Maybe remove the '" + name + "' argument from your initialization code in JS?"
+ );
+ }
+ }
+ }
+
+ function errorNode(message)
+ {
+ var code = document.createElement('code');
+
+ var lines = message.split('\n');
+ code.appendChild(document.createTextNode(lines[0]));
+ code.appendChild(document.createElement('br'));
+ code.appendChild(document.createElement('br'));
+ for (var i = 1; i < lines.length; ++i)
+ {
+ code.appendChild(document.createTextNode('\u00A0 \u00A0 ' + lines[i].replace(/ /g, '\u00A0 ')));
+ code.appendChild(document.createElement('br'));
+ }
+ code.appendChild(document.createElement('br'));
+ code.appendChild(document.createTextNode("Open the developer console for more details."));
+ return code;
+ }
+
+
+ //// FILTER SIGNALS ////
+
+ // TODO: move this code into the signal module and create a function
+ // Signal.initializeGraph that actually instantiates everything.
+
+ function filterListeners(inputs, listeners)
+ {
+ loop:
+ for (var i = listeners.length; i--; )
+ {
+ var listener = listeners[i];
+ for (var j = inputs.length; j--; )
+ {
+ if (listener.relevantInputs.indexOf(inputs[j].id) >= 0)
+ {
+ continue loop;
+ }
+ }
+ listener.domNode.removeEventListener(listener.eventName, listener.func);
+ }
+ }
+
+ function removeListeners(listeners)
+ {
+ for (var i = listeners.length; i--; )
+ {
+ var listener = listeners[i];
+ listener.domNode.removeEventListener(listener.eventName, listener.func);
+ }
+ }
+
+ // add receivers for built-in ports if they are defined
+ function addReceivers(ports)
+ {
+ if ('title' in ports)
+ {
+ if (typeof ports.title === 'string')
+ {
+ document.title = ports.title;
+ }
+ else
+ {
+ ports.title.subscribe(function(v) { document.title = v; });
+ }
+ }
+ if ('redirect' in ports)
+ {
+ ports.redirect.subscribe(function(v) {
+ if (v.length > 0)
+ {
+ window.location = v;
+ }
+ });
+ }
+ }
+
+
+ // returns a boolean representing whether the node is alive or not.
+ function trimDeadNodes(node)
+ {
+ if (node.isOutput)
+ {
+ return true;
+ }
+
+ var liveKids = [];
+ for (var i = node.kids.length; i--; )
+ {
+ var kid = node.kids[i];
+ if (trimDeadNodes(kid))
+ {
+ liveKids.push(kid);
+ }
+ }
+ node.kids = liveKids;
+
+ return liveKids.length > 0;
+ }
+
+
+ //// RENDERING ////
+
+ function initGraphics(elm, Module)
+ {
+ if (!('main' in Module))
+ {
+ throw new Error("'main' is missing! What do I display?!");
+ }
+
+ var signalGraph = Module.main;
+
+ // make sure the signal graph is actually a signal & extract the visual model
+ if (!('notify' in signalGraph))
+ {
+ signalGraph = Elm.Signal.make(elm).constant(signalGraph);
+ }
+ var initialScene = signalGraph.value;
+
+ // Figure out what the render functions should be
+ var render;
+ var update;
+ if (initialScene.props)
+ {
+ var Element = Elm.Native.Graphics.Element.make(elm);
+ render = Element.render;
+ update = Element.updateAndReplace;
+ }
+ else
+ {
+ var VirtualDom = Elm.Native.VirtualDom.make(elm);
+ render = VirtualDom.render;
+ update = VirtualDom.updateAndReplace;
+ }
+
+ // Add the initialScene to the DOM
+ var container = elm.node;
+ var node = render(initialScene);
+ while (container.firstChild)
+ {
+ container.removeChild(container.firstChild);
+ }
+ container.appendChild(node);
+
+ var _requestAnimationFrame =
+ typeof requestAnimationFrame !== 'undefined'
+ ? requestAnimationFrame
+ : function(cb) { setTimeout(cb, 1000/60); }
+ ;
+
+ // domUpdate is called whenever the main Signal changes.
+ //
+ // domUpdate and drawCallback implement a small state machine in order
+ // to schedule only 1 draw per animation frame. This enforces that
+ // once draw has been called, it will not be called again until the
+ // next frame.
+ //
+ // drawCallback is scheduled whenever
+ // 1. The state transitions from PENDING_REQUEST to EXTRA_REQUEST, or
+ // 2. The state transitions from NO_REQUEST to PENDING_REQUEST
+ //
+ // Invariants:
+ // 1. In the NO_REQUEST state, there is never a scheduled drawCallback.
+ // 2. In the PENDING_REQUEST and EXTRA_REQUEST states, there is always exactly 1
+ // scheduled drawCallback.
+ var NO_REQUEST = 0;
+ var PENDING_REQUEST = 1;
+ var EXTRA_REQUEST = 2;
+ var state = NO_REQUEST;
+ var savedScene = initialScene;
+ var scheduledScene = initialScene;
+
+ function domUpdate(newScene)
+ {
+ scheduledScene = newScene;
+
+ switch (state)
+ {
+ case NO_REQUEST:
+ _requestAnimationFrame(drawCallback);
+ state = PENDING_REQUEST;
+ return;
+ case PENDING_REQUEST:
+ state = PENDING_REQUEST;
+ return;
+ case EXTRA_REQUEST:
+ state = PENDING_REQUEST;
+ return;
+ }
+ }
+
+ function drawCallback()
+ {
+ switch (state)
+ {
+ case NO_REQUEST:
+ // This state should not be possible. How can there be no
+ // request, yet somehow we are actively fulfilling a
+ // request?
+ throw new Error(
+ "Unexpected draw callback.\n" +
+ "Please report this to <https://github.com/elm-lang/core/issues>."
+ );
+
+ case PENDING_REQUEST:
+ // At this point, we do not *know* that another frame is
+ // needed, but we make an extra request to rAF just in
+ // case. It's possible to drop a frame if rAF is called
+ // too late, so we just do it preemptively.
+ _requestAnimationFrame(drawCallback);
+ state = EXTRA_REQUEST;
+
+ // There's also stuff we definitely need to draw.
+ draw();
+ return;
+
+ case EXTRA_REQUEST:
+ // Turns out the extra request was not needed, so we will
+ // stop calling rAF. No reason to call it all the time if
+ // no one needs it.
+ state = NO_REQUEST;
+ return;
+ }
+ }
+
+ function draw()
+ {
+ update(elm.node.firstChild, savedScene, scheduledScene);
+ if (elm.Native.Window)
+ {
+ elm.Native.Window.values.resizeIfNeeded();
+ }
+ savedScene = scheduledScene;
+ }
+
+ var renderer = Elm.Native.Signal.make(elm).output('main', domUpdate, signalGraph);
+
+ // must check for resize after 'renderer' is created so
+ // that changes show up.
+ if (elm.Native.Window)
+ {
+ elm.Native.Window.values.resizeIfNeeded();
+ }
+
+ return renderer;
+ }
+
+ //// HOT SWAPPING ////
+
+ // Returns boolean indicating if the swap was successful.
+ // Requires that the two signal graphs have exactly the same
+ // structure.
+ function hotSwap(from, to)
+ {
+ function similar(nodeOld,nodeNew)
+ {
+ if (nodeOld.id !== nodeNew.id)
+ {
+ return false;
+ }
+ if (nodeOld.isOutput)
+ {
+ return nodeNew.isOutput;
+ }
+ return nodeOld.kids.length === nodeNew.kids.length;
+ }
+ function swap(nodeOld,nodeNew)
+ {
+ nodeNew.value = nodeOld.value;
+ return true;
+ }
+ var canSwap = depthFirstTraversals(similar, from.inputs, to.inputs);
+ if (canSwap)
+ {
+ depthFirstTraversals(swap, from.inputs, to.inputs);
+ }
+ from.node.parentNode.replaceChild(to.node, from.node);
+
+ return canSwap;
+ }
+
+ // Returns false if the node operation f ever fails.
+ function depthFirstTraversals(f, queueOld, queueNew)
+ {
+ if (queueOld.length !== queueNew.length)
+ {
+ return false;
+ }
+ queueOld = queueOld.slice(0);
+ queueNew = queueNew.slice(0);
+
+ var seen = [];
+ while (queueOld.length > 0 && queueNew.length > 0)
+ {
+ var nodeOld = queueOld.pop();
+ var nodeNew = queueNew.pop();
+ if (seen.indexOf(nodeOld.id) < 0)
+ {
+ if (!f(nodeOld, nodeNew))
+ {
+ return false;
+ }
+ queueOld = queueOld.concat(nodeOld.kids || []);
+ queueNew = queueNew.concat(nodeNew.kids || []);
+ seen.push(nodeOld.id);
+ }
+ }
+ return true;
+ }
+ }());
+
+ function F2(fun)
+ {
+ function wrapper(a) { return function(b) { return fun(a,b) } }
+ wrapper.arity = 2;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F3(fun)
+ {
+ function wrapper(a) {
+ return function(b) { return function(c) { return fun(a,b,c) }}
+ }
+ wrapper.arity = 3;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F4(fun)
+ {
+ function wrapper(a) { return function(b) { return function(c) {
+ return function(d) { return fun(a,b,c,d) }}}
+ }
+ wrapper.arity = 4;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F5(fun)
+ {
+ function wrapper(a) { return function(b) { return function(c) {
+ return function(d) { return function(e) { return fun(a,b,c,d,e) }}}}
+ }
+ wrapper.arity = 5;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F6(fun)
+ {
+ function wrapper(a) { return function(b) { return function(c) {
+ return function(d) { return function(e) { return function(f) {
+ return fun(a,b,c,d,e,f) }}}}}
+ }
+ wrapper.arity = 6;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F7(fun)
+ {
+ function wrapper(a) { return function(b) { return function(c) {
+ return function(d) { return function(e) { return function(f) {
+ return function(g) { return fun(a,b,c,d,e,f,g) }}}}}}
+ }
+ wrapper.arity = 7;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F8(fun)
+ {
+ function wrapper(a) { return function(b) { return function(c) {
+ return function(d) { return function(e) { return function(f) {
+ return function(g) { return function(h) {
+ return fun(a,b,c,d,e,f,g,h)}}}}}}}
+ }
+ wrapper.arity = 8;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function F9(fun)
+ {
+ function wrapper(a) { return function(b) { return function(c) {
+ return function(d) { return function(e) { return function(f) {
+ return function(g) { return function(h) { return function(i) {
+ return fun(a,b,c,d,e,f,g,h,i) }}}}}}}}
+ }
+ wrapper.arity = 9;
+ wrapper.func = fun;
+ return wrapper;
+ }
+
+ function A2(fun,a,b)
+ {
+ return fun.arity === 2
+ ? fun.func(a,b)
+ : fun(a)(b);
+ }
+ function A3(fun,a,b,c)
+ {
+ return fun.arity === 3
+ ? fun.func(a,b,c)
+ : fun(a)(b)(c);
+ }
+ function A4(fun,a,b,c,d)
+ {
+ return fun.arity === 4
+ ? fun.func(a,b,c,d)
+ : fun(a)(b)(c)(d);
+ }
+ function A5(fun,a,b,c,d,e)
+ {
+ return fun.arity === 5
+ ? fun.func(a,b,c,d,e)
+ : fun(a)(b)(c)(d)(e);
+ }
+ function A6(fun,a,b,c,d,e,f)
+ {
+ return fun.arity === 6
+ ? fun.func(a,b,c,d,e,f)
+ : fun(a)(b)(c)(d)(e)(f);
+ }
+ function A7(fun,a,b,c,d,e,f,g)
+ {
+ return fun.arity === 7
+ ? fun.func(a,b,c,d,e,f,g)
+ : fun(a)(b)(c)(d)(e)(f)(g);
+ }
+ function A8(fun,a,b,c,d,e,f,g,h)
+ {
+ return fun.arity === 8
+ ? fun.func(a,b,c,d,e,f,g,h)
+ : fun(a)(b)(c)(d)(e)(f)(g)(h);
+ }
+ function A9(fun,a,b,c,d,e,f,g,h,i)
+ {
+ return fun.arity === 9
+ ? fun.func(a,b,c,d,e,f,g,h,i)
+ : fun(a)(b)(c)(d)(e)(f)(g)(h)(i);
+ }
+}
+
+Elm.Native.Show = {};
+Elm.Native.Show.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Show = localRuntime.Native.Show || {};
+ if (localRuntime.Native.Show.values)
+ {
+ return localRuntime.Native.Show.values;
+ }
+
+ var _Array;
+ var Dict;
+ var List;
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+ var toString = function(v)
+ {
+ var type = typeof v;
+ if (type === "function")
+ {
+ var name = v.func ? v.func.name : v.name;
+ return '<function' + (name === '' ? '' : ': ') + name + '>';
+ }
+ else if (type === "boolean")
+ {
+ return v ? "True" : "False";
+ }
+ else if (type === "number")
+ {
+ return v + "";
+ }
+ else if ((v instanceof String) && v.isChar)
+ {
+ return "'" + addSlashes(v, true) + "'";
+ }
+ else if (type === "string")
+ {
+ return '"' + addSlashes(v, false) + '"';
+ }
+ else if (type === "object" && '_' in v && probablyPublic(v))
+ {
+ var output = [];
+ for (var k in v._)
+ {
+ for (var i = v._[k].length; i--; )
+ {
+ output.push(k + " = " + toString(v._[k][i]));
+ }
+ }
+ for (var k in v)
+ {
+ if (k === '_') continue;
+ output.push(k + " = " + toString(v[k]));
+ }
+ if (output.length === 0)
+ {
+ return "{}";
+ }
+ return "{ " + output.join(", ") + " }";
+ }
+ else if (type === "object" && 'ctor' in v)
+ {
+ if (v.ctor.substring(0,6) === "_Tuple")
+ {
+ var output = [];
+ for (var k in v)
+ {
+ if (k === 'ctor') continue;
+ output.push(toString(v[k]));
+ }
+ return "(" + output.join(",") + ")";
+ }
+ else if (v.ctor === "_Array")
+ {
+ if (!_Array)
+ {
+ _Array = Elm.Array.make(localRuntime);
+ }
+ var list = _Array.toList(v);
+ return "Array.fromList " + toString(list);
+ }
+ else if (v.ctor === "::")
+ {
+ var output = '[' + toString(v._0);
+ v = v._1;
+ while (v.ctor === "::")
+ {
+ output += "," + toString(v._0);
+ v = v._1;
+ }
+ return output + ']';
+ }
+ else if (v.ctor === "[]")
+ {
+ return "[]";
+ }
+ else if (v.ctor === "RBNode" || v.ctor === "RBEmpty")
+ {
+ if (!Dict)
+ {
+ Dict = Elm.Dict.make(localRuntime);
+ }
+ if (!List)
+ {
+ List = Elm.List.make(localRuntime);
+ }
+ var list = Dict.toList(v);
+ var name = "Dict";
+ if (list.ctor === "::" && list._0._1.ctor === "_Tuple0")
+ {
+ name = "Set";
+ list = A2(List.map, function(x){return x._0}, list);
+ }
+ return name + ".fromList " + toString(list);
+ }
+ else if (v.ctor.slice(0,5) === "Text:")
+ {
+ return '<text>'
+ }
+ else
+ {
+ var output = "";
+ for (var i in v)
+ {
+ if (i === 'ctor') continue;
+ var str = toString(v[i]);
+ var parenless = str[0] === '{' || str[0] === '<' || str.indexOf(' ') < 0;
+ output += ' ' + (parenless ? str : '(' + str + ')');
+ }
+ return v.ctor + output;
+ }
+ }
+ if (type === 'object' && 'notify' in v && 'id' in v)
+ {
+ return '<Signal>';
+ }
+ return "<internal structure>";
+ };
+
+ function addSlashes(str, isChar)
+ {
+ var s = str.replace(/\\/g, '\\\\')
+ .replace(/\n/g, '\\n')
+ .replace(/\t/g, '\\t')
+ .replace(/\r/g, '\\r')
+ .replace(/\v/g, '\\v')
+ .replace(/\0/g, '\\0');
+ if (isChar)
+ {
+ return s.replace(/\'/g, "\\'")
+ }
+ else
+ {
+ return s.replace(/\"/g, '\\"');
+ }
+ }
+
+ function probablyPublic(v)
+ {
+ var keys = Object.keys(v);
+ var len = keys.length;
+ if (len === 3
+ && 'props' in v
+ && 'element' in v)
+ {
+ return false;
+ }
+ else if (len === 5
+ && 'horizontal' in v
+ && 'vertical' in v
+ && 'x' in v
+ && 'y' in v)
+ {
+ return false;
+ }
+ else if (len === 7
+ && 'theta' in v
+ && 'scale' in v
+ && 'x' in v
+ && 'y' in v
+ && 'alpha' in v
+ && 'form' in v)
+ {
+ return false;
+ }
+ return true;
+ }
+
+ return localRuntime.Native.Show.values = {
+ toString: toString
+ };
+};
+
+Elm.Native.Signal = {};
+Elm.Native.Signal.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Signal = localRuntime.Native.Signal || {};
+ if (localRuntime.Native.Signal.values)
+ {
+ return localRuntime.Native.Signal.values;
+ }
+
+
+ var Task = Elm.Native.Task.make(localRuntime);
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+
+ function broadcastToKids(node, timestamp, update)
+ {
+ var kids = node.kids;
+ for (var i = kids.length; i--; )
+ {
+ kids[i].notify(timestamp, update, node.id);
+ }
+ }
+
+
+ // INPUT
+
+ function input(name, base)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'input-' + name,
+ value: base,
+ parents: [],
+ kids: []
+ };
+
+ node.notify = function(timestamp, targetId, value) {
+ var update = targetId === node.id;
+ if (update)
+ {
+ node.value = value;
+ }
+ broadcastToKids(node, timestamp, update);
+ return update;
+ };
+
+ localRuntime.inputs.push(node);
+
+ return node;
+ }
+
+ function constant(value)
+ {
+ return input('constant', value);
+ }
+
+
+ // MAILBOX
+
+ function mailbox(base)
+ {
+ var signal = input('mailbox', base);
+
+ function send(value) {
+ return Task.asyncFunction(function(callback) {
+ localRuntime.setTimeout(function() {
+ localRuntime.notify(signal.id, value);
+ }, 0);
+ callback(Task.succeed(Utils.Tuple0));
+ });
+ }
+
+ return {
+ _: {},
+ signal: signal,
+ address: {
+ ctor: 'Address',
+ _0: send
+ }
+ };
+ }
+
+ function sendMessage(message)
+ {
+ Task.perform(message._0);
+ }
+
+
+ // OUTPUT
+
+ function output(name, handler, parent)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'output-' + name,
+ parents: [parent],
+ isOutput: true
+ };
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ if (parentUpdate)
+ {
+ handler(parent.value);
+ }
+ };
+
+ parent.kids.push(node);
+
+ return node;
+ }
+
+
+ // MAP
+
+ function mapMany(refreshValue, args)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'map' + args.length,
+ value: refreshValue(),
+ parents: args,
+ kids: []
+ };
+
+ var numberOfParents = args.length;
+ var count = 0;
+ var update = false;
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ ++count;
+
+ update = update || parentUpdate;
+
+ if (count === numberOfParents)
+ {
+ if (update)
+ {
+ node.value = refreshValue();
+ }
+ broadcastToKids(node, timestamp, update);
+ update = false;
+ count = 0;
+ }
+ };
+
+ for (var i = numberOfParents; i--; )
+ {
+ args[i].kids.push(node);
+ }
+
+ return node;
+ }
+
+
+ function map(func, a)
+ {
+ function refreshValue()
+ {
+ return func(a.value);
+ }
+ return mapMany(refreshValue, [a]);
+ }
+
+
+ function map2(func, a, b)
+ {
+ function refreshValue()
+ {
+ return A2( func, a.value, b.value );
+ }
+ return mapMany(refreshValue, [a,b]);
+ }
+
+
+ function map3(func, a, b, c)
+ {
+ function refreshValue()
+ {
+ return A3( func, a.value, b.value, c.value );
+ }
+ return mapMany(refreshValue, [a,b,c]);
+ }
+
+
+ function map4(func, a, b, c, d)
+ {
+ function refreshValue()
+ {
+ return A4( func, a.value, b.value, c.value, d.value );
+ }
+ return mapMany(refreshValue, [a,b,c,d]);
+ }
+
+
+ function map5(func, a, b, c, d, e)
+ {
+ function refreshValue()
+ {
+ return A5( func, a.value, b.value, c.value, d.value, e.value );
+ }
+ return mapMany(refreshValue, [a,b,c,d,e]);
+ }
+
+
+
+ // FOLD
+
+ function foldp(update, state, signal)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'foldp',
+ parents: [signal],
+ kids: [],
+ value: state
+ };
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ if (parentUpdate)
+ {
+ node.value = A2( update, signal.value, node.value );
+ }
+ broadcastToKids(node, timestamp, parentUpdate);
+ };
+
+ signal.kids.push(node);
+
+ return node;
+ }
+
+
+ // TIME
+
+ function timestamp(signal)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'timestamp',
+ value: Utils.Tuple2(localRuntime.timer.programStart, signal.value),
+ parents: [signal],
+ kids: []
+ };
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ if (parentUpdate)
+ {
+ node.value = Utils.Tuple2(timestamp, signal.value);
+ }
+ broadcastToKids(node, timestamp, parentUpdate);
+ };
+
+ signal.kids.push(node);
+
+ return node;
+ }
+
+
+ function delay(time, signal)
+ {
+ var delayed = input('delay-input-' + time, signal.value);
+
+ function handler(value)
+ {
+ setTimeout(function() {
+ localRuntime.notify(delayed.id, value);
+ }, time);
+ }
+
+ output('delay-output-' + time, handler, signal);
+
+ return delayed;
+ }
+
+
+ // MERGING
+
+ function genericMerge(tieBreaker, leftStream, rightStream)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'merge',
+ value: A2(tieBreaker, leftStream.value, rightStream.value),
+ parents: [leftStream, rightStream],
+ kids: []
+ };
+
+ var left = { touched: false, update: false, value: null };
+ var right = { touched: false, update: false, value: null };
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ if (parentID === leftStream.id)
+ {
+ left.touched = true;
+ left.update = parentUpdate;
+ left.value = leftStream.value;
+ }
+ if (parentID === rightStream.id)
+ {
+ right.touched = true;
+ right.update = parentUpdate;
+ right.value = rightStream.value;
+ }
+
+ if (left.touched && right.touched)
+ {
+ var update = false;
+ if (left.update && right.update)
+ {
+ node.value = A2(tieBreaker, left.value, right.value);
+ update = true;
+ }
+ else if (left.update)
+ {
+ node.value = left.value;
+ update = true;
+ }
+ else if (right.update)
+ {
+ node.value = right.value;
+ update = true;
+ }
+ left.touched = false;
+ right.touched = false;
+
+ broadcastToKids(node, timestamp, update);
+ }
+ };
+
+ leftStream.kids.push(node);
+ rightStream.kids.push(node);
+
+ return node;
+ }
+
+
+ // FILTERING
+
+ function filterMap(toMaybe, base, signal)
+ {
+ var maybe = toMaybe(signal.value);
+ var node = {
+ id: Utils.guid(),
+ name: 'filterMap',
+ value: maybe.ctor === 'Nothing' ? base : maybe._0,
+ parents: [signal],
+ kids: []
+ };
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ var update = false;
+ if (parentUpdate)
+ {
+ var maybe = toMaybe(signal.value);
+ if (maybe.ctor === 'Just')
+ {
+ update = true;
+ node.value = maybe._0;
+ }
+ }
+ broadcastToKids(node, timestamp, update);
+ };
+
+ signal.kids.push(node);
+
+ return node;
+ }
+
+
+ // SAMPLING
+
+ function sampleOn(ticker, signal)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'sampleOn',
+ value: signal.value,
+ parents: [ticker, signal],
+ kids: []
+ };
+
+ var signalTouch = false;
+ var tickerTouch = false;
+ var tickerUpdate = false;
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ if (parentID === ticker.id)
+ {
+ tickerTouch = true;
+ tickerUpdate = parentUpdate;
+ }
+ if (parentID === signal.id)
+ {
+ signalTouch = true;
+ }
+
+ if (tickerTouch && signalTouch)
+ {
+ if (tickerUpdate)
+ {
+ node.value = signal.value;
+ }
+ tickerTouch = false;
+ signalTouch = false;
+
+ broadcastToKids(node, timestamp, tickerUpdate);
+ }
+ };
+
+ ticker.kids.push(node);
+ signal.kids.push(node);
+
+ return node;
+ }
+
+
+ // DROP REPEATS
+
+ function dropRepeats(signal)
+ {
+ var node = {
+ id: Utils.guid(),
+ name: 'dropRepeats',
+ value: signal.value,
+ parents: [signal],
+ kids: []
+ };
+
+ node.notify = function(timestamp, parentUpdate, parentID)
+ {
+ var update = false;
+ if (parentUpdate && !Utils.eq(node.value, signal.value))
+ {
+ node.value = signal.value;
+ update = true;
+ }
+ broadcastToKids(node, timestamp, update);
+ };
+
+ signal.kids.push(node);
+
+ return node;
+ }
+
+
+ return localRuntime.Native.Signal.values = {
+ input: input,
+ constant: constant,
+ mailbox: mailbox,
+ sendMessage: sendMessage,
+ output: output,
+ map: F2(map),
+ map2: F3(map2),
+ map3: F4(map3),
+ map4: F5(map4),
+ map5: F6(map5),
+ foldp: F3(foldp),
+ genericMerge: F3(genericMerge),
+ filterMap: F3(filterMap),
+ sampleOn: F2(sampleOn),
+ dropRepeats: dropRepeats,
+ timestamp: timestamp,
+ delay: F2(delay)
+ };
+};
+
+Elm.Native.String = {};
+Elm.Native.String.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.String = localRuntime.Native.String || {};
+ if (localRuntime.Native.String.values)
+ {
+ return localRuntime.Native.String.values;
+ }
+ if ('values' in Elm.Native.String)
+ {
+ return localRuntime.Native.String.values = Elm.Native.String.values;
+ }
+
+
+ var Char = Elm.Char.make(localRuntime);
+ var List = Elm.Native.List.make(localRuntime);
+ var Maybe = Elm.Maybe.make(localRuntime);
+ var Result = Elm.Result.make(localRuntime);
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+ function isEmpty(str)
+ {
+ return str.length === 0;
+ }
+ function cons(chr,str)
+ {
+ return chr + str;
+ }
+ function uncons(str)
+ {
+ var hd;
+ return (hd = str[0])
+ ? Maybe.Just(Utils.Tuple2(Utils.chr(hd), str.slice(1)))
+ : Maybe.Nothing;
+ }
+ function append(a,b)
+ {
+ return a + b;
+ }
+ function concat(strs)
+ {
+ return List.toArray(strs).join('');
+ }
+ function length(str)
+ {
+ return str.length;
+ }
+ function map(f,str)
+ {
+ var out = str.split('');
+ for (var i = out.length; i--; )
+ {
+ out[i] = f(Utils.chr(out[i]));
+ }
+ return out.join('');
+ }
+ function filter(pred,str)
+ {
+ return str.split('').map(Utils.chr).filter(pred).join('');
+ }
+ function reverse(str)
+ {
+ return str.split('').reverse().join('');
+ }
+ function foldl(f,b,str)
+ {
+ var len = str.length;
+ for (var i = 0; i < len; ++i)
+ {
+ b = A2(f, Utils.chr(str[i]), b);
+ }
+ return b;
+ }
+ function foldr(f,b,str)
+ {
+ for (var i = str.length; i--; )
+ {
+ b = A2(f, Utils.chr(str[i]), b);
+ }
+ return b;
+ }
+
+ function split(sep, str)
+ {
+ return List.fromArray(str.split(sep));
+ }
+ function join(sep, strs)
+ {
+ return List.toArray(strs).join(sep);
+ }
+ function repeat(n, str)
+ {
+ var result = '';
+ while (n > 0)
+ {
+ if (n & 1)
+ {
+ result += str;
+ }
+ n >>= 1, str += str;
+ }
+ return result;
+ }
+
+ function slice(start, end, str)
+ {
+ return str.slice(start,end);
+ }
+ function left(n, str)
+ {
+ return n < 1 ? "" : str.slice(0,n);
+ }
+ function right(n, str)
+ {
+ return n < 1 ? "" : str.slice(-n);
+ }
+ function dropLeft(n, str)
+ {
+ return n < 1 ? str : str.slice(n);
+ }
+ function dropRight(n, str)
+ {
+ return n < 1 ? str : str.slice(0,-n);
+ }
+
+ function pad(n,chr,str)
+ {
+ var half = (n - str.length) / 2;
+ return repeat(Math.ceil(half),chr) + str + repeat(half|0,chr);
+ }
+ function padRight(n,chr,str)
+ {
+ return str + repeat(n - str.length, chr);
+ }
+ function padLeft(n,chr,str)
+ {
+ return repeat(n - str.length, chr) + str;
+ }
+
+ function trim(str)
+ {
+ return str.trim();
+ }
+ function trimLeft(str)
+ {
+ return str.trimLeft();
+ }
+ function trimRight(str)
+ {
+ return str.trimRight();
+ }
+
+ function words(str)
+ {
+ return List.fromArray(str.trim().split(/\s+/g));
+ }
+ function lines(str)
+ {
+ return List.fromArray(str.split(/\r\n|\r|\n/g));
+ }
+
+ function toUpper(str)
+ {
+ return str.toUpperCase();
+ }
+ function toLower(str)
+ {
+ return str.toLowerCase();
+ }
+
+ function any(pred, str)
+ {
+ for (var i = str.length; i--; )
+ {
+ if (pred(Utils.chr(str[i])))
+ {
+ return true;
+ }
+ }
+ return false;
+ }
+ function all(pred, str)
+ {
+ for (var i = str.length; i--; )
+ {
+ if (!pred(Utils.chr(str[i])))
+ {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ function contains(sub, str)
+ {
+ return str.indexOf(sub) > -1;
+ }
+ function startsWith(sub, str)
+ {
+ return str.indexOf(sub) === 0;
+ }
+ function endsWith(sub, str)
+ {
+ return str.length >= sub.length &&
+ str.lastIndexOf(sub) === str.length - sub.length;
+ }
+ function indexes(sub, str)
+ {
+ var subLen = sub.length;
+ var i = 0;
+ var is = [];
+ while ((i = str.indexOf(sub, i)) > -1)
+ {
+ is.push(i);
+ i = i + subLen;
+ }
+ return List.fromArray(is);
+ }
+
+ function toInt(s)
+ {
+ var len = s.length;
+ if (len === 0)
+ {
+ return Result.Err("could not convert string '" + s + "' to an Int" );
+ }
+ var start = 0;
+ if (s[0] == '-')
+ {
+ if (len === 1)
+ {
+ return Result.Err("could not convert string '" + s + "' to an Int" );
+ }
+ start = 1;
+ }
+ for (var i = start; i < len; ++i)
+ {
+ if (!Char.isDigit(s[i]))
+ {
+ return Result.Err("could not convert string '" + s + "' to an Int" );
+ }
+ }
+ return Result.Ok(parseInt(s, 10));
+ }
+
+ function toFloat(s)
+ {
+ var len = s.length;
+ if (len === 0)
+ {
+ return Result.Err("could not convert string '" + s + "' to a Float" );
+ }
+ var start = 0;
+ if (s[0] == '-')
+ {
+ if (len === 1)
+ {
+ return Result.Err("could not convert string '" + s + "' to a Float" );
+ }
+ start = 1;
+ }
+ var dotCount = 0;
+ for (var i = start; i < len; ++i)
+ {
+ if (Char.isDigit(s[i]))
+ {
+ continue;
+ }
+ if (s[i] === '.')
+ {
+ dotCount += 1;
+ if (dotCount <= 1)
+ {
+ continue;
+ }
+ }
+ return Result.Err("could not convert string '" + s + "' to a Float" );
+ }
+ return Result.Ok(parseFloat(s));
+ }
+
+ function toList(str)
+ {
+ return List.fromArray(str.split('').map(Utils.chr));
+ }
+ function fromList(chars)
+ {
+ return List.toArray(chars).join('');
+ }
+
+ return Elm.Native.String.values = {
+ isEmpty: isEmpty,
+ cons: F2(cons),
+ uncons: uncons,
+ append: F2(append),
+ concat: concat,
+ length: length,
+ map: F2(map),
+ filter: F2(filter),
+ reverse: reverse,
+ foldl: F3(foldl),
+ foldr: F3(foldr),
+
+ split: F2(split),
+ join: F2(join),
+ repeat: F2(repeat),
+
+ slice: F3(slice),
+ left: F2(left),
+ right: F2(right),
+ dropLeft: F2(dropLeft),
+ dropRight: F2(dropRight),
+
+ pad: F3(pad),
+ padLeft: F3(padLeft),
+ padRight: F3(padRight),
+
+ trim: trim,
+ trimLeft: trimLeft,
+ trimRight: trimRight,
+
+ words: words,
+ lines: lines,
+
+ toUpper: toUpper,
+ toLower: toLower,
+
+ any: F2(any),
+ all: F2(all),
+
+ contains: F2(contains),
+ startsWith: F2(startsWith),
+ endsWith: F2(endsWith),
+ indexes: F2(indexes),
+
+ toInt: toInt,
+ toFloat: toFloat,
+ toList: toList,
+ fromList: fromList
+ };
+};
+
+Elm.Native.Task = {};
+Elm.Native.Task.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Task = localRuntime.Native.Task || {};
+ if (localRuntime.Native.Task.values)
+ {
+ return localRuntime.Native.Task.values;
+ }
+
+ var Result = Elm.Result.make(localRuntime);
+ var Signal;
+ var Utils = Elm.Native.Utils.make(localRuntime);
+
+
+ // CONSTRUCTORS
+
+ function succeed(value)
+ {
+ return {
+ tag: 'Succeed',
+ value: value
+ };
+ }
+
+ function fail(error)
+ {
+ return {
+ tag: 'Fail',
+ value: error
+ };
+ }
+
+ function asyncFunction(func)
+ {
+ return {
+ tag: 'Async',
+ asyncFunction: func
+ };
+ }
+
+ function andThen(task, callback)
+ {
+ return {
+ tag: 'AndThen',
+ task: task,
+ callback: callback
+ };
+ }
+
+ function catch_(task, callback)
+ {
+ return {
+ tag: 'Catch',
+ task: task,
+ callback: callback
+ };
+ }
+
+
+ // RUNNER
+
+ function perform(task) {
+ runTask({ task: task }, function() {});
+ }
+
+ function performSignal(name, signal)
+ {
+ var workQueue = [];
+
+ function onComplete()
+ {
+ workQueue.shift();
+
+ setTimeout(function() {
+ if (workQueue.length > 0)
+ {
+ runTask(workQueue[0], onComplete);
+ }
+ }, 0);
+ }
+
+ function register(task)
+ {
+ var root = { task: task };
+ workQueue.push(root);
+ if (workQueue.length === 1)
+ {
+ runTask(root, onComplete);
+ }
+ }
+
+ if (!Signal)
+ {
+ Signal = Elm.Native.Signal.make(localRuntime);
+ }
+ Signal.output('perform-tasks-' + name, register, signal);
+
+ register(signal.value);
+
+ return signal;
+ }
+
+ function mark(status, task)
+ {
+ return { status: status, task: task };
+ }
+
+ function runTask(root, onComplete)
+ {
+ var result = mark('runnable', root.task);
+ while (result.status === 'runnable')
+ {
+ result = stepTask(onComplete, root, result.task);
+ }
+
+ if (result.status === 'done')
+ {
+ root.task = result.task;
+ onComplete();
+ }
+
+ if (result.status === 'blocked')
+ {
+ root.task = result.task;
+ }
+ }
+
+ function stepTask(onComplete, root, task)
+ {
+ var tag = task.tag;
+
+ if (tag === 'Succeed' || tag === 'Fail')
+ {
+ return mark('done', task);
+ }
+
+ if (tag === 'Async')
+ {
+ var placeHolder = {};
+ var couldBeSync = true;
+ var wasSync = false;
+
+ task.asyncFunction(function(result) {
+ placeHolder.tag = result.tag;
+ placeHolder.value = result.value;
+ if (couldBeSync)
+ {
+ wasSync = true;
+ }
+ else
+ {
+ runTask(root, onComplete);
+ }
+ });
+ couldBeSync = false;
+ return mark(wasSync ? 'done' : 'blocked', placeHolder);
+ }
+
+ if (tag === 'AndThen' || tag === 'Catch')
+ {
+ var result = mark('runnable', task.task);
+ while (result.status === 'runnable')
+ {
+ result = stepTask(onComplete, root, result.task);
+ }
+
+ if (result.status === 'done')
+ {
+ var activeTask = result.task;
+ var activeTag = activeTask.tag;
+
+ var succeedChain = activeTag === 'Succeed' && tag === 'AndThen';
+ var failChain = activeTag === 'Fail' && tag === 'Catch';
+
+ return (succeedChain || failChain)
+ ? mark('runnable', task.callback(activeTask.value))
+ : mark('runnable', activeTask);
+ }
+ if (result.status === 'blocked')
+ {
+ return mark('blocked', {
+ tag: tag,
+ task: result.task,
+ callback: task.callback
+ });
+ }
+ }
+ }
+
+
+ // THREADS
+
+ function sleep(time) {
+ return asyncFunction(function(callback) {
+ setTimeout(function() {
+ callback(succeed(Utils.Tuple0));
+ }, time);
+ });
+ }
+
+ function spawn(task) {
+ return asyncFunction(function(callback) {
+ var id = setTimeout(function() {
+ perform(task);
+ }, 0);
+ callback(succeed(id));
+ });
+ }
+
+
+ return localRuntime.Native.Task.values = {
+ succeed: succeed,
+ fail: fail,
+ asyncFunction: asyncFunction,
+ andThen: F2(andThen),
+ catch_: F2(catch_),
+ perform: perform,
+ performSignal: performSignal,
+ spawn: spawn,
+ sleep: sleep
+ };
+};
+
+Elm.Native.Text = {};
+Elm.Native.Text.make = function(localRuntime) {
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Text = localRuntime.Native.Text || {};
+ if (localRuntime.Native.Text.values)
+ {
+ return localRuntime.Native.Text.values;
+ }
+
+ var toCss = Elm.Native.Color.make(localRuntime).toCss;
+ var List = Elm.Native.List.make(localRuntime);
+
+
+ // CONSTRUCTORS
+
+ function fromString(str)
+ {
+ return {
+ ctor: 'Text:Text',
+ _0: str
+ };
+ }
+
+ function append(a, b)
+ {
+ return {
+ ctor: 'Text:Append',
+ _0: a,
+ _1: b
+ };
+ }
+
+ function addMeta(field, value, text)
+ {
+ var newProps = {};
+ var newText = {
+ ctor: 'Text:Meta',
+ _0: newProps,
+ _1: text
+ };
+
+ if (text.ctor === 'Text:Meta')
+ {
+ newText._1 = text._1;
+ var props = text._0;
+ for (var i = metaKeys.length; i--; )
+ {
+ var key = metaKeys[i];
+ var val = props[key];
+ if (val)
+ {
+ newProps[key] = val;
+ }
+ }
+ }
+ newProps[field] = value;
+ return newText;
+ }
+
+ var metaKeys = [
+ 'font-size',
+ 'font-family',
+ 'font-style',
+ 'font-weight',
+ 'href',
+ 'text-decoration',
+ 'color'
+ ];
+
+
+ // conversions from Elm values to CSS
+
+ function toTypefaces(list)
+ {
+ var typefaces = List.toArray(list);
+ for (var i = typefaces.length; i--; )
+ {
+ var typeface = typefaces[i];
+ if (typeface.indexOf(' ') > -1)
+ {
+ typefaces[i] = "'" + typeface + "'";
+ }
+ }
+ return typefaces.join(',');
+ }
+
+ function toLine(line)
+ {
+ var ctor = line.ctor;
+ return ctor === 'Under'
+ ? 'underline'
+ : ctor === 'Over'
+ ? 'overline'
+ : 'line-through';
+ }
+
+ // setting styles of Text
+
+ function style(style, text)
+ {
+ var newText = addMeta('color', toCss(style.color), text);
+ var props = newText._0;
+
+ if (style.typeface.ctor !== '[]')
+ {
+ props['font-family'] = toTypefaces(style.typeface);
+ }
+ if (style.height.ctor !== "Nothing")
+ {
+ props['font-size'] = style.height._0 + 'px';
+ }
+ if (style.bold)
+ {
+ props['font-weight'] = 'bold';
+ }
+ if (style.italic)
+ {
+ props['font-style'] = 'italic';
+ }
+ if (style.line.ctor !== 'Nothing')
+ {
+ props['text-decoration'] = toLine(style.line._0);
+ }
+ return newText;
+ }
+
+ function height(px, text)
+ {
+ return addMeta('font-size', px + 'px', text);
+ }
+
+ function typeface(names, text)
+ {
+ return addMeta('font-family', toTypefaces(names), text);
+ }
+
+ function monospace(text)
+ {
+ return addMeta('font-family', 'monospace', text);
+ }
+
+ function italic(text)
+ {
+ return addMeta('font-style', 'italic', text);
+ }
+
+ function bold(text)
+ {
+ return addMeta('font-weight', 'bold', text);
+ }
+
+ function link(href, text)
+ {
+ return addMeta('href', href, text);
+ }
+
+ function line(line, text)
+ {
+ return addMeta('text-decoration', toLine(line), text);
+ }
+
+ function color(color, text)
+ {
+ return addMeta('color', toCss(color), text);;
+ }
+
+
+ // RENDER
+
+ function renderHtml(text)
+ {
+ var tag = text.ctor;
+ if (tag === 'Text:Append')
+ {
+ return renderHtml(text._0) + renderHtml(text._1);
+ }
+ if (tag === 'Text:Text')
+ {
+ return properEscape(text._0);
+ }
+ if (tag === 'Text:Meta')
+ {
+ return renderMeta(text._0, renderHtml(text._1));
+ }
+ }
+
+ function renderMeta(metas, string)
+ {
+ var href = metas['href'];
+ if (href)
+ {
+ string = '<a href="' + href + '">' + string + '</a>';
+ }
+ var styles = '';
+ for (var key in metas)
+ {
+ if (key === 'href')
+ {
+ continue;
+ }
+ styles += key + ':' + metas[key] + ';';
+ }
+ if (styles)
+ {
+ string = '<span style="' + styles + '">' + string + '</span>';
+ }
+ return string;
+ }
+
+ function properEscape(str)
+ {
+ if (str.length == 0)
+ {
+ return str;
+ }
+ str = str //.replace(/&/g, "&#38;")
+ .replace(/"/g, '&#34;')
+ .replace(/'/g, "&#39;")
+ .replace(/</g, "&#60;")
+ .replace(/>/g, "&#62;");
+ var arr = str.split('\n');
+ for (var i = arr.length; i--; )
+ {
+ arr[i] = makeSpaces(arr[i]);
+ }
+ return arr.join('<br/>');
+ }
+
+ function makeSpaces(s)
+ {
+ if (s.length == 0)
+ {
+ return s;
+ }
+ var arr = s.split('');
+ if (arr[0] == ' ')
+ {
+ arr[0] = "&nbsp;"
+ }
+ for (var i = arr.length; --i; )
+ {
+ if (arr[i][0] == ' ' && arr[i-1] == ' ')
+ {
+ arr[i-1] = arr[i-1] + arr[i];
+ arr[i] = '';
+ }
+ }
+ for (var i = arr.length; i--; )
+ {
+ if (arr[i].length > 1 && arr[i][0] == ' ')
+ {
+ var spaces = arr[i].split('');
+ for (var j = spaces.length - 2; j >= 0; j -= 2)
+ {
+ spaces[j] = '&nbsp;';
+ }
+ arr[i] = spaces.join('');
+ }
+ }
+ arr = arr.join('');
+ if (arr[arr.length-1] === " ")
+ {
+ return arr.slice(0,-1) + '&nbsp;';
+ }
+ return arr;
+ }
+
+
+ return localRuntime.Native.Text.values = {
+ fromString: fromString,
+ append: F2(append),
+
+ height: F2(height),
+ italic: italic,
+ bold: bold,
+ line: F2(line),
+ monospace: monospace,
+ typeface: F2(typeface),
+ color: F2(color),
+ link: F2(link),
+ style: F2(style),
+
+ toTypefaces: toTypefaces,
+ toLine: toLine,
+ renderHtml: renderHtml
+ };
+};
+
+Elm.Native.Time = {};
+Elm.Native.Time.make = function(localRuntime)
+{
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Time = localRuntime.Native.Time || {};
+ if (localRuntime.Native.Time.values)
+ {
+ return localRuntime.Native.Time.values;
+ }
+
+ var NS = Elm.Native.Signal.make(localRuntime);
+ var Maybe = Elm.Maybe.make(localRuntime);
+
+
+ // FRAMES PER SECOND
+
+ function fpsWhen(desiredFPS, isOn)
+ {
+ var msPerFrame = 1000 / desiredFPS;
+ var ticker = NS.input('fps-' + desiredFPS, null);
+
+ function notifyTicker()
+ {
+ localRuntime.notify(ticker.id, null);
+ }
+
+ function firstArg(x, y)
+ {
+ return x;
+ }
+
+ // input fires either when isOn changes, or when ticker fires.
+ // Its value is a tuple with the current timestamp, and the state of isOn
+ var input = NS.timestamp(A3(NS.map2, F2(firstArg), NS.dropRepeats(isOn), ticker));
+
+ var initialState = {
+ isOn: false,
+ time: localRuntime.timer.programStart,
+ delta: 0
+ };
+
+ var timeoutId;
+
+ function update(input,state)
+ {
+ var currentTime = input._0;
+ var isOn = input._1;
+ var wasOn = state.isOn;
+ var previousTime = state.time;
+
+ if (isOn)
+ {
+ timeoutId = localRuntime.setTimeout(notifyTicker, msPerFrame);
+ }
+ else if (wasOn)
+ {
+ clearTimeout(timeoutId);
+ }
+
+ return {
+ isOn: isOn,
+ time: currentTime,
+ delta: (isOn && !wasOn) ? 0 : currentTime - previousTime
+ };
+ }
+
+ return A2(
+ NS.map,
+ function(state) { return state.delta; },
+ A3(NS.foldp, F2(update), update(input.value,initialState), input)
+ );
+ }
+
+
+ // EVERY
+
+ function every(t)
+ {
+ var ticker = NS.input('every-' + t, null);
+ function tellTime()
+ {
+ localRuntime.notify(ticker.id, null);
+ }
+ var clock = A2( NS.map, fst, NS.timestamp(ticker) );
+ setInterval(tellTime, t);
+ return clock;
+ }
+
+
+ function fst(pair)
+ {
+ return pair._0;
+ }
+
+
+ function read(s)
+ {
+ var t = Date.parse(s);
+ return isNaN(t) ? Maybe.Nothing : Maybe.Just(t);
+ }
+
+ return localRuntime.Native.Time.values = {
+ fpsWhen: F2(fpsWhen),
+ every: every,
+ toDate: function(t) { return new window.Date(t); },
+ read: read
+ };
+
+};
+
+Elm.Native.Transform2D = {};
+Elm.Native.Transform2D.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Transform2D = localRuntime.Native.Transform2D || {};
+ if (localRuntime.Native.Transform2D.values)
+ {
+ return localRuntime.Native.Transform2D.values;
+ }
+
+ var A;
+ if (typeof Float32Array === 'undefined')
+ {
+ A = function(arr)
+ {
+ this.length = arr.length;
+ this[0] = arr[0];
+ this[1] = arr[1];
+ this[2] = arr[2];
+ this[3] = arr[3];
+ this[4] = arr[4];
+ this[5] = arr[5];
+ };
+ }
+ else
+ {
+ A = Float32Array;
+ }
+
+ // layout of matrix in an array is
+ //
+ // | m11 m12 dx |
+ // | m21 m22 dy |
+ // | 0 0 1 |
+ //
+ // new A([ m11, m12, dx, m21, m22, dy ])
+
+ var identity = new A([1,0,0,0,1,0]);
+ function matrix(m11, m12, m21, m22, dx, dy)
+ {
+ return new A([m11, m12, dx, m21, m22, dy]);
+ }
+
+ function rotation(t)
+ {
+ var c = Math.cos(t);
+ var s = Math.sin(t);
+ return new A([c, -s, 0, s, c, 0]);
+ }
+
+ function rotate(t,m)
+ {
+ var c = Math.cos(t);
+ var s = Math.sin(t);
+ var m11 = m[0], m12 = m[1], m21 = m[3], m22 = m[4];
+ return new A([m11*c + m12*s, -m11*s + m12*c, m[2],
+ m21*c + m22*s, -m21*s + m22*c, m[5]]);
+ }
+ /*
+ function move(xy,m) {
+ var x = xy._0;
+ var y = xy._1;
+ var m11 = m[0], m12 = m[1], m21 = m[3], m22 = m[4];
+ return new A([m11, m12, m11*x + m12*y + m[2],
+ m21, m22, m21*x + m22*y + m[5]]);
+ }
+ function scale(s,m) { return new A([m[0]*s, m[1]*s, m[2], m[3]*s, m[4]*s, m[5]]); }
+ function scaleX(x,m) { return new A([m[0]*x, m[1], m[2], m[3]*x, m[4], m[5]]); }
+ function scaleY(y,m) { return new A([m[0], m[1]*y, m[2], m[3], m[4]*y, m[5]]); }
+ function reflectX(m) { return new A([-m[0], m[1], m[2], -m[3], m[4], m[5]]); }
+ function reflectY(m) { return new A([m[0], -m[1], m[2], m[3], -m[4], m[5]]); }
+
+ function transform(m11, m21, m12, m22, mdx, mdy, n) {
+ var n11 = n[0], n12 = n[1], n21 = n[3], n22 = n[4], ndx = n[2], ndy = n[5];
+ return new A([m11*n11 + m12*n21,
+ m11*n12 + m12*n22,
+ m11*ndx + m12*ndy + mdx,
+ m21*n11 + m22*n21,
+ m21*n12 + m22*n22,
+ m21*ndx + m22*ndy + mdy]);
+ }
+ */
+ function multiply(m, n)
+ {
+ var m11 = m[0], m12 = m[1], m21 = m[3], m22 = m[4], mdx = m[2], mdy = m[5];
+ var n11 = n[0], n12 = n[1], n21 = n[3], n22 = n[4], ndx = n[2], ndy = n[5];
+ return new A([m11*n11 + m12*n21,
+ m11*n12 + m12*n22,
+ m11*ndx + m12*ndy + mdx,
+ m21*n11 + m22*n21,
+ m21*n12 + m22*n22,
+ m21*ndx + m22*ndy + mdy]);
+ }
+
+ return localRuntime.Native.Transform2D.values = {
+ identity:identity,
+ matrix:F6(matrix),
+ rotation:rotation,
+ multiply:F2(multiply)
+ /*
+ transform:F7(transform),
+ rotate:F2(rotate),
+ move:F2(move),
+ scale:F2(scale),
+ scaleX:F2(scaleX),
+ scaleY:F2(scaleY),
+ reflectX:reflectX,
+ reflectY:reflectY
+ */
+ };
+
+};
+
+Elm.Native = Elm.Native || {};
+Elm.Native.Utils = {};
+Elm.Native.Utils.make = function(localRuntime) {
+
+ localRuntime.Native = localRuntime.Native || {};
+ localRuntime.Native.Utils = localRuntime.Native.Utils || {};
+ if (localRuntime.Native.Utils.values)
+ {
+ return localRuntime.Native.Utils.values;
+ }
+
+ function eq(l,r)
+ {
+ var stack = [{'x': l, 'y': r}]
+ while (stack.length > 0)
+ {
+ var front = stack.pop();
+ var x = front.x;
+ var y = front.y;
+ if (x === y)
+ {
+ continue;
+ }
+ if (typeof x === "object")
+ {
+ var c = 0;
+ for (var i in x)
+ {
+ ++c;
+ if (i in y)
+ {
+ if (i !== 'ctor')
+ {
+ stack.push({ 'x': x[i], 'y': y[i] });
+ }
+ }
+ else
+ {
+ return false;
+ }
+ }
+ if ('ctor' in x)
+ {
+ stack.push({'x': x.ctor, 'y': y.ctor});
+ }
+ if (c !== Object.keys(y).length)
+ {
+ return false;
+ }
+ }
+ else if (typeof x === 'function')
+ {
+ throw new Error('Equality error: general function equality is ' +
+ 'undecidable, and therefore, unsupported');
+ }
+ else
+ {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ // code in Generate/JavaScript.hs depends on the particular
+ // integer values assigned to LT, EQ, and GT
+ var LT = -1, EQ = 0, GT = 1, ord = ['LT','EQ','GT'];
+
+ function compare(x,y)
+ {
+ return {
+ ctor: ord[cmp(x,y)+1]
+ };
+ }
+
+ function cmp(x,y) {
+ var ord;
+ if (typeof x !== 'object')
+ {
+ return x === y ? EQ : x < y ? LT : GT;
+ }
+ else if (x.isChar)
+ {
+ var a = x.toString();
+ var b = y.toString();
+ return a === b
+ ? EQ
+ : a < b
+ ? LT
+ : GT;
+ }
+ else if (x.ctor === "::" || x.ctor === "[]")
+ {
+ while (true)
+ {
+ if (x.ctor === "[]" && y.ctor === "[]")
+ {
+ return EQ;
+ }
+ if (x.ctor !== y.ctor)
+ {
+ return x.ctor === '[]' ? LT : GT;
+ }
+ ord = cmp(x._0, y._0);
+ if (ord !== EQ)
+ {
+ return ord;
+ }
+ x = x._1;
+ y = y._1;
+ }
+ }
+ else if (x.ctor.slice(0,6) === '_Tuple')
+ {
+ var n = x.ctor.slice(6) - 0;
+ var err = 'cannot compare tuples with more than 6 elements.';
+ if (n === 0) return EQ;
+ if (n >= 1) { ord = cmp(x._0, y._0); if (ord !== EQ) return ord;
+ if (n >= 2) { ord = cmp(x._1, y._1); if (ord !== EQ) return ord;
+ if (n >= 3) { ord = cmp(x._2, y._2); if (ord !== EQ) return ord;
+ if (n >= 4) { ord = cmp(x._3, y._3); if (ord !== EQ) return ord;
+ if (n >= 5) { ord = cmp(x._4, y._4); if (ord !== EQ) return ord;
+ if (n >= 6) { ord = cmp(x._5, y._5); if (ord !== EQ) return ord;
+ if (n >= 7) throw new Error('Comparison error: ' + err); } } } } } }
+ return EQ;
+ }
+ else
+ {
+ throw new Error('Comparison error: comparison is only defined on ints, ' +
+ 'floats, times, chars, strings, lists of comparable values, ' +
+ 'and tuples of comparable values.');
+ }
+ }
+
+
+ var Tuple0 = {
+ ctor: "_Tuple0"
+ };
+
+ function Tuple2(x,y)
+ {
+ return {
+ ctor: "_Tuple2",
+ _0: x,
+ _1: y
+ };
+ }
+
+ function chr(c)
+ {
+ var x = new String(c);
+ x.isChar = true;
+ return x;
+ }
+
+ function txt(str)
+ {
+ var t = new String(str);
+ t.text = true;
+ return t;
+ }
+
+ var count = 0;
+ function guid(_)
+ {
+ return count++
+ }
+
+ function copy(oldRecord)
+ {
+ var newRecord = {};
+ for (var key in oldRecord)
+ {
+ var value = key === '_'
+ ? copy(oldRecord._)
+ : oldRecord[key];
+ newRecord[key] = value;
+ }
+ return newRecord;
+ }
+
+ function remove(key, oldRecord)
+ {
+ var record = copy(oldRecord);
+ if (key in record._)
+ {
+ record[key] = record._[key][0];
+ record._[key] = record._[key].slice(1);
+ if (record._[key].length === 0)
+ {
+ delete record._[key];
+ }
+ }
+ else
+ {
+ delete record[key];
+ }
+ return record;
+ }
+
+ function replace(keyValuePairs, oldRecord)
+ {
+ var record = copy(oldRecord);
+ for (var i = keyValuePairs.length; i--; )
+ {
+ var pair = keyValuePairs[i];
+ record[pair[0]] = pair[1];
+ }
+ return record;
+ }
+
+ function insert(key, value, oldRecord)
+ {
+ var newRecord = copy(oldRecord);
+ if (key in newRecord)
+ {
+ var values = newRecord._[key];
+ var copiedValues = values ? values.slice(0) : [];
+ newRecord._[key] = [newRecord[key]].concat(copiedValues);
+ }
+ newRecord[key] = value;
+ return newRecord;
+ }
+
+ function getXY(e)
+ {
+ var posx = 0;
+ var posy = 0;
+ if (e.pageX || e.pageY)
+ {
+ posx = e.pageX;
+ posy = e.pageY;
+ }
+ else if (e.clientX || e.clientY)
+ {
+ posx = e.clientX + document.body.scrollLeft + document.documentElement.scrollLeft;
+ posy = e.clientY + document.body.scrollTop + document.documentElement.scrollTop;
+ }
+
+ if (localRuntime.isEmbed())
+ {
+ var rect = localRuntime.node.getBoundingClientRect();
+ var relx = rect.left + document.body.scrollLeft + document.documentElement.scrollLeft;
+ var rely = rect.top + document.body.scrollTop + document.documentElement.scrollTop;
+ // TODO: figure out if there is a way to avoid rounding here
+ posx = posx - Math.round(relx) - localRuntime.node.clientLeft;
+ posy = posy - Math.round(rely) - localRuntime.node.clientTop;
+ }
+ return Tuple2(posx, posy);
+ }
+
+
+ //// LIST STUFF ////
+
+ var Nil = { ctor:'[]' };
+
+ function Cons(hd,tl)
+ {
+ return {
+ ctor: "::",
+ _0: hd,
+ _1: tl
+ };
+ }
+
+ function append(xs,ys)
+ {
+ // append Strings
+ if (typeof xs === "string")
+ {
+ return xs + ys;
+ }
+
+ // append Text
+ if (xs.ctor.slice(0,5) === 'Text:')
+ {
+ return {
+ ctor: 'Text:Append',
+ _0: xs,
+ _1: ys
+ };
+ }
+
+
+
+ // append Lists
+ if (xs.ctor === '[]')
+ {
+ return ys;
+ }
+ var root = Cons(xs._0, Nil);
+ var curr = root;
+ xs = xs._1;
+ while (xs.ctor !== '[]')
+ {
+ curr._1 = Cons(xs._0, Nil);
+ xs = xs._1;
+ curr = curr._1;
+ }
+ curr._1 = ys;
+ return root;
+ }
+
+ //// RUNTIME ERRORS ////
+
+ function indent(lines)
+ {
+ return '\n' + lines.join('\n');
+ }
+
+ function badCase(moduleName, span)
+ {
+ var msg = indent([
+ 'Non-exhaustive pattern match in case-expression.',
+ 'Make sure your patterns cover every case!'
+ ]);
+ throw new Error('Runtime error in module ' + moduleName + ' (' + span + ')' + msg);
+ }
+
+ function badIf(moduleName, span)
+ {
+ var msg = indent([
+ 'Non-exhaustive pattern match in multi-way-if expression.',
+ 'It is best to use \'otherwise\' as the last branch of multi-way-if.'
+ ]);
+ throw new Error('Runtime error in module ' + moduleName + ' (' + span + ')' + msg);
+ }
+
+
+ function badPort(expected, received)
+ {
+ var msg = indent([
+ 'Expecting ' + expected + ' but was given ',
+ JSON.stringify(received)
+ ]);
+ throw new Error('Runtime error when sending values through a port.' + msg);
+ }
+
+
+ return localRuntime.Native.Utils.values = {
+ eq: eq,
+ cmp: cmp,
+ compare: F2(compare),
+ Tuple0: Tuple0,
+ Tuple2: Tuple2,
+ chr: chr,
+ txt: txt,
+ copy: copy,
+ remove: remove,
+ replace: replace,
+ insert: insert,
+ guid: guid,
+ getXY: getXY,
+
+ Nil: Nil,
+ Cons: Cons,
+ append: F2(append),
+
+ badCase: badCase,
+ badIf: badIf,
+ badPort: badPort
+ };
+};
+
+(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);throw new Error("Cannot find module '"+o+"'")}var f=n[o]={exports:{}};t[o][0].call(f.exports,function(e){var n=t[o][1][e];return s(n?n:e)},f,f.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){
+var createElement = require("./vdom/create-element.js")
+
+module.exports = createElement
+
+},{"./vdom/create-element.js":6}],2:[function(require,module,exports){
+(function (global){
+var topLevel = typeof global !== 'undefined' ? global :
+ typeof window !== 'undefined' ? window : {}
+var minDoc = require('min-document');
+
+if (typeof document !== 'undefined') {
+ module.exports = document;
+} else {
+ var doccy = topLevel['__GLOBAL_DOCUMENT_CACHE@4'];
+
+ if (!doccy) {
+ doccy = topLevel['__GLOBAL_DOCUMENT_CACHE@4'] = minDoc;
+ }
+
+ module.exports = doccy;
+}
+
+}).call(this,typeof self !== "undefined" ? self : typeof window !== "undefined" ? window : {})
+},{"min-document":24}],3:[function(require,module,exports){
+"use strict";
+
+module.exports = function isObject(x) {
+ return typeof x === "object" && x !== null;
+};
+
+},{}],4:[function(require,module,exports){
+var nativeIsArray = Array.isArray
+var toString = Object.prototype.toString
+
+module.exports = nativeIsArray || isArray
+
+function isArray(obj) {
+ return toString.call(obj) === "[object Array]"
+}
+
+},{}],5:[function(require,module,exports){
+var isObject = require("is-object")
+var isHook = require("../vnode/is-vhook.js")
+
+module.exports = applyProperties
+
+function applyProperties(node, props, previous) {
+ for (var propName in props) {
+ var propValue = props[propName]
+
+ if (propValue === undefined) {
+ removeProperty(node, propName, propValue, previous);
+ } else if (isHook(propValue)) {
+ removeProperty(node, propName, propValue, previous)
+ if (propValue.hook) {
+ propValue.hook(node,
+ propName,
+ previous ? previous[propName] : undefined)
+ }
+ } else {
+ if (isObject(propValue)) {
+ patchObject(node, props, previous, propName, propValue);
+ } else {
+ node[propName] = propValue
+ }
+ }
+ }
+}
+
+function removeProperty(node, propName, propValue, previous) {
+ if (previous) {
+ var previousValue = previous[propName]
+
+ if (!isHook(previousValue)) {
+ if (propName === "attributes") {
+ for (var attrName in previousValue) {
+ node.removeAttribute(attrName)
+ }
+ } else if (propName === "style") {
+ for (var i in previousValue) {
+ node.style[i] = ""
+ }
+ } else if (typeof previousValue === "string") {
+ node[propName] = ""
+ } else {
+ node[propName] = null
+ }
+ } else if (previousValue.unhook) {
+ previousValue.unhook(node, propName, propValue)
+ }
+ }
+}
+
+function patchObject(node, props, previous, propName, propValue) {
+ var previousValue = previous ? previous[propName] : undefined
+
+ // Set attributes
+ if (propName === "attributes") {
+ for (var attrName in propValue) {
+ var attrValue = propValue[attrName]
+
+ if (attrValue === undefined) {
+ node.removeAttribute(attrName)
+ } else {
+ node.setAttribute(attrName, attrValue)
+ }
+ }
+
+ return
+ }
+
+ if(previousValue && isObject(previousValue) &&
+ getPrototype(previousValue) !== getPrototype(propValue)) {
+ node[propName] = propValue
+ return
+ }
+
+ if (!isObject(node[propName])) {
+ node[propName] = {}
+ }
+
+ var replacer = propName === "style" ? "" : undefined
+
+ for (var k in propValue) {
+ var value = propValue[k]
+ node[propName][k] = (value === undefined) ? replacer : value
+ }
+}
+
+function getPrototype(value) {
+ if (Object.getPrototypeOf) {
+ return Object.getPrototypeOf(value)
+ } else if (value.__proto__) {
+ return value.__proto__
+ } else if (value.constructor) {
+ return value.constructor.prototype
+ }
+}
+
+},{"../vnode/is-vhook.js":13,"is-object":3}],6:[function(require,module,exports){
+var document = require("global/document")
+
+var applyProperties = require("./apply-properties")
+
+var isVNode = require("../vnode/is-vnode.js")
+var isVText = require("../vnode/is-vtext.js")
+var isWidget = require("../vnode/is-widget.js")
+var handleThunk = require("../vnode/handle-thunk.js")
+
+module.exports = createElement
+
+function createElement(vnode, opts) {
+ var doc = opts ? opts.document || document : document
+ var warn = opts ? opts.warn : null
+
+ vnode = handleThunk(vnode).a
+
+ if (isWidget(vnode)) {
+ return vnode.init()
+ } else if (isVText(vnode)) {
+ return doc.createTextNode(vnode.text)
+ } else if (!isVNode(vnode)) {
+ if (warn) {
+ warn("Item is not a valid virtual dom node", vnode)
+ }
+ return null
+ }
+
+ var node = (vnode.namespace === null) ?
+ doc.createElement(vnode.tagName) :
+ doc.createElementNS(vnode.namespace, vnode.tagName)
+
+ var props = vnode.properties
+ applyProperties(node, props)
+
+ var children = vnode.children
+
+ for (var i = 0; i < children.length; i++) {
+ var childNode = createElement(children[i], opts)
+ if (childNode) {
+ node.appendChild(childNode)
+ }
+ }
+
+ return node
+}
+
+},{"../vnode/handle-thunk.js":11,"../vnode/is-vnode.js":14,"../vnode/is-vtext.js":15,"../vnode/is-widget.js":16,"./apply-properties":5,"global/document":2}],7:[function(require,module,exports){
+// Maps a virtual DOM tree onto a real DOM tree in an efficient manner.
+// We don't want to read all of the DOM nodes in the tree so we use
+// the in-order tree indexing to eliminate recursion down certain branches.
+// We only recurse into a DOM node if we know that it contains a child of
+// interest.
+
+var noChild = {}
+
+module.exports = domIndex
+
+function domIndex(rootNode, tree, indices, nodes) {
+ if (!indices || indices.length === 0) {
+ return {}
+ } else {
+ indices.sort(ascending)
+ return recurse(rootNode, tree, indices, nodes, 0)
+ }
+}
+
+function recurse(rootNode, tree, indices, nodes, rootIndex) {
+ nodes = nodes || {}
+
+
+ if (rootNode) {
+ if (indexInRange(indices, rootIndex, rootIndex)) {
+ nodes[rootIndex] = rootNode
+ }
+
+ var vChildren = tree.children
+
+ if (vChildren) {
+
+ var childNodes = rootNode.childNodes
+
+ for (var i = 0; i < tree.children.length; i++) {
+ rootIndex += 1
+
+ var vChild = vChildren[i] || noChild
+ var nextIndex = rootIndex + (vChild.count || 0)
+
+ // skip recursion down the tree if there are no nodes down here
+ if (indexInRange(indices, rootIndex, nextIndex)) {
+ recurse(childNodes[i], vChild, indices, nodes, rootIndex)
+ }
+
+ rootIndex = nextIndex
+ }
+ }
+ }
+
+ return nodes
+}
+
+// Binary search for an index in the interval [left, right]
+function indexInRange(indices, left, right) {
+ if (indices.length === 0) {
+ return false
+ }
+
+ var minIndex = 0
+ var maxIndex = indices.length - 1
+ var currentIndex
+ var currentItem
+
+ while (minIndex <= maxIndex) {
+ currentIndex = ((maxIndex + minIndex) / 2) >> 0
+ currentItem = indices[currentIndex]
+
+ if (minIndex === maxIndex) {
+ return currentItem >= left && currentItem <= right
+ } else if (currentItem < left) {
+ minIndex = currentIndex + 1
+ } else if (currentItem > right) {
+ maxIndex = currentIndex - 1
+ } else {
+ return true
+ }
+ }
+
+ return false;
+}
+
+function ascending(a, b) {
+ return a > b ? 1 : -1
+}
+
+},{}],8:[function(require,module,exports){
+var applyProperties = require("./apply-properties")
+
+var isWidget = require("../vnode/is-widget.js")
+var VPatch = require("../vnode/vpatch.js")
+
+var render = require("./create-element")
+var updateWidget = require("./update-widget")
+
+module.exports = applyPatch
+
+function applyPatch(vpatch, domNode, renderOptions) {
+ var type = vpatch.type
+ var vNode = vpatch.vNode
+ var patch = vpatch.patch
+
+ switch (type) {
+ case VPatch.REMOVE:
+ return removeNode(domNode, vNode)
+ case VPatch.INSERT:
+ return insertNode(domNode, patch, renderOptions)
+ case VPatch.VTEXT:
+ return stringPatch(domNode, vNode, patch, renderOptions)
+ case VPatch.WIDGET:
+ return widgetPatch(domNode, vNode, patch, renderOptions)
+ case VPatch.VNODE:
+ return vNodePatch(domNode, vNode, patch, renderOptions)
+ case VPatch.ORDER:
+ reorderChildren(domNode, patch)
+ return domNode
+ case VPatch.PROPS:
+ applyProperties(domNode, patch, vNode.properties)
+ return domNode
+ case VPatch.THUNK:
+ return replaceRoot(domNode,
+ renderOptions.patch(domNode, patch, renderOptions))
+ default:
+ return domNode
+ }
+}
+
+function removeNode(domNode, vNode) {
+ var parentNode = domNode.parentNode
+
+ if (parentNode) {
+ parentNode.removeChild(domNode)
+ }
+
+ destroyWidget(domNode, vNode);
+
+ return null
+}
+
+function insertNode(parentNode, vNode, renderOptions) {
+ var newNode = render(vNode, renderOptions)
+
+ if (parentNode) {
+ parentNode.appendChild(newNode)
+ }
+
+ return parentNode
+}
+
+function stringPatch(domNode, leftVNode, vText, renderOptions) {
+ var newNode
+
+ if (domNode.nodeType === 3) {
+ domNode.replaceData(0, domNode.length, vText.text)
+ newNode = domNode
+ } else {
+ var parentNode = domNode.parentNode
+ newNode = render(vText, renderOptions)
+
+ if (parentNode && newNode !== domNode) {
+ parentNode.replaceChild(newNode, domNode)
+ }
+ }
+
+ return newNode
+}
+
+function widgetPatch(domNode, leftVNode, widget, renderOptions) {
+ var updating = updateWidget(leftVNode, widget)
+ var newNode
+
+ if (updating) {
+ newNode = widget.update(leftVNode, domNode) || domNode
+ } else {
+ newNode = render(widget, renderOptions)
+ }
+
+ var parentNode = domNode.parentNode
+
+ if (parentNode && newNode !== domNode) {
+ parentNode.replaceChild(newNode, domNode)
+ }
+
+ if (!updating) {
+ destroyWidget(domNode, leftVNode)
+ }
+
+ return newNode
+}
+
+function vNodePatch(domNode, leftVNode, vNode, renderOptions) {
+ var parentNode = domNode.parentNode
+ var newNode = render(vNode, renderOptions)
+
+ if (parentNode && newNode !== domNode) {
+ parentNode.replaceChild(newNode, domNode)
+ }
+
+ return newNode
+}
+
+function destroyWidget(domNode, w) {
+ if (typeof w.destroy === "function" && isWidget(w)) {
+ w.destroy(domNode)
+ }
+}
+
+function reorderChildren(domNode, moves) {
+ var childNodes = domNode.childNodes
+ var keyMap = {}
+ var node
+ var remove
+ var insert
+
+ for (var i = 0; i < moves.removes.length; i++) {
+ remove = moves.removes[i]
+ node = childNodes[remove.from]
+ if (remove.key) {
+ keyMap[remove.key] = node
+ }
+ domNode.removeChild(node)
+ }
+
+ var length = childNodes.length
+ for (var j = 0; j < moves.inserts.length; j++) {
+ insert = moves.inserts[j]
+ node = keyMap[insert.key]
+ // this is the weirdest bug i've ever seen in webkit
+ domNode.insertBefore(node, insert.to >= length++ ? null : childNodes[insert.to])
+ }
+}
+
+function replaceRoot(oldRoot, newRoot) {
+ if (oldRoot && newRoot && oldRoot !== newRoot && oldRoot.parentNode) {
+ oldRoot.parentNode.replaceChild(newRoot, oldRoot)
+ }
+
+ return newRoot;
+}
+
+},{"../vnode/is-widget.js":16,"../vnode/vpatch.js":19,"./apply-properties":5,"./create-element":6,"./update-widget":10}],9:[function(require,module,exports){
+var document = require("global/document")
+var isArray = require("x-is-array")
+
+var domIndex = require("./dom-index")
+var patchOp = require("./patch-op")
+module.exports = patch
+
+function patch(rootNode, patches) {
+ return patchRecursive(rootNode, patches)
+}
+
+function patchRecursive(rootNode, patches, renderOptions) {
+ var indices = patchIndices(patches)
+
+ if (indices.length === 0) {
+ return rootNode
+ }
+
+ var index = domIndex(rootNode, patches.a, indices)
+ var ownerDocument = rootNode.ownerDocument
+
+ if (!renderOptions) {
+ renderOptions = { patch: patchRecursive }
+ if (ownerDocument !== document) {
+ renderOptions.document = ownerDocument
+ }
+ }
+
+ for (var i = 0; i < indices.length; i++) {
+ var nodeIndex = indices[i]
+ rootNode = applyPatch(rootNode,
+ index[nodeIndex],
+ patches[nodeIndex],
+ renderOptions)
+ }
+
+ return rootNode
+}
+
+function applyPatch(rootNode, domNode, patchList, renderOptions) {
+ if (!domNode) {
+ return rootNode
+ }
+
+ var newNode
+
+ if (isArray(patchList)) {
+ for (var i = 0; i < patchList.length; i++) {
+ newNode = patchOp(patchList[i], domNode, renderOptions)
+
+ if (domNode === rootNode) {
+ rootNode = newNode
+ }
+ }
+ } else {
+ newNode = patchOp(patchList, domNode, renderOptions)
+
+ if (domNode === rootNode) {
+ rootNode = newNode
+ }
+ }
+
+ return rootNode
+}
+
+function patchIndices(patches) {
+ var indices = []
+
+ for (var key in patches) {
+ if (key !== "a") {
+ indices.push(Number(key))
+ }
+ }
+
+ return indices
+}
+
+},{"./dom-index":7,"./patch-op":8,"global/document":2,"x-is-array":4}],10:[function(require,module,exports){
+var isWidget = require("../vnode/is-widget.js")
+
+module.exports = updateWidget
+
+function updateWidget(a, b) {
+ if (isWidget(a) && isWidget(b)) {
+ if ("name" in a && "name" in b) {
+ return a.id === b.id
+ } else {
+ return a.init === b.init
+ }
+ }
+
+ return false
+}
+
+},{"../vnode/is-widget.js":16}],11:[function(require,module,exports){
+var isVNode = require("./is-vnode")
+var isVText = require("./is-vtext")
+var isWidget = require("./is-widget")
+var isThunk = require("./is-thunk")
+
+module.exports = handleThunk
+
+function handleThunk(a, b) {
+ var renderedA = a
+ var renderedB = b
+
+ if (isThunk(b)) {
+ renderedB = renderThunk(b, a)
+ }
+
+ if (isThunk(a)) {
+ renderedA = renderThunk(a, null)
+ }
+
+ return {
+ a: renderedA,
+ b: renderedB
+ }
+}
+
+function renderThunk(thunk, previous) {
+ var renderedThunk = thunk.vnode
+
+ if (!renderedThunk) {
+ renderedThunk = thunk.vnode = thunk.render(previous)
+ }
+
+ if (!(isVNode(renderedThunk) ||
+ isVText(renderedThunk) ||
+ isWidget(renderedThunk))) {
+ throw new Error("thunk did not return a valid node");
+ }
+
+ return renderedThunk
+}
+
+},{"./is-thunk":12,"./is-vnode":14,"./is-vtext":15,"./is-widget":16}],12:[function(require,module,exports){
+module.exports = isThunk
+
+function isThunk(t) {
+ return t && t.type === "Thunk"
+}
+
+},{}],13:[function(require,module,exports){
+module.exports = isHook
+
+function isHook(hook) {
+ return hook &&
+ (typeof hook.hook === "function" && !hook.hasOwnProperty("hook") ||
+ typeof hook.unhook === "function" && !hook.hasOwnProperty("unhook"))
+}
+
+},{}],14:[function(require,module,exports){
+var version = require("./version")
+
+module.exports = isVirtualNode
+
+function isVirtualNode(x) {
+ return x && x.type === "VirtualNode" && x.version === version
+}
+
+},{"./version":17}],15:[function(require,module,exports){
+var version = require("./version")
+
+module.exports = isVirtualText
+
+function isVirtualText(x) {
+ return x && x.type === "VirtualText" && x.version === version
+}
+
+},{"./version":17}],16:[function(require,module,exports){
+module.exports = isWidget
+
+function isWidget(w) {
+ return w && w.type === "Widget"
+}
+
+},{}],17:[function(require,module,exports){
+module.exports = "2"
+
+},{}],18:[function(require,module,exports){
+var version = require("./version")
+var isVNode = require("./is-vnode")
+var isWidget = require("./is-widget")
+var isThunk = require("./is-thunk")
+var isVHook = require("./is-vhook")
+
+module.exports = VirtualNode
+
+var noProperties = {}
+var noChildren = []
+
+function VirtualNode(tagName, properties, children, key, namespace) {
+ this.tagName = tagName
+ this.properties = properties || noProperties
+ this.children = children || noChildren
+ this.key = key != null ? String(key) : undefined
+ this.namespace = (typeof namespace === "string") ? namespace : null
+
+ var count = (children && children.length) || 0
+ var descendants = 0
+ var hasWidgets = false
+ var hasThunks = false
+ var descendantHooks = false
+ var hooks
+
+ for (var propName in properties) {
+ if (properties.hasOwnProperty(propName)) {
+ var property = properties[propName]
+ if (isVHook(property) && property.unhook) {
+ if (!hooks) {
+ hooks = {}
+ }
+
+ hooks[propName] = property
+ }
+ }
+ }
+
+ for (var i = 0; i < count; i++) {
+ var child = children[i]
+ if (isVNode(child)) {
+ descendants += child.count || 0
+
+ if (!hasWidgets && child.hasWidgets) {
+ hasWidgets = true
+ }
+
+ if (!hasThunks && child.hasThunks) {
+ hasThunks = true
+ }
+
+ if (!descendantHooks && (child.hooks || child.descendantHooks)) {
+ descendantHooks = true
+ }
+ } else if (!hasWidgets && isWidget(child)) {
+ if (typeof child.destroy === "function") {
+ hasWidgets = true
+ }
+ } else if (!hasThunks && isThunk(child)) {
+ hasThunks = true;
+ }
+ }
+
+ this.count = count + descendants
+ this.hasWidgets = hasWidgets
+ this.hasThunks = hasThunks
+ this.hooks = hooks
+ this.descendantHooks = descendantHooks
+}
+
+VirtualNode.prototype.version = version
+VirtualNode.prototype.type = "VirtualNode"
+
+},{"./is-thunk":12,"./is-vhook":13,"./is-vnode":14,"./is-widget":16,"./version":17}],19:[function(require,module,exports){
+var version = require("./version")
+
+VirtualPatch.NONE = 0
+VirtualPatch.VTEXT = 1
+VirtualPatch.VNODE = 2
+VirtualPatch.WIDGET = 3
+VirtualPatch.PROPS = 4
+VirtualPatch.ORDER = 5
+VirtualPatch.INSERT = 6
+VirtualPatch.REMOVE = 7
+VirtualPatch.THUNK = 8
+
+module.exports = VirtualPatch
+
+function VirtualPatch(type, vNode, patch) {
+ this.type = Number(type)
+ this.vNode = vNode
+ this.patch = patch
+}
+
+VirtualPatch.prototype.version = version
+VirtualPatch.prototype.type = "VirtualPatch"
+
+},{"./version":17}],20:[function(require,module,exports){
+var version = require("./version")
+
+module.exports = VirtualText
+
+function VirtualText(text) {
+ this.text = String(text)
+}
+
+VirtualText.prototype.version = version
+VirtualText.prototype.type = "VirtualText"
+
+},{"./version":17}],21:[function(require,module,exports){
+var isObject = require("is-object")
+var isHook = require("../vnode/is-vhook")
+
+module.exports = diffProps
+
+function diffProps(a, b) {
+ var diff
+
+ for (var aKey in a) {
+ if (!(aKey in b)) {
+ diff = diff || {}
+ diff[aKey] = undefined
+ }
+
+ var aValue = a[aKey]
+ var bValue = b[aKey]
+
+ if (aValue === bValue) {
+ continue
+ } else if (isObject(aValue) && isObject(bValue)) {
+ if (getPrototype(bValue) !== getPrototype(aValue)) {
+ diff = diff || {}
+ diff[aKey] = bValue
+ } else if (isHook(bValue)) {
+ diff = diff || {}
+ diff[aKey] = bValue
+ } else {
+ var objectDiff = diffProps(aValue, bValue)
+ if (objectDiff) {
+ diff = diff || {}
+ diff[aKey] = objectDiff
+ }
+ }
+ } else {
+ diff = diff || {}
+ diff[aKey] = bValue
+ }
+ }
+
+ for (var bKey in b) {
+ if (!(bKey in a)) {
+ diff = diff || {}
+ diff[bKey] = b[bKey]
+ }
+ }
+
+ return diff
+}
+
+function getPrototype(value) {
+ if (Object.getPrototypeOf) {
+ return Object.getPrototypeOf(value)
+ } else if (value.__proto__) {
+ return value.__proto__
+ } else if (value.constructor) {
+ return value.constructor.prototype
+ }
+}
+
+},{"../vnode/is-vhook":13,"is-object":3}],22:[function(require,module,exports){
+var isArray = require("x-is-array")
+
+var VPatch = require("../vnode/vpatch")
+var isVNode = require("../vnode/is-vnode")
+var isVText = require("../vnode/is-vtext")
+var isWidget = require("../vnode/is-widget")
+var isThunk = require("../vnode/is-thunk")
+var handleThunk = require("../vnode/handle-thunk")
+
+var diffProps = require("./diff-props")
+
+module.exports = diff
+
+function diff(a, b) {
+ var patch = { a: a }
+ walk(a, b, patch, 0)
+ return patch
+}
+
+function walk(a, b, patch, index) {
+ if (a === b) {
+ return
+ }
+
+ var apply = patch[index]
+ var applyClear = false
+
+ if (isThunk(a) || isThunk(b)) {
+ thunks(a, b, patch, index)
+ } else if (b == null) {
+
+ // If a is a widget we will add a remove patch for it
+ // Otherwise any child widgets/hooks must be destroyed.
+ // This prevents adding two remove patches for a widget.
+ if (!isWidget(a)) {
+ clearState(a, patch, index)
+ apply = patch[index]
+ }
+
+ apply = appendPatch(apply, new VPatch(VPatch.REMOVE, a, b))
+ } else if (isVNode(b)) {
+ if (isVNode(a)) {
+ if (a.tagName === b.tagName &&
+ a.namespace === b.namespace &&
+ a.key === b.key) {
+ var propsPatch = diffProps(a.properties, b.properties)
+ if (propsPatch) {
+ apply = appendPatch(apply,
+ new VPatch(VPatch.PROPS, a, propsPatch))
+ }
+ apply = diffChildren(a, b, patch, apply, index)
+ } else {
+ apply = appendPatch(apply, new VPatch(VPatch.VNODE, a, b))
+ applyClear = true
+ }
+ } else {
+ apply = appendPatch(apply, new VPatch(VPatch.VNODE, a, b))
+ applyClear = true
+ }
+ } else if (isVText(b)) {
+ if (!isVText(a)) {
+ apply = appendPatch(apply, new VPatch(VPatch.VTEXT, a, b))
+ applyClear = true
+ } else if (a.text !== b.text) {
+ apply = appendPatch(apply, new VPatch(VPatch.VTEXT, a, b))
+ }
+ } else if (isWidget(b)) {
+ if (!isWidget(a)) {
+ applyClear = true
+ }
+
+ apply = appendPatch(apply, new VPatch(VPatch.WIDGET, a, b))
+ }
+
+ if (apply) {
+ patch[index] = apply
+ }
+
+ if (applyClear) {
+ clearState(a, patch, index)
+ }
+}
+
+function diffChildren(a, b, patch, apply, index) {
+ var aChildren = a.children
+ var orderedSet = reorder(aChildren, b.children)
+ var bChildren = orderedSet.children
+
+ var aLen = aChildren.length
+ var bLen = bChildren.length
+ var len = aLen > bLen ? aLen : bLen
+
+ for (var i = 0; i < len; i++) {
+ var leftNode = aChildren[i]
+ var rightNode = bChildren[i]
+ index += 1
+
+ if (!leftNode) {
+ if (rightNode) {
+ // Excess nodes in b need to be added
+ apply = appendPatch(apply,
+ new VPatch(VPatch.INSERT, null, rightNode))
+ }
+ } else {
+ walk(leftNode, rightNode, patch, index)
+ }
+
+ if (isVNode(leftNode) && leftNode.count) {
+ index += leftNode.count
+ }
+ }
+
+ if (orderedSet.moves) {
+ // Reorder nodes last
+ apply = appendPatch(apply, new VPatch(
+ VPatch.ORDER,
+ a,
+ orderedSet.moves
+ ))
+ }
+
+ return apply
+}
+
+function clearState(vNode, patch, index) {
+ // TODO: Make this a single walk, not two
+ unhook(vNode, patch, index)
+ destroyWidgets(vNode, patch, index)
+}
+
+// Patch records for all destroyed widgets must be added because we need
+// a DOM node reference for the destroy function
+function destroyWidgets(vNode, patch, index) {
+ if (isWidget(vNode)) {
+ if (typeof vNode.destroy === "function") {
+ patch[index] = appendPatch(
+ patch[index],
+ new VPatch(VPatch.REMOVE, vNode, null)
+ )
+ }
+ } else if (isVNode(vNode) && (vNode.hasWidgets || vNode.hasThunks)) {
+ var children = vNode.children
+ var len = children.length
+ for (var i = 0; i < len; i++) {
+ var child = children[i]
+ index += 1
+
+ destroyWidgets(child, patch, index)
+
+ if (isVNode(child) && child.count) {
+ index += child.count
+ }
+ }
+ } else if (isThunk(vNode)) {
+ thunks(vNode, null, patch, index)
+ }
+}
+
+// Create a sub-patch for thunks
+function thunks(a, b, patch, index) {
+ var nodes = handleThunk(a, b)
+ var thunkPatch = diff(nodes.a, nodes.b)
+ if (hasPatches(thunkPatch)) {
+ patch[index] = new VPatch(VPatch.THUNK, null, thunkPatch)
+ }
+}
+
+function hasPatches(patch) {
+ for (var index in patch) {
+ if (index !== "a") {
+ return true
+ }
+ }
+
+ return false
+}
+
+// Execute hooks when two nodes are identical
+function unhook(vNode, patch, index) {
+ if (isVNode(vNode)) {
+ if (vNode.hooks) {
+ patch[index] = appendPatch(
+ patch[index],
+ new VPatch(
+ VPatch.PROPS,
+ vNode,
+ undefinedKeys(vNode.hooks)
+ )
+ )
+ }
+
+ if (vNode.descendantHooks || vNode.hasThunks) {
+ var children = vNode.children
+ var len = children.length
+ for (var i = 0; i < len; i++) {
+ var child = children[i]
+ index += 1
+
+ unhook(child, patch, index)
+
+ if (isVNode(child) && child.count) {
+ index += child.count
+ }
+ }
+ }
+ } else if (isThunk(vNode)) {
+ thunks(vNode, null, patch, index)
+ }
+}
+
+function undefinedKeys(obj) {
+ var result = {}
+
+ for (var key in obj) {
+ result[key] = undefined
+ }
+
+ return result
+}
+
+// List diff, naive left to right reordering
+function reorder(aChildren, bChildren) {
+ // O(M) time, O(M) memory
+ var bChildIndex = keyIndex(bChildren)
+ var bKeys = bChildIndex.keys
+ var bFree = bChildIndex.free
+
+ if (bFree.length === bChildren.length) {
+ return {
+ children: bChildren,
+ moves: null
+ }
+ }
+
+ // O(N) time, O(N) memory
+ var aChildIndex = keyIndex(aChildren)
+ var aKeys = aChildIndex.keys
+ var aFree = aChildIndex.free
+
+ if (aFree.length === aChildren.length) {
+ return {
+ children: bChildren,
+ moves: null
+ }
+ }
+
+ // O(MAX(N, M)) memory
+ var newChildren = []
+
+ var freeIndex = 0
+ var freeCount = bFree.length
+ var deletedItems = 0
+
+ // Iterate through a and match a node in b
+ // O(N) time,
+ for (var i = 0 ; i < aChildren.length; i++) {
+ var aItem = aChildren[i]
+ var itemIndex
+
+ if (aItem.key) {
+ if (bKeys.hasOwnProperty(aItem.key)) {
+ // Match up the old keys
+ itemIndex = bKeys[aItem.key]
+ newChildren.push(bChildren[itemIndex])
+
+ } else {
+ // Remove old keyed items
+ itemIndex = i - deletedItems++
+ newChildren.push(null)
+ }
+ } else {
+ // Match the item in a with the next free item in b
+ if (freeIndex < freeCount) {
+ itemIndex = bFree[freeIndex++]
+ newChildren.push(bChildren[itemIndex])
+ } else {
+ // There are no free items in b to match with
+ // the free items in a, so the extra free nodes
+ // are deleted.
+ itemIndex = i - deletedItems++
+ newChildren.push(null)
+ }
+ }
+ }
+
+ var lastFreeIndex = freeIndex >= bFree.length ?
+ bChildren.length :
+ bFree[freeIndex]
+
+ // Iterate through b and append any new keys
+ // O(M) time
+ for (var j = 0; j < bChildren.length; j++) {
+ var newItem = bChildren[j]
+
+ if (newItem.key) {
+ if (!aKeys.hasOwnProperty(newItem.key)) {
+ // Add any new keyed items
+ // We are adding new items to the end and then sorting them
+ // in place. In future we should insert new items in place.
+ newChildren.push(newItem)
+ }
+ } else if (j >= lastFreeIndex) {
+ // Add any leftover non-keyed items
+ newChildren.push(newItem)
+ }
+ }
+
+ var simulate = newChildren.slice()
+ var simulateIndex = 0
+ var removes = []
+ var inserts = []
+ var simulateItem
+
+ for (var k = 0; k < bChildren.length;) {
+ var wantedItem = bChildren[k]
+ simulateItem = simulate[simulateIndex]
+
+ // remove items
+ while (simulateItem === null && simulate.length) {
+ removes.push(remove(simulate, simulateIndex, null))
+ simulateItem = simulate[simulateIndex]
+ }
+
+ if (!simulateItem || simulateItem.key !== wantedItem.key) {
+ // if we need a key in this position...
+ if (wantedItem.key) {
+ if (simulateItem && simulateItem.key) {
+ // if an insert doesn't put this key in place, it needs to move
+ if (bKeys[simulateItem.key] !== k + 1) {
+ removes.push(remove(simulate, simulateIndex, simulateItem.key))
+ simulateItem = simulate[simulateIndex]
+ // if the remove didn't put the wanted item in place, we need to insert it
+ if (!simulateItem || simulateItem.key !== wantedItem.key) {
+ inserts.push({key: wantedItem.key, to: k})
+ }
+ // items are matching, so skip ahead
+ else {
+ simulateIndex++
+ }
+ }
+ else {
+ inserts.push({key: wantedItem.key, to: k})
+ }
+ }
+ else {
+ inserts.push({key: wantedItem.key, to: k})
+ }
+ k++
+ }
+ // a key in simulate has no matching wanted key, remove it
+ else if (simulateItem && simulateItem.key) {
+ removes.push(remove(simulate, simulateIndex, simulateItem.key))
+ }
+ }
+ else {
+ simulateIndex++
+ k++
+ }
+ }
+
+ // remove all the remaining nodes from simulate
+ while(simulateIndex < simulate.length) {
+ simulateItem = simulate[simulateIndex]
+ removes.push(remove(simulate, simulateIndex, simulateItem && simulateItem.key))
+ }
+
+ // If the only moves we have are deletes then we can just
+ // let the delete patch remove these items.
+ if (removes.length === deletedItems && !inserts.length) {
+ return {
+ children: newChildren,
+ moves: null
+ }
+ }
+
+ return {
+ children: newChildren,
+ moves: {
+ removes: removes,
+ inserts: inserts
+ }
+ }
+}
+
+function remove(arr, index, key) {
+ arr.splice(index, 1)
+
+ return {
+ from: index,
+ key: key
+ }
+}
+
+function keyIndex(children) {
+ var keys = {}
+ var free = []
+ var length = children.length
+
+ for (var i = 0; i < length; i++) {
+ var child = children[i]
+
+ if (child.key) {
+ keys[child.key] = i
+ } else {
+ free.push(i)
+ }
+ }
+
+ return {
+ keys: keys, // A hash of key name to index
+ free: free, // An array of unkeyed item indices
+ }
+}
+
+function appendPatch(apply, patch) {
+ if (apply) {
+ if (isArray(apply)) {
+ apply.push(patch)
+ } else {
+ apply = [apply, patch]
+ }
+
+ return apply
+ } else {
+ return patch
+ }
+}
+
+},{"../vnode/handle-thunk":11,"../vnode/is-thunk":12,"../vnode/is-vnode":14,"../vnode/is-vtext":15,"../vnode/is-widget":16,"../vnode/vpatch":19,"./diff-props":21,"x-is-array":4}],23:[function(require,module,exports){
+var VNode = require('virtual-dom/vnode/vnode');
+var VText = require('virtual-dom/vnode/vtext');
+var diff = require('virtual-dom/vtree/diff');
+var patch = require('virtual-dom/vdom/patch');
+var createElement = require('virtual-dom/create-element');
+var isHook = require("virtual-dom/vnode/is-vhook");
+
+
+Elm.Native.VirtualDom = {};
+Elm.Native.VirtualDom.make = function(elm)
+{
+ elm.Native = elm.Native || {};
+ elm.Native.VirtualDom = elm.Native.VirtualDom || {};
+ if (elm.Native.VirtualDom.values)
+ {
+ return elm.Native.VirtualDom.values;
+ }
+
+ var Element = Elm.Native.Graphics.Element.make(elm);
+ var Json = Elm.Native.Json.make(elm);
+ var List = Elm.Native.List.make(elm);
+ var Signal = Elm.Native.Signal.make(elm);
+ var Utils = Elm.Native.Utils.make(elm);
+
+ var ATTRIBUTE_KEY = 'UniqueNameThatOthersAreVeryUnlikelyToUse';
+
+ function listToProperties(list)
+ {
+ var object = {};
+ while (list.ctor !== '[]')
+ {
+ var entry = list._0;
+ if (entry.key === ATTRIBUTE_KEY)
+ {
+ object.attributes = object.attributes || {};
+ object.attributes[entry.value.attrKey] = entry.value.attrValue;
+ }
+ else
+ {
+ object[entry.key] = entry.value;
+ }
+ list = list._1;
+ }
+ return object;
+ }
+
+ function node(name)
+ {
+ return F2(function(propertyList, contents) {
+ return makeNode(name, propertyList, contents);
+ });
+ }
+
+ function makeNode(name, propertyList, contents)
+ {
+ var props = listToProperties(propertyList);
+
+ var key, namespace;
+ // support keys
+ if (props.key !== undefined)
+ {
+ key = props.key;
+ props.key = undefined;
+ }
+
+ // support namespace
+ if (props.namespace !== undefined)
+ {
+ namespace = props.namespace;
+ props.namespace = undefined;
+ }
+
+ // ensure that setting text of an input does not move the cursor
+ var useSoftSet =
+ name === 'input'
+ && props.value !== undefined
+ && !isHook(props.value);
+
+ if (useSoftSet)
+ {
+ props.value = SoftSetHook(props.value);
+ }
+
+ return new VNode(name, props, List.toArray(contents), key, namespace);
+ }
+
+ function property(key, value)
+ {
+ return {
+ key: key,
+ value: value
+ };
+ }
+
+ function attribute(key, value)
+ {
+ return {
+ key: ATTRIBUTE_KEY,
+ value: {
+ attrKey: key,
+ attrValue: value
+ }
+ };
+ }
+
+ function on(name, options, decoder, createMessage)
+ {
+ function eventHandler(event)
+ {
+ var value = A2(Json.runDecoderValue, decoder, event);
+ if (value.ctor === 'Ok')
+ {
+ if (options.stopPropagation)
+ {
+ event.stopPropagation();
+ }
+ if (options.preventDefault)
+ {
+ event.preventDefault();
+ }
+ Signal.sendMessage(createMessage(value._0));
+ }
+ }
+ return property('on' + name, eventHandler);
+ }
+
+ function SoftSetHook(value)
+ {
+ if (!(this instanceof SoftSetHook))
+ {
+ return new SoftSetHook(value);
+ }
+
+ this.value = value;
+ }
+
+ SoftSetHook.prototype.hook = function (node, propertyName)
+ {
+ if (node[propertyName] !== this.value)
+ {
+ node[propertyName] = this.value;
+ }
+ };
+
+ function text(string)
+ {
+ return new VText(string);
+ }
+
+ function ElementWidget(element)
+ {
+ this.element = element;
+ }
+
+ ElementWidget.prototype.type = "Widget";
+
+ ElementWidget.prototype.init = function init()
+ {
+ return Element.render(this.element);
+ };
+
+ ElementWidget.prototype.update = function update(previous, node)
+ {
+ return Element.update(node, previous.element, this.element);
+ };
+
+ function fromElement(element)
+ {
+ return new ElementWidget(element);
+ }
+
+ function toElement(width, height, html)
+ {
+ return A3(Element.newElement, width, height, {
+ ctor: 'Custom',
+ type: 'evancz/elm-html',
+ render: render,
+ update: update,
+ model: html
+ });
+ }
+
+ function render(model)
+ {
+ var element = Element.createNode('div');
+ element.appendChild(createElement(model));
+ return element;
+ }
+
+ function update(node, oldModel, newModel)
+ {
+ updateAndReplace(node.firstChild, oldModel, newModel);
+ return node;
+ }
+
+ function updateAndReplace(node, oldModel, newModel)
+ {
+ var patches = diff(oldModel, newModel);
+ var newNode = patch(node, patches);
+ return newNode;
+ }
+
+ function lazyRef(fn, a)
+ {
+ function thunk()
+ {
+ return fn(a);
+ }
+ return new Thunk(fn, [a], thunk);
+ }
+
+ function lazyRef2(fn, a, b)
+ {
+ function thunk()
+ {
+ return A2(fn, a, b);
+ }
+ return new Thunk(fn, [a,b], thunk);
+ }
+
+ function lazyRef3(fn, a, b, c)
+ {
+ function thunk()
+ {
+ return A3(fn, a, b, c);
+ }
+ return new Thunk(fn, [a,b,c], thunk);
+ }
+
+ function Thunk(fn, args, thunk)
+ {
+ this.fn = fn;
+ this.args = args;
+ this.vnode = null;
+ this.key = undefined;
+ this.thunk = thunk;
+ }
+
+ Thunk.prototype.type = "Thunk";
+ Thunk.prototype.update = updateThunk;
+ Thunk.prototype.render = renderThunk;
+
+ function shouldUpdate(current, previous)
+ {
+ if (current.fn !== previous.fn)
+ {
+ return true;
+ }
+
+ // if it's the same function, we know the number of args must match
+ var cargs = current.args;
+ var pargs = previous.args;
+
+ for (var i = cargs.length; i--; )
+ {
+ if (cargs[i] !== pargs[i])
+ {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ function updateThunk(previous, domNode)
+ {
+ if (!shouldUpdate(this, previous))
+ {
+ this.vnode = previous.vnode;
+ return;
+ }
+
+ if (!this.vnode)
+ {
+ this.vnode = this.thunk();
+ }
+
+ var patches = diff(previous.vnode, this.vnode);
+ patch(domNode, patches);
+ }
+
+ function renderThunk()
+ {
+ return this.thunk();
+ }
+
+ return Elm.Native.VirtualDom.values = {
+ node: node,
+ text: text,
+ on: F4(on),
+
+ property: F2(property),
+ attribute: F2(attribute),
+
+ lazy: F2(lazyRef),
+ lazy2: F3(lazyRef2),
+ lazy3: F4(lazyRef3),
+
+ toElement: F3(toElement),
+ fromElement: fromElement,
+
+ render: createElement,
+ updateAndReplace: updateAndReplace
+ };
+};
+
+},{"virtual-dom/create-element":1,"virtual-dom/vdom/patch":9,"virtual-dom/vnode/is-vhook":13,"virtual-dom/vnode/vnode":18,"virtual-dom/vnode/vtext":20,"virtual-dom/vtree/diff":22}],24:[function(require,module,exports){
+
+},{}]},{},[23]);
+
+Elm.Persona = Elm.Persona || {};
+Elm.Persona.make = function (_elm) {
+ "use strict";
+ _elm.Persona = _elm.Persona || {};
+ if (_elm.Persona.values)
+ return _elm.Persona.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Persona",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var toString = function (operation) {
+ switch (operation.ctor)
+ {case "SignIn": return "SignIn";
+ case "SignOut":
+ return "SignOut";}
+ return "NoOp";
+ };
+ var SignOut = {ctor: "SignOut"};
+ var SignIn = {ctor: "SignIn"};
+ var NoOp = {ctor: "NoOp"};
+ var operations = $Signal.mailbox(NoOp);
+ var fromString = function (str) {
+ switch (str)
+ {case "SignIn": return SignIn;
+ case "SignOut": return SignOut;}
+ return NoOp;
+ };
+ _elm.Persona.values = {_op: _op
+ ,operations: operations
+ ,fromString: fromString
+ ,toString: toString
+ ,NoOp: NoOp
+ ,SignIn: SignIn
+ ,SignOut: SignOut};
+ return _elm.Persona.values;
+};
+Elm.Reads = Elm.Reads || {};
+Elm.Reads.make = function (_elm) {
+ "use strict";
+ _elm.Reads = _elm.Reads || {};
+ if (_elm.Reads.values)
+ return _elm.Reads.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Reads",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Reads = Elm.Native.Reads.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var readInt = $Native$Reads.readInt;
+ _elm.Reads.values = {_op: _op
+ ,readInt: readInt};
+ return _elm.Reads.values;
+};
+Elm.Result = Elm.Result || {};
+Elm.Result.make = function (_elm) {
+ "use strict";
+ _elm.Result = _elm.Result || {};
+ if (_elm.Result.values)
+ return _elm.Result.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Result",
+ $Maybe = Elm.Maybe.make(_elm);
+ var toMaybe = function (result) {
+ switch (result.ctor)
+ {case "Err":
+ return $Maybe.Nothing;
+ case "Ok":
+ return $Maybe.Just(result._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var Err = function (a) {
+ return {ctor: "Err",_0: a};
+ };
+ var andThen = F2(function (result,
+ callback) {
+ switch (result.ctor)
+ {case "Err":
+ return Err(result._0);
+ case "Ok":
+ return callback(result._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var Ok = function (a) {
+ return {ctor: "Ok",_0: a};
+ };
+ var map = F2(function (func,
+ ra) {
+ switch (ra.ctor)
+ {case "Err": return Err(ra._0);
+ case "Ok":
+ return Ok(func(ra._0));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var map2 = F3(function (func,
+ ra,
+ rb) {
+ var _v9 = {ctor: "_Tuple2"
+ ,_0: ra
+ ,_1: rb};
+ switch (_v9.ctor)
+ {case "_Tuple2":
+ switch (_v9._0.ctor)
+ {case "Err":
+ return Err(_v9._0._0);
+ case "Ok": switch (_v9._1.ctor)
+ {case "Ok": return Ok(A2(func,
+ _v9._0._0,
+ _v9._1._0));}
+ break;}
+ switch (_v9._1.ctor)
+ {case "Err":
+ return Err(_v9._1._0);}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var map3 = F4(function (func,
+ ra,
+ rb,
+ rc) {
+ var _v16 = {ctor: "_Tuple3"
+ ,_0: ra
+ ,_1: rb
+ ,_2: rc};
+ switch (_v16.ctor)
+ {case "_Tuple3":
+ switch (_v16._0.ctor)
+ {case "Err":
+ return Err(_v16._0._0);
+ case "Ok": switch (_v16._1.ctor)
+ {case "Ok":
+ switch (_v16._2.ctor)
+ {case "Ok": return Ok(A3(func,
+ _v16._0._0,
+ _v16._1._0,
+ _v16._2._0));}
+ break;}
+ break;}
+ switch (_v16._1.ctor)
+ {case "Err":
+ return Err(_v16._1._0);}
+ switch (_v16._2.ctor)
+ {case "Err":
+ return Err(_v16._2._0);}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var map4 = F5(function (func,
+ ra,
+ rb,
+ rc,
+ rd) {
+ var _v26 = {ctor: "_Tuple4"
+ ,_0: ra
+ ,_1: rb
+ ,_2: rc
+ ,_3: rd};
+ switch (_v26.ctor)
+ {case "_Tuple4":
+ switch (_v26._0.ctor)
+ {case "Err":
+ return Err(_v26._0._0);
+ case "Ok": switch (_v26._1.ctor)
+ {case "Ok":
+ switch (_v26._2.ctor)
+ {case "Ok":
+ switch (_v26._3.ctor)
+ {case "Ok": return Ok(A4(func,
+ _v26._0._0,
+ _v26._1._0,
+ _v26._2._0,
+ _v26._3._0));}
+ break;}
+ break;}
+ break;}
+ switch (_v26._1.ctor)
+ {case "Err":
+ return Err(_v26._1._0);}
+ switch (_v26._2.ctor)
+ {case "Err":
+ return Err(_v26._2._0);}
+ switch (_v26._3.ctor)
+ {case "Err":
+ return Err(_v26._3._0);}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var map5 = F6(function (func,
+ ra,
+ rb,
+ rc,
+ rd,
+ re) {
+ var _v39 = {ctor: "_Tuple5"
+ ,_0: ra
+ ,_1: rb
+ ,_2: rc
+ ,_3: rd
+ ,_4: re};
+ switch (_v39.ctor)
+ {case "_Tuple5":
+ switch (_v39._0.ctor)
+ {case "Err":
+ return Err(_v39._0._0);
+ case "Ok": switch (_v39._1.ctor)
+ {case "Ok":
+ switch (_v39._2.ctor)
+ {case "Ok":
+ switch (_v39._3.ctor)
+ {case "Ok":
+ switch (_v39._4.ctor)
+ {case "Ok": return Ok(A5(func,
+ _v39._0._0,
+ _v39._1._0,
+ _v39._2._0,
+ _v39._3._0,
+ _v39._4._0));}
+ break;}
+ break;}
+ break;}
+ break;}
+ switch (_v39._1.ctor)
+ {case "Err":
+ return Err(_v39._1._0);}
+ switch (_v39._2.ctor)
+ {case "Err":
+ return Err(_v39._2._0);}
+ switch (_v39._3.ctor)
+ {case "Err":
+ return Err(_v39._3._0);}
+ switch (_v39._4.ctor)
+ {case "Err":
+ return Err(_v39._4._0);}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var formatError = F2(function (f,
+ result) {
+ switch (result.ctor)
+ {case "Err":
+ return Err(f(result._0));
+ case "Ok":
+ return Ok(result._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var fromMaybe = F2(function (err,
+ maybe) {
+ switch (maybe.ctor)
+ {case "Just":
+ return Ok(maybe._0);
+ case "Nothing":
+ return Err(err);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ _elm.Result.values = {_op: _op
+ ,map: map
+ ,map2: map2
+ ,map3: map3
+ ,map4: map4
+ ,map5: map5
+ ,andThen: andThen
+ ,toMaybe: toMaybe
+ ,fromMaybe: fromMaybe
+ ,formatError: formatError
+ ,Ok: Ok
+ ,Err: Err};
+ return _elm.Result.values;
+};
+Elm.ServerCommunication = Elm.ServerCommunication || {};
+Elm.ServerCommunication.make = function (_elm) {
+ "use strict";
+ _elm.ServerCommunication = _elm.ServerCommunication || {};
+ if (_elm.ServerCommunication.values)
+ return _elm.ServerCommunication.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "ServerCommunication",
+ $Basics = Elm.Basics.make(_elm),
+ $Http = Elm.Http.make(_elm),
+ $InitViewAction = Elm.InitViewAction.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View$LoggedIn$Add = Elm.Model.View.LoggedIn.Add.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $SimpleHTTP = Elm.SimpleHTTP.make(_elm),
+ $Task = Elm.Task.make(_elm),
+ $Time = Elm.Time.make(_elm),
+ $Update = Elm.Update.make(_elm),
+ $Update$LoggedIn = Elm.Update.LoggedIn.make(_elm),
+ $Update$LoggedIn$Account = Elm.Update.LoggedIn.Account.make(_elm),
+ $Update$LoggedIn$Monthly = Elm.Update.LoggedIn.Monthly.make(_elm);
+ var deletePaymentURL = function (id) {
+ return A2($Basics._op["++"],
+ "payment/delete?id=",
+ $Basics.toString(id));
+ };
+ var addPaymentURL = F3(function (name,
+ cost,
+ frequency) {
+ return A2($Basics._op["++"],
+ "/payment/add?name=",
+ A2($Basics._op["++"],
+ name,
+ A2($Basics._op["++"],
+ "&cost=",
+ A2($Basics._op["++"],
+ $Basics.toString(cost),
+ A2($Basics._op["++"],
+ "&frequency=",
+ $Basics.toString(frequency))))));
+ });
+ var getPaymentsAtPage = function (page) {
+ return A2($Http.get,
+ $Model$Payment.paymentsDecoder,
+ A2($Basics._op["++"],
+ "payments?page=",
+ A2($Basics._op["++"],
+ $Basics.toString(page),
+ A2($Basics._op["++"],
+ "&perPage=",
+ $Basics.toString($Model$Payment.perPage)))));
+ };
+ var sendRequest = function (communication) {
+ switch (communication.ctor)
+ {case "AddMonthlyPayment":
+ return $Task.map(function (id) {
+ return $Update.UpdateLoggedIn(A3($Update$LoggedIn.AddMonthlyPayment,
+ id,
+ communication._0,
+ communication._1));
+ })(A2($Basics.flip,
+ $Task.andThen,
+ $SimpleHTTP.decodeHttpValue(A2($Json$Decode._op[":="],
+ "id",
+ $Model$Payment.paymentIdDecoder)))($SimpleHTTP.post(A3(addPaymentURL,
+ communication._0,
+ communication._1,
+ $Model$View$LoggedIn$Add.Monthly))));
+ case "AddPayment":
+ return $Task.map(function (payments) {
+ return $Update.UpdateLoggedIn(A4($Update$LoggedIn.AddPayment,
+ communication._0,
+ communication._1,
+ communication._2,
+ payments));
+ })(A2($Basics.flip,
+ $Task.andThen,
+ $Basics.always(getPaymentsAtPage(1)))($SimpleHTTP.post(A3(addPaymentURL,
+ communication._1,
+ communication._2,
+ $Model$View$LoggedIn$Add.Punctual))));
+ case "DeleteMonthlyPayment":
+ return $Task.map($Basics.always($Update.UpdateLoggedIn($Update$LoggedIn.UpdateMonthly($Update$LoggedIn$Monthly.DeletePayment(communication._0)))))($SimpleHTTP.post(deletePaymentURL(communication._0)));
+ case "DeletePayment":
+ return $Task.map(function (payments) {
+ return $Update.UpdateLoggedIn(A2($Update$LoggedIn.DeletePayment,
+ communication._0,
+ payments));
+ })(A2($Basics.flip,
+ $Task.andThen,
+ $Basics.always(getPaymentsAtPage(communication._1)))($SimpleHTTP.post(deletePaymentURL(communication._0.id))));
+ case "NoCommunication":
+ return $Task.succeed($Update.NoOp);
+ case "SetIncome":
+ return $Task.map($Basics.always($Update.UpdateLoggedIn($Update$LoggedIn.UpdateAccount(A2($Update$LoggedIn$Account.UpdateIncome,
+ communication._0,
+ communication._1)))))($SimpleHTTP.post(A2($Basics._op["++"],
+ "/income?amount=",
+ $Basics.toString(communication._1))));
+ case "SignIn":
+ return A2($Basics.flip,
+ $Task.andThen,
+ $Basics.always($InitViewAction.initViewAction))($SimpleHTTP.post(A2($Basics._op["++"],
+ "/signIn?assertion=",
+ communication._0)));
+ case "SignOut":
+ return $Task.map($Basics.always($Update.GoSignInView))($SimpleHTTP.post("/signOut"));
+ case "UpdatePage":
+ return A2($Basics.flip,
+ $Task.andThen,
+ function ($) {
+ return $Task.succeed($Update.UpdateLoggedIn($Update$LoggedIn.UpdatePage(communication._0)($)));
+ })(getPaymentsAtPage(communication._0));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var SignOut = {ctor: "SignOut"};
+ var UpdatePage = function (a) {
+ return {ctor: "UpdatePage"
+ ,_0: a};
+ };
+ var DeleteMonthlyPayment = function (a) {
+ return {ctor: "DeleteMonthlyPayment"
+ ,_0: a};
+ };
+ var DeletePayment = F2(function (a,
+ b) {
+ return {ctor: "DeletePayment"
+ ,_0: a
+ ,_1: b};
+ });
+ var SetIncome = F2(function (a,
+ b) {
+ return {ctor: "SetIncome"
+ ,_0: a
+ ,_1: b};
+ });
+ var AddMonthlyPayment = F2(function (a,
+ b) {
+ return {ctor: "AddMonthlyPayment"
+ ,_0: a
+ ,_1: b};
+ });
+ var AddPayment = F3(function (a,
+ b,
+ c) {
+ return {ctor: "AddPayment"
+ ,_0: a
+ ,_1: b
+ ,_2: c};
+ });
+ var SignIn = function (a) {
+ return {ctor: "SignIn"
+ ,_0: a};
+ };
+ var NoCommunication = {ctor: "NoCommunication"};
+ var serverCommunications = $Signal.mailbox(NoCommunication);
+ _elm.ServerCommunication.values = {_op: _op
+ ,sendRequest: sendRequest
+ ,serverCommunications: serverCommunications
+ ,NoCommunication: NoCommunication
+ ,SignIn: SignIn
+ ,AddPayment: AddPayment
+ ,AddMonthlyPayment: AddMonthlyPayment
+ ,SetIncome: SetIncome
+ ,DeletePayment: DeletePayment
+ ,DeleteMonthlyPayment: DeleteMonthlyPayment
+ ,UpdatePage: UpdatePage
+ ,SignOut: SignOut};
+ return _elm.ServerCommunication.values;
+};
+Elm.Sign = Elm.Sign || {};
+Elm.Sign.make = function (_elm) {
+ "use strict";
+ _elm.Sign = _elm.Sign || {};
+ if (_elm.Sign.values)
+ return _elm.Sign.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Sign",
+ $Basics = Elm.Basics.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var toServerCommunication = function (operation) {
+ switch (operation.ctor)
+ {case "NoOp":
+ return $ServerCommunication.NoCommunication;
+ case "SignIn":
+ return $ServerCommunication.SignIn(operation._0);
+ case "SignOut":
+ return $ServerCommunication.SignOut;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var SignOut = {ctor: "SignOut"};
+ var SignIn = function (a) {
+ return {ctor: "SignIn"
+ ,_0: a};
+ };
+ var NoOp = {ctor: "NoOp"};
+ var operationDecoderWithTag = function (operation) {
+ switch (operation)
+ {case "SignIn":
+ return A2($Json$Decode.map,
+ SignIn,
+ A2($Json$Decode._op[":="],
+ "assertion",
+ $Json$Decode.string));
+ case "SignOut":
+ return $Json$Decode.succeed(SignOut);}
+ return $Json$Decode.succeed(NoOp);
+ };
+ var operationDecoder = A2($Json$Decode.andThen,
+ A2($Json$Decode._op[":="],
+ "operation",
+ $Json$Decode.string),
+ operationDecoderWithTag);
+ var decodeOperation = function (value) {
+ return $Maybe.withDefault(NoOp)($Result.toMaybe(A2($Json$Decode.decodeValue,
+ operationDecoder,
+ value)));
+ };
+ _elm.Sign.values = {_op: _op
+ ,decodeOperation: decodeOperation
+ ,toServerCommunication: toServerCommunication
+ ,NoOp: NoOp
+ ,SignIn: SignIn
+ ,SignOut: SignOut};
+ return _elm.Sign.values;
+};
+Elm.Signal = Elm.Signal || {};
+Elm.Signal.make = function (_elm) {
+ "use strict";
+ _elm.Signal = _elm.Signal || {};
+ if (_elm.Signal.values)
+ return _elm.Signal.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Signal",
+ $Basics = Elm.Basics.make(_elm),
+ $Debug = Elm.Debug.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Signal = Elm.Native.Signal.make(_elm),
+ $Task = Elm.Task.make(_elm);
+ var send = F2(function (_v0,
+ value) {
+ var _raw = _v0,
+ $ = _raw.ctor === "Address" ? _raw : _U.badCase($moduleName,
+ "bugs in reporting the exact location right now"),
+ actuallySend = $._0;
+ return A2($Task.onError,
+ actuallySend(value),
+ function (_v1) {
+ var _ = _v1;
+ return $Task.succeed({ctor: "_Tuple0"});
+ });
+ });
+ var Message = function (a) {
+ return {ctor: "Message"
+ ,_0: a};
+ };
+ var message = F2(function (_v2,
+ value) {
+ var _raw = _v2,
+ $ = _raw.ctor === "Address" ? _raw : _U.badCase($moduleName,
+ "bugs in reporting the exact location right now"),
+ send = $._0;
+ return Message(send(value));
+ });
+ var mailbox = $Native$Signal.mailbox;
+ var Address = function (a) {
+ return {ctor: "Address"
+ ,_0: a};
+ };
+ var forwardTo = F2(function (_v3,
+ f) {
+ var _raw = _v3,
+ $ = _raw.ctor === "Address" ? _raw : _U.badCase($moduleName,
+ "bugs in reporting the exact location right now"),
+ send = $._0;
+ return Address(function (x) {
+ return send(f(x));
+ });
+ });
+ var Mailbox = F2(function (a,
+ b) {
+ return {_: {}
+ ,address: a
+ ,signal: b};
+ });
+ var sampleOn = $Native$Signal.sampleOn;
+ var dropRepeats = $Native$Signal.dropRepeats;
+ var filterMap = $Native$Signal.filterMap;
+ var filter = F3(function (isOk,
+ base,
+ signal) {
+ return A3(filterMap,
+ function (value) {
+ return isOk(value) ? $Maybe.Just(value) : $Maybe.Nothing;
+ },
+ base,
+ signal);
+ });
+ var merge = F2(function (left,
+ right) {
+ return A3($Native$Signal.genericMerge,
+ $Basics.always,
+ left,
+ right);
+ });
+ var mergeMany = function (signalList) {
+ var _v4 = $List.reverse(signalList);
+ switch (_v4.ctor)
+ {case "::":
+ return A3($List.foldl,
+ merge,
+ _v4._0,
+ _v4._1);
+ case "[]":
+ return $Debug.crash("mergeMany was given an empty list!");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var foldp = $Native$Signal.foldp;
+ var map5 = $Native$Signal.map5;
+ var map4 = $Native$Signal.map4;
+ var map3 = $Native$Signal.map3;
+ var map2 = $Native$Signal.map2;
+ _op["~"] = F2(function (funcs,
+ args) {
+ return A3(map2,
+ F2(function (f,v) {
+ return f(v);
+ }),
+ funcs,
+ args);
+ });
+ var map = $Native$Signal.map;
+ _op["<~"] = map;
+ var constant = $Native$Signal.constant;
+ var Signal = {ctor: "Signal"};
+ _elm.Signal.values = {_op: _op
+ ,merge: merge
+ ,mergeMany: mergeMany
+ ,map: map
+ ,map2: map2
+ ,map3: map3
+ ,map4: map4
+ ,map5: map5
+ ,constant: constant
+ ,dropRepeats: dropRepeats
+ ,filter: filter
+ ,filterMap: filterMap
+ ,sampleOn: sampleOn
+ ,foldp: foldp
+ ,mailbox: mailbox
+ ,send: send
+ ,message: message
+ ,forwardTo: forwardTo
+ ,Mailbox: Mailbox};
+ return _elm.Signal.values;
+};
+Elm.SimpleHTTP = Elm.SimpleHTTP || {};
+Elm.SimpleHTTP.make = function (_elm) {
+ "use strict";
+ _elm.SimpleHTTP = _elm.SimpleHTTP || {};
+ if (_elm.SimpleHTTP.values)
+ return _elm.SimpleHTTP.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "SimpleHTTP",
+ $Basics = Elm.Basics.make(_elm),
+ $Http = Elm.Http.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Task = Elm.Task.make(_elm);
+ var decodeHttpValue = F2(function (decoder,
+ value) {
+ switch (value.ctor)
+ {case "Text":
+ var _v2 = A2($Json$Decode.decodeString,
+ decoder,
+ value._0);
+ switch (_v2.ctor)
+ {case "Err":
+ return $Task.fail($Http.UnexpectedPayload(_v2._0));
+ case "Ok":
+ return $Task.succeed(_v2._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");}
+ return $Task.fail($Http.UnexpectedPayload("Response body is a blob, expecting a string."));
+ });
+ var promoteError = function (rawError) {
+ switch (rawError.ctor)
+ {case "RawNetworkError":
+ return $Http.NetworkError;
+ case "RawTimeout":
+ return $Http.Timeout;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var handleResponse = function (response) {
+ return _U.cmp(200,
+ response.status) < 1 && _U.cmp(response.status,
+ 300) < 0 ? $Task.succeed(response.value) : $Task.fail(A2($Http.BadResponse,
+ response.status,
+ response.statusText));
+ };
+ var post = function (url) {
+ return A2($Basics.flip,
+ $Task.andThen,
+ handleResponse)($Task.mapError(promoteError)($Http.send($Http.defaultSettings)({_: {}
+ ,body: $Http.empty
+ ,headers: _L.fromArray([])
+ ,url: url
+ ,verb: "POST"})));
+ };
+ _elm.SimpleHTTP.values = {_op: _op
+ ,post: post
+ ,decodeHttpValue: decodeHttpValue};
+ return _elm.SimpleHTTP.values;
+};
+Elm.String = Elm.String || {};
+Elm.String.make = function (_elm) {
+ "use strict";
+ _elm.String = _elm.String || {};
+ if (_elm.String.values)
+ return _elm.String.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "String",
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$String = Elm.Native.String.make(_elm),
+ $Result = Elm.Result.make(_elm);
+ var fromList = $Native$String.fromList;
+ var toList = $Native$String.toList;
+ var toFloat = $Native$String.toFloat;
+ var toInt = $Native$String.toInt;
+ var indices = $Native$String.indexes;
+ var indexes = $Native$String.indexes;
+ var endsWith = $Native$String.endsWith;
+ var startsWith = $Native$String.startsWith;
+ var contains = $Native$String.contains;
+ var all = $Native$String.all;
+ var any = $Native$String.any;
+ var toLower = $Native$String.toLower;
+ var toUpper = $Native$String.toUpper;
+ var lines = $Native$String.lines;
+ var words = $Native$String.words;
+ var trimRight = $Native$String.trimRight;
+ var trimLeft = $Native$String.trimLeft;
+ var trim = $Native$String.trim;
+ var padRight = $Native$String.padRight;
+ var padLeft = $Native$String.padLeft;
+ var pad = $Native$String.pad;
+ var dropRight = $Native$String.dropRight;
+ var dropLeft = $Native$String.dropLeft;
+ var right = $Native$String.right;
+ var left = $Native$String.left;
+ var slice = $Native$String.slice;
+ var repeat = $Native$String.repeat;
+ var join = $Native$String.join;
+ var split = $Native$String.split;
+ var foldr = $Native$String.foldr;
+ var foldl = $Native$String.foldl;
+ var reverse = $Native$String.reverse;
+ var filter = $Native$String.filter;
+ var map = $Native$String.map;
+ var length = $Native$String.length;
+ var concat = $Native$String.concat;
+ var append = $Native$String.append;
+ var uncons = $Native$String.uncons;
+ var cons = $Native$String.cons;
+ var fromChar = function ($char) {
+ return A2(cons,$char,"");
+ };
+ var isEmpty = $Native$String.isEmpty;
+ _elm.String.values = {_op: _op
+ ,isEmpty: isEmpty
+ ,length: length
+ ,reverse: reverse
+ ,repeat: repeat
+ ,cons: cons
+ ,uncons: uncons
+ ,fromChar: fromChar
+ ,append: append
+ ,concat: concat
+ ,split: split
+ ,join: join
+ ,words: words
+ ,lines: lines
+ ,slice: slice
+ ,left: left
+ ,right: right
+ ,dropLeft: dropLeft
+ ,dropRight: dropRight
+ ,contains: contains
+ ,startsWith: startsWith
+ ,endsWith: endsWith
+ ,indexes: indexes
+ ,indices: indices
+ ,toInt: toInt
+ ,toFloat: toFloat
+ ,toList: toList
+ ,fromList: fromList
+ ,toUpper: toUpper
+ ,toLower: toLower
+ ,pad: pad
+ ,padLeft: padLeft
+ ,padRight: padRight
+ ,trim: trim
+ ,trimLeft: trimLeft
+ ,trimRight: trimRight
+ ,map: map
+ ,filter: filter
+ ,foldl: foldl
+ ,foldr: foldr
+ ,any: any
+ ,all: all};
+ return _elm.String.values;
+};
+Elm.Task = Elm.Task || {};
+Elm.Task.make = function (_elm) {
+ "use strict";
+ _elm.Task = _elm.Task || {};
+ if (_elm.Task.values)
+ return _elm.Task.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Task",
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Task = Elm.Native.Task.make(_elm),
+ $Result = Elm.Result.make(_elm);
+ var sleep = $Native$Task.sleep;
+ var spawn = $Native$Task.spawn;
+ var ThreadID = function (a) {
+ return {ctor: "ThreadID"
+ ,_0: a};
+ };
+ var onError = $Native$Task.catch_;
+ var andThen = $Native$Task.andThen;
+ var fail = $Native$Task.fail;
+ var mapError = F2(function (f,
+ promise) {
+ return A2(onError,
+ promise,
+ function (err) {
+ return fail(f(err));
+ });
+ });
+ var succeed = $Native$Task.succeed;
+ var map = F2(function (func,
+ promiseA) {
+ return A2(andThen,
+ promiseA,
+ function (a) {
+ return succeed(func(a));
+ });
+ });
+ var map2 = F3(function (func,
+ promiseA,
+ promiseB) {
+ return A2(andThen,
+ promiseA,
+ function (a) {
+ return A2(andThen,
+ promiseB,
+ function (b) {
+ return succeed(A2(func,a,b));
+ });
+ });
+ });
+ var map3 = F4(function (func,
+ promiseA,
+ promiseB,
+ promiseC) {
+ return A2(andThen,
+ promiseA,
+ function (a) {
+ return A2(andThen,
+ promiseB,
+ function (b) {
+ return A2(andThen,
+ promiseC,
+ function (c) {
+ return succeed(A3(func,
+ a,
+ b,
+ c));
+ });
+ });
+ });
+ });
+ var map4 = F5(function (func,
+ promiseA,
+ promiseB,
+ promiseC,
+ promiseD) {
+ return A2(andThen,
+ promiseA,
+ function (a) {
+ return A2(andThen,
+ promiseB,
+ function (b) {
+ return A2(andThen,
+ promiseC,
+ function (c) {
+ return A2(andThen,
+ promiseD,
+ function (d) {
+ return succeed(A4(func,
+ a,
+ b,
+ c,
+ d));
+ });
+ });
+ });
+ });
+ });
+ var map5 = F6(function (func,
+ promiseA,
+ promiseB,
+ promiseC,
+ promiseD,
+ promiseE) {
+ return A2(andThen,
+ promiseA,
+ function (a) {
+ return A2(andThen,
+ promiseB,
+ function (b) {
+ return A2(andThen,
+ promiseC,
+ function (c) {
+ return A2(andThen,
+ promiseD,
+ function (d) {
+ return A2(andThen,
+ promiseE,
+ function (e) {
+ return succeed(A5(func,
+ a,
+ b,
+ c,
+ d,
+ e));
+ });
+ });
+ });
+ });
+ });
+ });
+ var andMap = F2(function (promiseFunc,
+ promiseValue) {
+ return A2(andThen,
+ promiseFunc,
+ function (func) {
+ return A2(andThen,
+ promiseValue,
+ function (value) {
+ return succeed(func(value));
+ });
+ });
+ });
+ var sequence = function (promises) {
+ switch (promises.ctor)
+ {case "::": return A3(map2,
+ F2(function (x,y) {
+ return A2($List._op["::"],
+ x,
+ y);
+ }),
+ promises._0,
+ sequence(promises._1));
+ case "[]":
+ return succeed(_L.fromArray([]));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var toMaybe = function (task) {
+ return A2(onError,
+ A2(map,$Maybe.Just,task),
+ function (_v3) {
+ var _ = _v3;
+ return succeed($Maybe.Nothing);
+ });
+ };
+ var fromMaybe = F2(function ($default,
+ maybe) {
+ switch (maybe.ctor)
+ {case "Just":
+ return succeed(maybe._0);
+ case "Nothing":
+ return fail($default);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var toResult = function (task) {
+ return A2(onError,
+ A2(map,$Result.Ok,task),
+ function (msg) {
+ return succeed($Result.Err(msg));
+ });
+ };
+ var fromResult = function (result) {
+ switch (result.ctor)
+ {case "Err":
+ return fail(result._0);
+ case "Ok":
+ return succeed(result._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var Task = {ctor: "Task"};
+ _elm.Task.values = {_op: _op
+ ,succeed: succeed
+ ,fail: fail
+ ,map: map
+ ,map2: map2
+ ,map3: map3
+ ,map4: map4
+ ,map5: map5
+ ,andMap: andMap
+ ,sequence: sequence
+ ,andThen: andThen
+ ,onError: onError
+ ,mapError: mapError
+ ,toMaybe: toMaybe
+ ,fromMaybe: fromMaybe
+ ,toResult: toResult
+ ,fromResult: fromResult
+ ,spawn: spawn
+ ,sleep: sleep};
+ return _elm.Task.values;
+};
+Elm.Text = Elm.Text || {};
+Elm.Text.make = function (_elm) {
+ "use strict";
+ _elm.Text = _elm.Text || {};
+ if (_elm.Text.values)
+ return _elm.Text.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Text",
+ $Color = Elm.Color.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$Text = Elm.Native.Text.make(_elm);
+ var line = $Native$Text.line;
+ var italic = $Native$Text.italic;
+ var bold = $Native$Text.bold;
+ var color = $Native$Text.color;
+ var height = $Native$Text.height;
+ var link = $Native$Text.link;
+ var monospace = $Native$Text.monospace;
+ var typeface = $Native$Text.typeface;
+ var style = $Native$Text.style;
+ var append = $Native$Text.append;
+ var fromString = $Native$Text.fromString;
+ var empty = fromString("");
+ var concat = function (texts) {
+ return A3($List.foldr,
+ append,
+ empty,
+ texts);
+ };
+ var join = F2(function (seperator,
+ texts) {
+ return concat(A2($List.intersperse,
+ seperator,
+ texts));
+ });
+ var defaultStyle = {_: {}
+ ,bold: false
+ ,color: $Color.black
+ ,height: $Maybe.Nothing
+ ,italic: false
+ ,line: $Maybe.Nothing
+ ,typeface: _L.fromArray([])};
+ var Style = F6(function (a,
+ b,
+ c,
+ d,
+ e,
+ f) {
+ return {_: {}
+ ,bold: d
+ ,color: c
+ ,height: b
+ ,italic: e
+ ,line: f
+ ,typeface: a};
+ });
+ var Through = {ctor: "Through"};
+ var Over = {ctor: "Over"};
+ var Under = {ctor: "Under"};
+ var Text = {ctor: "Text"};
+ _elm.Text.values = {_op: _op
+ ,fromString: fromString
+ ,empty: empty
+ ,append: append
+ ,concat: concat
+ ,join: join
+ ,link: link
+ ,style: style
+ ,defaultStyle: defaultStyle
+ ,typeface: typeface
+ ,monospace: monospace
+ ,height: height
+ ,color: color
+ ,bold: bold
+ ,italic: italic
+ ,line: line
+ ,Style: Style
+ ,Under: Under
+ ,Over: Over
+ ,Through: Through};
+ return _elm.Text.values;
+};
+Elm.Time = Elm.Time || {};
+Elm.Time.make = function (_elm) {
+ "use strict";
+ _elm.Time = _elm.Time || {};
+ if (_elm.Time.values)
+ return _elm.Time.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Time",
+ $Basics = Elm.Basics.make(_elm),
+ $Native$Signal = Elm.Native.Signal.make(_elm),
+ $Native$Time = Elm.Native.Time.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var delay = $Native$Signal.delay;
+ var since = F2(function (time,
+ signal) {
+ var stop = A2($Signal.map,
+ $Basics.always(-1),
+ A2(delay,time,signal));
+ var start = A2($Signal.map,
+ $Basics.always(1),
+ signal);
+ var delaydiff = A3($Signal.foldp,
+ F2(function (x,y) {
+ return x + y;
+ }),
+ 0,
+ A2($Signal.merge,start,stop));
+ return A2($Signal.map,
+ F2(function (x,y) {
+ return !_U.eq(x,y);
+ })(0),
+ delaydiff);
+ });
+ var timestamp = $Native$Signal.timestamp;
+ var every = $Native$Time.every;
+ var fpsWhen = $Native$Time.fpsWhen;
+ var fps = function (targetFrames) {
+ return A2(fpsWhen,
+ targetFrames,
+ $Signal.constant(true));
+ };
+ var inMilliseconds = function (t) {
+ return t;
+ };
+ var millisecond = 1;
+ var second = 1000 * millisecond;
+ var minute = 60 * second;
+ var hour = 60 * minute;
+ var inHours = function (t) {
+ return t / hour;
+ };
+ var inMinutes = function (t) {
+ return t / minute;
+ };
+ var inSeconds = function (t) {
+ return t / second;
+ };
+ _elm.Time.values = {_op: _op
+ ,millisecond: millisecond
+ ,second: second
+ ,minute: minute
+ ,hour: hour
+ ,inMilliseconds: inMilliseconds
+ ,inSeconds: inSeconds
+ ,inMinutes: inMinutes
+ ,inHours: inHours
+ ,fps: fps
+ ,fpsWhen: fpsWhen
+ ,every: every
+ ,timestamp: timestamp
+ ,delay: delay
+ ,since: since};
+ return _elm.Time.values;
+};
+Elm.Transform2D = Elm.Transform2D || {};
+Elm.Transform2D.make = function (_elm) {
+ "use strict";
+ _elm.Transform2D = _elm.Transform2D || {};
+ if (_elm.Transform2D.values)
+ return _elm.Transform2D.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Transform2D",
+ $Native$Transform2D = Elm.Native.Transform2D.make(_elm);
+ var multiply = $Native$Transform2D.multiply;
+ var rotation = $Native$Transform2D.rotation;
+ var matrix = $Native$Transform2D.matrix;
+ var translation = F2(function (x,
+ y) {
+ return A6(matrix,
+ 1,
+ 0,
+ 0,
+ 1,
+ x,
+ y);
+ });
+ var scale = function (s) {
+ return A6(matrix,
+ s,
+ 0,
+ 0,
+ s,
+ 0,
+ 0);
+ };
+ var scaleX = function (x) {
+ return A6(matrix,
+ x,
+ 0,
+ 0,
+ 1,
+ 0,
+ 0);
+ };
+ var scaleY = function (y) {
+ return A6(matrix,
+ 1,
+ 0,
+ 0,
+ y,
+ 0,
+ 0);
+ };
+ var identity = $Native$Transform2D.identity;
+ var Transform2D = {ctor: "Transform2D"};
+ _elm.Transform2D.values = {_op: _op
+ ,identity: identity
+ ,matrix: matrix
+ ,multiply: multiply
+ ,rotation: rotation
+ ,translation: translation
+ ,scale: scale
+ ,scaleX: scaleX
+ ,scaleY: scaleY};
+ return _elm.Transform2D.values;
+};
+Elm.Update = Elm.Update || {};
+Elm.Update.make = function (_elm) {
+ "use strict";
+ _elm.Update = _elm.Update || {};
+ if (_elm.Update.values)
+ return _elm.Update.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Update",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Payer = Elm.Model.Payer.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View = Elm.Model.View.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Model$View$SignInView = Elm.Model.View.SignInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Time = Elm.Time.make(_elm),
+ $Update$LoggedIn = Elm.Update.LoggedIn.make(_elm),
+ $Update$SignIn = Elm.Update.SignIn.make(_elm);
+ var updateModel = F2(function (action,
+ model) {
+ switch (action.ctor)
+ {case "GoLoggedInView":
+ return _U.replace([["view"
+ ,$Model$View.LoggedInView(A6($Model$View$LoggedInView.initLoggedInView,
+ action._0,
+ action._1,
+ action._2,
+ action._3,
+ action._4,
+ action._5))]],
+ model);
+ case "GoSignInView":
+ return _U.replace([["view"
+ ,$Model$View.SignInView($Model$View$SignInView.initSignInView)]],
+ model);
+ case "NoOp": return model;
+ case "SignInError":
+ var signInView = _U.replace([["result"
+ ,$Maybe.Just($Result.Err(action._0))]],
+ $Model$View$SignInView.initSignInView);
+ return _U.replace([["view"
+ ,$Model$View.SignInView(signInView)]],
+ model);
+ case "UpdateLoggedIn":
+ var _v11 = model.view;
+ switch (_v11.ctor)
+ {case "LoggedInView":
+ return _U.replace([["view"
+ ,$Model$View.LoggedInView(A3($Update$LoggedIn.updateLoggedIn,
+ model,
+ action._0,
+ _v11._0))]],
+ model);}
+ return model;
+ case "UpdateSignIn":
+ var _v13 = model.view;
+ switch (_v13.ctor)
+ {case "SignInView":
+ return _U.replace([["view"
+ ,$Model$View.SignInView(A2($Update$SignIn.updateSignIn,
+ action._0,
+ _v13._0))]],
+ model);}
+ return model;
+ case "UpdateTime":
+ return _U.replace([["currentTime"
+ ,action._0]],
+ model);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var UpdateLoggedIn = function (a) {
+ return {ctor: "UpdateLoggedIn"
+ ,_0: a};
+ };
+ var GoLoggedInView = F6(function (a,
+ b,
+ c,
+ d,
+ e,
+ f) {
+ return {ctor: "GoLoggedInView"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d
+ ,_4: e
+ ,_5: f};
+ });
+ var UpdateSignIn = function (a) {
+ return {ctor: "UpdateSignIn"
+ ,_0: a};
+ };
+ var SignInError = function (a) {
+ return {ctor: "SignInError"
+ ,_0: a};
+ };
+ var GoSignInView = {ctor: "GoSignInView"};
+ var UpdateTime = function (a) {
+ return {ctor: "UpdateTime"
+ ,_0: a};
+ };
+ var NoOp = {ctor: "NoOp"};
+ var actions = $Signal.mailbox(NoOp);
+ _elm.Update.values = {_op: _op
+ ,actions: actions
+ ,updateModel: updateModel
+ ,NoOp: NoOp
+ ,UpdateTime: UpdateTime
+ ,GoSignInView: GoSignInView
+ ,SignInError: SignInError
+ ,UpdateSignIn: UpdateSignIn
+ ,GoLoggedInView: GoLoggedInView
+ ,UpdateLoggedIn: UpdateLoggedIn};
+ return _elm.Update.values;
+};
+Elm.Update = Elm.Update || {};
+Elm.Update.LoggedIn = Elm.Update.LoggedIn || {};
+Elm.Update.LoggedIn.make = function (_elm) {
+ "use strict";
+ _elm.Update = _elm.Update || {};
+ _elm.Update.LoggedIn = _elm.Update.LoggedIn || {};
+ if (_elm.Update.LoggedIn.values)
+ return _elm.Update.LoggedIn.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Update.LoggedIn",
+ $Basics = Elm.Basics.make(_elm),
+ $Date = Elm.Date.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View$LoggedIn$Add = Elm.Model.View.LoggedIn.Add.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Update$LoggedIn$Account = Elm.Update.LoggedIn.Account.make(_elm),
+ $Update$LoggedIn$Add = Elm.Update.LoggedIn.Add.make(_elm),
+ $Update$LoggedIn$Monthly = Elm.Update.LoggedIn.Monthly.make(_elm);
+ var updateLoggedIn = F3(function (model,
+ action,
+ loggedInView) {
+ switch (action.ctor)
+ {case "AddMonthlyPayment":
+ return _U.replace([["add"
+ ,$Model$View$LoggedIn$Add.initAddPayment($Model$View$LoggedIn$Add.Monthly)]
+ ,["monthly"
+ ,function () {
+ var payment = A5($Model$Payment.Payment,
+ action._0,
+ $Date.fromTime(model.currentTime),
+ action._1,
+ action._2,
+ loggedInView.account.me);
+ return A2($Update$LoggedIn$Monthly.updateMonthly,
+ $Update$LoggedIn$Monthly.AddPayment(payment),
+ loggedInView.monthly);
+ }()]],
+ loggedInView);
+ case "AddPayment":
+ return _U.replace([["payments"
+ ,action._3]
+ ,["currentPage",1]
+ ,["add"
+ ,$Model$View$LoggedIn$Add.initAddPayment($Model$View$LoggedIn$Add.Punctual)]
+ ,["account"
+ ,A2($Update$LoggedIn$Account.updateAccount,
+ A3($Update$LoggedIn$Account.UpdatePayer,
+ action._0,
+ model.currentTime,
+ action._2),
+ loggedInView.account)]
+ ,["paymentsCount"
+ ,loggedInView.paymentsCount + 1]],
+ loggedInView);
+ case "DeletePayment":
+ return _U.replace([["payments"
+ ,action._1]
+ ,["account"
+ ,A2($Update$LoggedIn$Account.updateAccount,
+ A3($Update$LoggedIn$Account.UpdatePayer,
+ action._0.userId,
+ $Date.toTime(action._0.creation),
+ 0 - action._0.cost),
+ loggedInView.account)]
+ ,["paymentsCount"
+ ,loggedInView.paymentsCount - 1]],
+ loggedInView);
+ case "ToggleEdit":
+ return _U.replace([["paymentEdition"
+ ,_U.eq(loggedInView.paymentEdition,
+ $Maybe.Just(action._0)) ? $Maybe.Nothing : $Maybe.Just(action._0)]],
+ loggedInView);
+ case "UpdateAccount":
+ return _U.replace([["account"
+ ,A2($Update$LoggedIn$Account.updateAccount,
+ action._0,
+ loggedInView.account)]],
+ loggedInView);
+ case "UpdateAdd":
+ return _U.replace([["add"
+ ,A2($Update$LoggedIn$Add.updateAddPayment,
+ action._0,
+ loggedInView.add)]],
+ loggedInView);
+ case "UpdateMonthly":
+ return _U.replace([["monthly"
+ ,A2($Update$LoggedIn$Monthly.updateMonthly,
+ action._0,
+ loggedInView.monthly)]],
+ loggedInView);
+ case "UpdatePage":
+ return _U.replace([["currentPage"
+ ,action._0]
+ ,["payments",action._1]],
+ loggedInView);
+ case "UpdatePayments":
+ return _U.replace([["payments"
+ ,action._0]],
+ loggedInView);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var UpdateAccount = function (a) {
+ return {ctor: "UpdateAccount"
+ ,_0: a};
+ };
+ var UpdateMonthly = function (a) {
+ return {ctor: "UpdateMonthly"
+ ,_0: a};
+ };
+ var UpdatePage = F2(function (a,
+ b) {
+ return {ctor: "UpdatePage"
+ ,_0: a
+ ,_1: b};
+ });
+ var DeletePayment = F2(function (a,
+ b) {
+ return {ctor: "DeletePayment"
+ ,_0: a
+ ,_1: b};
+ });
+ var ToggleEdit = function (a) {
+ return {ctor: "ToggleEdit"
+ ,_0: a};
+ };
+ var AddMonthlyPayment = F3(function (a,
+ b,
+ c) {
+ return {ctor: "AddMonthlyPayment"
+ ,_0: a
+ ,_1: b
+ ,_2: c};
+ });
+ var AddPayment = F4(function (a,
+ b,
+ c,
+ d) {
+ return {ctor: "AddPayment"
+ ,_0: a
+ ,_1: b
+ ,_2: c
+ ,_3: d};
+ });
+ var UpdatePayments = function (a) {
+ return {ctor: "UpdatePayments"
+ ,_0: a};
+ };
+ var UpdateAdd = function (a) {
+ return {ctor: "UpdateAdd"
+ ,_0: a};
+ };
+ _elm.Update.LoggedIn.values = {_op: _op
+ ,updateLoggedIn: updateLoggedIn
+ ,UpdateAdd: UpdateAdd
+ ,UpdatePayments: UpdatePayments
+ ,AddPayment: AddPayment
+ ,AddMonthlyPayment: AddMonthlyPayment
+ ,ToggleEdit: ToggleEdit
+ ,DeletePayment: DeletePayment
+ ,UpdatePage: UpdatePage
+ ,UpdateMonthly: UpdateMonthly
+ ,UpdateAccount: UpdateAccount};
+ return _elm.Update.LoggedIn.values;
+};
+Elm.Update = Elm.Update || {};
+Elm.Update.LoggedIn = Elm.Update.LoggedIn || {};
+Elm.Update.LoggedIn.Account = Elm.Update.LoggedIn.Account || {};
+Elm.Update.LoggedIn.Account.make = function (_elm) {
+ "use strict";
+ _elm.Update = _elm.Update || {};
+ _elm.Update.LoggedIn = _elm.Update.LoggedIn || {};
+ _elm.Update.LoggedIn.Account = _elm.Update.LoggedIn.Account || {};
+ if (_elm.Update.LoggedIn.Account.values)
+ return _elm.Update.LoggedIn.Account.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Update.LoggedIn.Account",
+ $Basics = Elm.Basics.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payer = Elm.Model.Payer.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View$LoggedIn$Account = Elm.Model.View.LoggedIn.Account.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Time = Elm.Time.make(_elm),
+ $Utils$Maybe = Elm.Utils.Maybe.make(_elm);
+ var updateAccount = F2(function (action,
+ account) {
+ switch (action.ctor)
+ {case "ToggleDetail":
+ return _U.replace([["visibleDetail"
+ ,$Basics.not(account.visibleDetail)]],
+ account);
+ case "ToggleIncomeEdition":
+ return _U.replace([["incomeEdition"
+ ,$Utils$Maybe.isJust(account.incomeEdition) ? $Maybe.Nothing : $Maybe.Just($Model$View$LoggedIn$Account.initIncomeEdition(A2($Maybe.withDefault,
+ 0,
+ $Model$View$LoggedIn$Account.getCurrentIncome(account))))]],
+ account);
+ case "UpdateEditionError":
+ var _v8 = account.incomeEdition;
+ switch (_v8.ctor)
+ {case "Just":
+ return _U.replace([["incomeEdition"
+ ,$Maybe.Just(_U.replace([["error"
+ ,$Maybe.Just(action._0)]],
+ _v8._0))]],
+ account);
+ case "Nothing": return account;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "UpdateIncome":
+ return _U.replace([["payers"
+ ,A2($Dict.update,
+ account.me,
+ function (mbPayer) {
+ switch (mbPayer.ctor)
+ {case "Just":
+ return $Maybe.Just(_U.replace([["incomes"
+ ,A2($Basics._op["++"],
+ mbPayer._0.incomes,
+ _L.fromArray([{_: {}
+ ,amount: action._1
+ ,creation: action._0}]))]],
+ mbPayer._0));
+ case "Nothing":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ })(account.payers)]
+ ,["incomeEdition"
+ ,$Maybe.Nothing]],
+ account);
+ case "UpdateIncomeEdition":
+ var _v12 = account.incomeEdition;
+ switch (_v12.ctor)
+ {case "Just":
+ return _U.replace([["incomeEdition"
+ ,$Maybe.Just(_U.replace([["income"
+ ,action._0]],
+ _v12._0))]],
+ account);
+ case "Nothing": return account;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "UpdatePayer":
+ return _U.replace([["payers"
+ ,A4($Model$Payer.updatePayers,
+ account.payers,
+ action._0,
+ action._1,
+ action._2)]],
+ account);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var UpdateIncome = F2(function (a,
+ b) {
+ return {ctor: "UpdateIncome"
+ ,_0: a
+ ,_1: b};
+ });
+ var UpdateEditionError = function (a) {
+ return {ctor: "UpdateEditionError"
+ ,_0: a};
+ };
+ var UpdateIncomeEdition = function (a) {
+ return {ctor: "UpdateIncomeEdition"
+ ,_0: a};
+ };
+ var ToggleIncomeEdition = {ctor: "ToggleIncomeEdition"};
+ var UpdatePayer = F3(function (a,
+ b,
+ c) {
+ return {ctor: "UpdatePayer"
+ ,_0: a
+ ,_1: b
+ ,_2: c};
+ });
+ var ToggleDetail = {ctor: "ToggleDetail"};
+ _elm.Update.LoggedIn.Account.values = {_op: _op
+ ,updateAccount: updateAccount
+ ,ToggleDetail: ToggleDetail
+ ,UpdatePayer: UpdatePayer
+ ,ToggleIncomeEdition: ToggleIncomeEdition
+ ,UpdateIncomeEdition: UpdateIncomeEdition
+ ,UpdateEditionError: UpdateEditionError
+ ,UpdateIncome: UpdateIncome};
+ return _elm.Update.LoggedIn.Account.values;
+};
+Elm.Update = Elm.Update || {};
+Elm.Update.LoggedIn = Elm.Update.LoggedIn || {};
+Elm.Update.LoggedIn.Add = Elm.Update.LoggedIn.Add || {};
+Elm.Update.LoggedIn.Add.make = function (_elm) {
+ "use strict";
+ _elm.Update = _elm.Update || {};
+ _elm.Update.LoggedIn = _elm.Update.LoggedIn || {};
+ _elm.Update.LoggedIn.Add = _elm.Update.LoggedIn.Add || {};
+ if (_elm.Update.LoggedIn.Add.values)
+ return _elm.Update.LoggedIn.Add.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Update.LoggedIn.Add",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$View$LoggedIn$Add = Elm.Model.View.LoggedIn.Add.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var updateAddPayment = F2(function (action,
+ addPayment) {
+ switch (action.ctor)
+ {case "AddError":
+ return _U.replace([["nameError"
+ ,action._0]
+ ,["costError",action._1]],
+ addPayment);
+ case "ToggleFrequency":
+ return _U.replace([["frequency"
+ ,_U.eq(addPayment.frequency,
+ $Model$View$LoggedIn$Add.Punctual) ? $Model$View$LoggedIn$Add.Monthly : $Model$View$LoggedIn$Add.Punctual]],
+ addPayment);
+ case "UpdateCost":
+ return _U.replace([["cost"
+ ,action._0]],
+ addPayment);
+ case "UpdateName":
+ return _U.replace([["name"
+ ,action._0]],
+ addPayment);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var ToggleFrequency = {ctor: "ToggleFrequency"};
+ var AddError = F2(function (a,
+ b) {
+ return {ctor: "AddError"
+ ,_0: a
+ ,_1: b};
+ });
+ var UpdateCost = function (a) {
+ return {ctor: "UpdateCost"
+ ,_0: a};
+ };
+ var UpdateName = function (a) {
+ return {ctor: "UpdateName"
+ ,_0: a};
+ };
+ _elm.Update.LoggedIn.Add.values = {_op: _op
+ ,updateAddPayment: updateAddPayment
+ ,UpdateName: UpdateName
+ ,UpdateCost: UpdateCost
+ ,AddError: AddError
+ ,ToggleFrequency: ToggleFrequency};
+ return _elm.Update.LoggedIn.Add.values;
+};
+Elm.Update = Elm.Update || {};
+Elm.Update.LoggedIn = Elm.Update.LoggedIn || {};
+Elm.Update.LoggedIn.Monthly = Elm.Update.LoggedIn.Monthly || {};
+Elm.Update.LoggedIn.Monthly.make = function (_elm) {
+ "use strict";
+ _elm.Update = _elm.Update || {};
+ _elm.Update.LoggedIn = _elm.Update.LoggedIn || {};
+ _elm.Update.LoggedIn.Monthly = _elm.Update.LoggedIn.Monthly || {};
+ if (_elm.Update.LoggedIn.Monthly.values)
+ return _elm.Update.LoggedIn.Monthly.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Update.LoggedIn.Monthly",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$View$LoggedIn$Monthly = Elm.Model.View.LoggedIn.Monthly.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var updateMonthly = F2(function (action,
+ monthly) {
+ switch (action.ctor)
+ {case "AddPayment":
+ return _U.replace([["payments"
+ ,A2($List._op["::"],
+ action._0,
+ monthly.payments)]
+ ,["visibleDetail",true]],
+ monthly);
+ case "DeletePayment":
+ return _U.replace([["payments"
+ ,A2($List.filter,
+ function (payment) {
+ return !_U.eq(payment.id,
+ action._0);
+ },
+ monthly.payments)]],
+ monthly);
+ case "ToggleDetail":
+ return _U.replace([["visibleDetail"
+ ,$Basics.not(monthly.visibleDetail)]],
+ monthly);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var DeletePayment = function (a) {
+ return {ctor: "DeletePayment"
+ ,_0: a};
+ };
+ var AddPayment = function (a) {
+ return {ctor: "AddPayment"
+ ,_0: a};
+ };
+ var ToggleDetail = {ctor: "ToggleDetail"};
+ _elm.Update.LoggedIn.Monthly.values = {_op: _op
+ ,updateMonthly: updateMonthly
+ ,ToggleDetail: ToggleDetail
+ ,AddPayment: AddPayment
+ ,DeletePayment: DeletePayment};
+ return _elm.Update.LoggedIn.Monthly.values;
+};
+Elm.Update = Elm.Update || {};
+Elm.Update.SignIn = Elm.Update.SignIn || {};
+Elm.Update.SignIn.make = function (_elm) {
+ "use strict";
+ _elm.Update = _elm.Update || {};
+ _elm.Update.SignIn = _elm.Update.SignIn || {};
+ if (_elm.Update.SignIn.values)
+ return _elm.Update.SignIn.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Update.SignIn",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$View$SignInView = Elm.Model.View.SignInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var updateSignIn = F2(function (action,
+ signInView) {
+ switch (action.ctor)
+ {case "ErrorLogin":
+ return _U.replace([["result"
+ ,$Maybe.Just($Result.Err(action._0))]],
+ signInView);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var ErrorLogin = function (a) {
+ return {ctor: "ErrorLogin"
+ ,_0: a};
+ };
+ _elm.Update.SignIn.values = {_op: _op
+ ,updateSignIn: updateSignIn
+ ,ErrorLogin: ErrorLogin};
+ return _elm.Update.SignIn.values;
+};
+Elm.Utils = Elm.Utils || {};
+Elm.Utils.Dict = Elm.Utils.Dict || {};
+Elm.Utils.Dict.make = function (_elm) {
+ "use strict";
+ _elm.Utils = _elm.Utils || {};
+ _elm.Utils.Dict = _elm.Utils.Dict || {};
+ if (_elm.Utils.Dict.values)
+ return _elm.Utils.Dict.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Utils.Dict",
+ $Basics = Elm.Basics.make(_elm),
+ $Dict = Elm.Dict.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var onSecond = F2(function (f,
+ tuple) {
+ switch (tuple.ctor)
+ {case "_Tuple2":
+ return {ctor: "_Tuple2"
+ ,_0: tuple._0
+ ,_1: f(tuple._1)};}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var mapValues = function (f) {
+ return function ($) {
+ return $Dict.fromList($List.map(onSecond(f))($Dict.toList($)));
+ };
+ };
+ _elm.Utils.Dict.values = {_op: _op
+ ,mapValues: mapValues};
+ return _elm.Utils.Dict.values;
+};
+Elm.Utils = Elm.Utils || {};
+Elm.Utils.Either = Elm.Utils.Either || {};
+Elm.Utils.Either.make = function (_elm) {
+ "use strict";
+ _elm.Utils = _elm.Utils || {};
+ _elm.Utils.Either = _elm.Utils.Either || {};
+ if (_elm.Utils.Either.values)
+ return _elm.Utils.Either.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Utils.Either",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var toMaybeError = function (result) {
+ switch (result.ctor)
+ {case "Err":
+ return $Maybe.Just(result._0);
+ case "Ok":
+ return $Maybe.Nothing;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ _elm.Utils.Either.values = {_op: _op
+ ,toMaybeError: toMaybeError};
+ return _elm.Utils.Either.values;
+};
+Elm.Utils = Elm.Utils || {};
+Elm.Utils.Maybe = Elm.Utils.Maybe || {};
+Elm.Utils.Maybe.make = function (_elm) {
+ "use strict";
+ _elm.Utils = _elm.Utils || {};
+ _elm.Utils.Maybe = _elm.Utils.Maybe || {};
+ if (_elm.Utils.Maybe.values)
+ return _elm.Utils.Maybe.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Utils.Maybe",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var maybeToList = function (mb) {
+ switch (mb.ctor)
+ {case "Just":
+ return _L.fromArray([mb._0]);
+ case "Nothing":
+ return _L.fromArray([]);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var catMaybes = A2($List.foldr,
+ F2(function (mb,xs) {
+ switch (mb.ctor)
+ {case "Just":
+ return A2($List._op["::"],
+ mb._0,
+ xs);
+ case "Nothing": return xs;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }),
+ _L.fromArray([]));
+ var isJust = function (maybe) {
+ switch (maybe.ctor)
+ {case "Just": return true;
+ case "Nothing": return false;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ _elm.Utils.Maybe.values = {_op: _op
+ ,isJust: isJust
+ ,catMaybes: catMaybes
+ ,maybeToList: maybeToList};
+ return _elm.Utils.Maybe.values;
+};
+Elm.Utils = Elm.Utils || {};
+Elm.Utils.Validation = Elm.Utils.Validation || {};
+Elm.Utils.Validation.make = function (_elm) {
+ "use strict";
+ _elm.Utils = _elm.Utils || {};
+ _elm.Utils.Validation = _elm.Utils.Validation || {};
+ if (_elm.Utils.Validation.values)
+ return _elm.Utils.Validation.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "Utils.Validation",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Reads = Elm.Reads.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm);
+ var validateNumber = F3(function (message,
+ numberForm,
+ str) {
+ var _v0 = $Reads.readInt(str);
+ switch (_v0.ctor)
+ {case "Just":
+ return numberForm(_v0._0) ? $Result.Ok(_v0._0) : $Result.Err(message);
+ case "Nothing":
+ return $Result.Err(message);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var validateNonEmpty = F2(function (message,
+ str) {
+ return $String.isEmpty(str) ? $Result.Err(message) : $Result.Ok(str);
+ });
+ _elm.Utils.Validation.values = {_op: _op
+ ,validateNonEmpty: validateNonEmpty
+ ,validateNumber: validateNumber};
+ return _elm.Utils.Validation.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Date = Elm.View.Date || {};
+Elm.View.Date.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Date = _elm.View.Date || {};
+ if (_elm.View.Date.values)
+ return _elm.View.Date.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Date",
+ $Basics = Elm.Basics.make(_elm),
+ $Date = Elm.Date.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm);
+ var getMonthKey = function (month) {
+ switch (month.ctor)
+ {case "Apr": return "April";
+ case "Aug": return "August";
+ case "Dec": return "December";
+ case "Feb": return "February";
+ case "Jan": return "January";
+ case "Jul": return "July";
+ case "Jun": return "June";
+ case "Mar": return "March";
+ case "May": return "May";
+ case "Nov": return "November";
+ case "Oct": return "October";
+ case "Sep": return "September";}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var getMonthNumber = function (month) {
+ switch (month.ctor)
+ {case "Apr": return 4;
+ case "Aug": return 8;
+ case "Dec": return 12;
+ case "Feb": return 2;
+ case "Jan": return 1;
+ case "Jul": return 7;
+ case "Jun": return 6;
+ case "Mar": return 3;
+ case "May": return 5;
+ case "Nov": return 11;
+ case "Oct": return 10;
+ case "Sep": return 9;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var renderLongDate = F2(function (date,
+ translations) {
+ var params = _L.fromArray([$Basics.toString($Date.day(date))
+ ,A2($Model$Translations.getMessage,
+ getMonthKey($Date.month(date)),
+ translations)
+ ,$Basics.toString($Date.year(date))]);
+ return A3($Model$Translations.getParamMessage,
+ params,
+ "LongDate",
+ translations);
+ });
+ var renderShortDate = F2(function (date,
+ translations) {
+ var params = _L.fromArray([A3($String.pad,
+ 2,
+ _U.chr("0"),
+ $Basics.toString($Date.day(date)))
+ ,A3($String.pad,
+ 2,
+ _U.chr("0"),
+ $Basics.toString(getMonthNumber($Date.month(date))))
+ ,$Basics.toString($Date.year(date))]);
+ return A3($Model$Translations.getParamMessage,
+ params,
+ "ShortDate",
+ translations);
+ });
+ _elm.View.Date.values = {_op: _op
+ ,renderShortDate: renderShortDate
+ ,renderLongDate: renderLongDate};
+ return _elm.View.Date.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Events = Elm.View.Events || {};
+Elm.View.Events.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Events = _elm.View.Events || {};
+ if (_elm.View.Events.values)
+ return _elm.View.Events.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Events",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var onSubmitPrevDefault = F2(function (address,
+ value) {
+ return A4($Html$Events.onWithOptions,
+ "submit",
+ _U.replace([["preventDefault"
+ ,true]],
+ $Html$Events.defaultOptions),
+ $Json$Decode.value,
+ function (_v0) {
+ var _ = _v0;
+ return A2($Signal.message,
+ address,
+ value);
+ });
+ });
+ _elm.View.Events.values = {_op: _op
+ ,onSubmitPrevDefault: onSubmitPrevDefault};
+ return _elm.View.Events.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Expand = Elm.View.Expand || {};
+Elm.View.Expand.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Expand = _elm.View.Expand || {};
+ if (_elm.View.Expand.values)
+ return _elm.View.Expand.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Expand",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $View$Icon = Elm.View.Icon.make(_elm);
+ var chevronIcon = F2(function (expandType,
+ isExpanded) {
+ var _v0 = {ctor: "_Tuple2"
+ ,_0: expandType
+ ,_1: isExpanded};
+ switch (_v0.ctor)
+ {case "_Tuple2":
+ switch (_v0._0.ctor)
+ {case "ExpandDown":
+ switch (_v0._1)
+ {case false:
+ return "chevron-down";
+ case true: return "chevron-up";}
+ break;
+ case "ExpandUp": switch (_v0._1)
+ {case false:
+ return "chevron-up";
+ case true:
+ return "chevron-down";}
+ break;}
+ break;}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var expand = F2(function (expandType,
+ isExpanded) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("expand")]),
+ _L.fromArray([$View$Icon.renderIcon(A2(chevronIcon,
+ expandType,
+ isExpanded))]));
+ });
+ var ExpandDown = {ctor: "ExpandDown"};
+ var ExpandUp = {ctor: "ExpandUp"};
+ _elm.View.Expand.values = {_op: _op
+ ,expand: expand
+ ,ExpandUp: ExpandUp
+ ,ExpandDown: ExpandDown};
+ return _elm.View.Expand.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Header = Elm.View.Header || {};
+Elm.View.Header.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Header = _elm.View.Header || {};
+ if (_elm.View.Header.values)
+ return _elm.View.Header.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Header",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$View = Elm.Model.View.make(_elm),
+ $Persona = Elm.Persona.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $View$Icon = Elm.View.Icon.make(_elm);
+ var renderHeader = function (model) {
+ return A2($Html.header,
+ _L.fromArray([]),
+ _L.fromArray([A2($Html.h1,
+ _L.fromArray([]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "SharedCost",
+ model.translations))]))
+ ,function () {
+ var _v0 = model.view;
+ switch (_v0.ctor)
+ {case "LoadingView":
+ return $Html.text("");
+ case "LoggedInView":
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("icon")
+ ,A2($Html$Events.onClick,
+ $Persona.operations.address,
+ $Persona.SignOut)]),
+ _L.fromArray([$View$Icon.renderIcon("sign-out")]));
+ case "SignInView":
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("icon")
+ ,A2($Html$Events.onClick,
+ $Persona.operations.address,
+ $Persona.SignIn)]),
+ _L.fromArray([$View$Icon.renderIcon("sign-in")]));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()]));
+ };
+ _elm.View.Header.values = {_op: _op
+ ,renderHeader: renderHeader};
+ return _elm.View.Header.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Icon = Elm.View.Icon || {};
+Elm.View.Icon.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Icon = _elm.View.Icon || {};
+ if (_elm.View.Icon.values)
+ return _elm.View.Icon.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Icon",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var renderIcon = function (iconClass) {
+ return A2($Html.i,
+ _L.fromArray([$Html$Attributes.$class(A2($Basics._op["++"],
+ "fa fa-fw fa-",
+ iconClass))]),
+ _L.fromArray([]));
+ };
+ _elm.View.Icon.values = {_op: _op
+ ,renderIcon: renderIcon};
+ return _elm.View.Icon.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Loading = Elm.View.Loading || {};
+Elm.View.Loading.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Loading = _elm.View.Loading || {};
+ if (_elm.View.Loading.values)
+ return _elm.View.Loading.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Loading",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var renderLoading = $Html.text("");
+ _elm.View.Loading.values = {_op: _op
+ ,renderLoading: renderLoading};
+ return _elm.View.Loading.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.LoggedIn = Elm.View.LoggedIn || {};
+Elm.View.LoggedIn.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.LoggedIn = _elm.View.LoggedIn || {};
+ if (_elm.View.LoggedIn.values)
+ return _elm.View.LoggedIn.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.LoggedIn",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $View$LoggedIn$Account = Elm.View.LoggedIn.Account.make(_elm),
+ $View$LoggedIn$Add = Elm.View.LoggedIn.Add.make(_elm),
+ $View$LoggedIn$Monthly = Elm.View.LoggedIn.Monthly.make(_elm),
+ $View$LoggedIn$Paging = Elm.View.LoggedIn.Paging.make(_elm),
+ $View$LoggedIn$Table = Elm.View.LoggedIn.Table.make(_elm);
+ var renderLoggedIn = F2(function (model,
+ loggedInView) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("loggedIn")]),
+ _L.fromArray([A2($View$LoggedIn$Add.addPayment,
+ model,
+ loggedInView)
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("expandables")]),
+ _L.fromArray([A2($View$LoggedIn$Account.account,
+ model,
+ loggedInView)
+ ,A2($View$LoggedIn$Monthly.monthlyPayments,
+ model,
+ loggedInView)]))
+ ,A2($View$LoggedIn$Table.paymentsTable,
+ model,
+ loggedInView)
+ ,$View$LoggedIn$Paging.paymentsPaging(loggedInView)]));
+ });
+ _elm.View.LoggedIn.values = {_op: _op
+ ,renderLoggedIn: renderLoggedIn};
+ return _elm.View.LoggedIn.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.LoggedIn = Elm.View.LoggedIn || {};
+Elm.View.LoggedIn.Account = Elm.View.LoggedIn.Account || {};
+Elm.View.LoggedIn.Account.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.LoggedIn = _elm.View.LoggedIn || {};
+ _elm.View.LoggedIn.Account = _elm.View.LoggedIn.Account || {};
+ if (_elm.View.LoggedIn.Account.values)
+ return _elm.View.LoggedIn.Account.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.LoggedIn.Account",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Payer = Elm.Model.Payer.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View$LoggedIn$Account = Elm.Model.View.LoggedIn.Account.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Update = Elm.Update.make(_elm),
+ $Update$LoggedIn = Elm.Update.LoggedIn.make(_elm),
+ $Update$LoggedIn$Account = Elm.Update.LoggedIn.Account.make(_elm),
+ $View$Events = Elm.View.Events.make(_elm),
+ $View$Expand = Elm.View.Expand.make(_elm),
+ $View$Price = Elm.View.Price.make(_elm);
+ var toggleIncomeEdition = F2(function (className,
+ name) {
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.type$("button")
+ ,$Html$Attributes.$class(className)
+ ,A2($Html$Events.onClick,
+ $Update.actions.address,
+ function ($) {
+ return $Update.UpdateLoggedIn($Update$LoggedIn.UpdateAccount($));
+ }($Update$LoggedIn$Account.ToggleIncomeEdition))]),
+ _L.fromArray([$Html.text(name)]));
+ });
+ var incomeEdition = F3(function (model,
+ account,
+ edition) {
+ return A2($Html.form,
+ _L.fromArray([function () {
+ var _v0 = A2($Model$View$LoggedIn$Account.validateIncome,
+ edition.income,
+ model.translations);
+ switch (_v0.ctor)
+ {case "Err":
+ return A2($View$Events.onSubmitPrevDefault,
+ $Update.actions.address,
+ function ($) {
+ return $Update.UpdateLoggedIn($Update$LoggedIn.UpdateAccount($Update$LoggedIn$Account.UpdateEditionError($)));
+ }(_v0._0));
+ case "Ok":
+ return A2($View$Events.onSubmitPrevDefault,
+ $ServerCommunication.serverCommunications.address,
+ A2($ServerCommunication.SetIncome,
+ model.currentTime,
+ _v0._0));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()
+ ,$Html$Attributes.$class("income")]),
+ _L.fromArray([A2($Html.label,
+ _L.fromArray([$Html$Attributes.$for("incomeInput")]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "NewIncome",
+ model.translations))]))
+ ,A2($Html.input,
+ _L.fromArray([$Html$Attributes.id("incomeInput")
+ ,$Html$Attributes.value(edition.income)
+ ,A3($Html$Events.on,
+ "input",
+ $Html$Events.targetValue,
+ function ($) {
+ return $Signal.message($Update.actions.address)($Update.UpdateLoggedIn($Update$LoggedIn.UpdateAccount($Update$LoggedIn$Account.UpdateIncomeEdition($))));
+ })
+ ,$Html$Attributes.maxlength(10)]),
+ _L.fromArray([]))
+ ,A2($Html.button,
+ _L.fromArray([$Html$Attributes.type$("submit")
+ ,$Html$Attributes.$class("validateIncomeEdition")]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "Validate",
+ model.translations))]))
+ ,A2(toggleIncomeEdition,
+ "undoIncomeEdition",
+ A2($Model$Translations.getMessage,
+ "Undo",
+ model.translations))
+ ,function () {
+ var _v3 = edition.error;
+ switch (_v3.ctor)
+ {case "Just":
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("error")]),
+ _L.fromArray([$Html.text(_v3._0)]));
+ case "Nothing":
+ return $Html.text("");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()]));
+ });
+ var incomeRead = F2(function (model,
+ account) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("income")]),
+ _L.fromArray([function () {
+ var _v5 = $Model$View$LoggedIn$Account.getCurrentIncome(account);
+ switch (_v5.ctor)
+ {case "Just":
+ return $Html.text(A3($Model$Translations.getParamMessage,
+ _L.fromArray([A2($View$Price.price,
+ model,
+ _v5._0)]),
+ "Income",
+ model.translations));
+ case "Nothing":
+ return $Html.text(A2($Model$Translations.getMessage,
+ "NoIncome",
+ model.translations));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()
+ ,A2(toggleIncomeEdition,
+ "editIncomeEdition",
+ A2($Model$Translations.getMessage,
+ "Edit",
+ model.translations))]));
+ });
+ var income = F2(function (model,
+ account) {
+ var _v7 = account.incomeEdition;
+ switch (_v7.ctor)
+ {case "Just":
+ return A3(incomeEdition,
+ model,
+ account,
+ _v7._0);
+ case "Nothing":
+ return A2(incomeRead,
+ model,
+ account);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var exceedingPayer = F3(function (model,
+ loggedInView,
+ payer) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("exceedingPayer")]),
+ _L.fromArray([A2($Html.span,
+ _L.fromArray([$Html$Attributes.$class("userName")]),
+ _L.fromArray([$Html.text($Maybe.withDefault("−")($Model$User.getUserName(loggedInView.users)(payer.userId)))]))
+ ,A2($Html.span,
+ _L.fromArray([$Html$Attributes.$class("amount")]),
+ _L.fromArray([$Html.text(A2($Basics._op["++"],
+ "+ ",
+ A2($View$Price.price,
+ model,
+ payer.amount)))]))]));
+ });
+ var exceedingPayers = F2(function (model,
+ loggedInView) {
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("header")
+ ,A2($Html$Events.onClick,
+ $Update.actions.address,
+ function ($) {
+ return $Update.UpdateLoggedIn($Update$LoggedIn.UpdateAccount($));
+ }($Update$LoggedIn$Account.ToggleDetail))]),
+ A2($Basics._op["++"],
+ A2($List.map,
+ A2(exceedingPayer,
+ model,
+ loggedInView),
+ A2($Model$Payer.getOrderedExceedingPayers,
+ model.currentTime,
+ loggedInView.account.payers)),
+ _L.fromArray([A2($View$Expand.expand,
+ $View$Expand.ExpandDown,
+ loggedInView.account.visibleDetail)])));
+ });
+ var account = F2(function (model,
+ loggedInView) {
+ var account = loggedInView.account;
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "account"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "detail"
+ ,_1: account.visibleDetail}]))]),
+ _L.fromArray([A2(exceedingPayers,
+ model,
+ loggedInView)
+ ,account.visibleDetail ? A2(income,
+ model,
+ account) : $Html.text("")]));
+ });
+ _elm.View.LoggedIn.Account.values = {_op: _op
+ ,account: account};
+ return _elm.View.LoggedIn.Account.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.LoggedIn = Elm.View.LoggedIn || {};
+Elm.View.LoggedIn.Add = Elm.View.LoggedIn.Add || {};
+Elm.View.LoggedIn.Add.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.LoggedIn = _elm.View.LoggedIn || {};
+ _elm.View.LoggedIn.Add = _elm.View.LoggedIn.Add || {};
+ if (_elm.View.LoggedIn.Add.values)
+ return _elm.View.LoggedIn.Add.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.LoggedIn.Add",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$View$LoggedIn$Add = Elm.Model.View.LoggedIn.Add.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Update = Elm.Update.make(_elm),
+ $Update$LoggedIn = Elm.Update.LoggedIn.make(_elm),
+ $Update$LoggedIn$Add = Elm.Update.LoggedIn.Add.make(_elm),
+ $Utils$Either = Elm.Utils.Either.make(_elm),
+ $Utils$Maybe = Elm.Utils.Maybe.make(_elm),
+ $View$Events = Elm.View.Events.make(_elm),
+ $View$Icon = Elm.View.Icon.make(_elm);
+ var paymentFrequency = F2(function (model,
+ addPayment) {
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.type$("button")
+ ,$Html$Attributes.$class("frequency")
+ ,A2($Html$Events.onClick,
+ $Update.actions.address,
+ function ($) {
+ return $Update.UpdateLoggedIn($Update$LoggedIn.UpdateAdd($));
+ }($Update$LoggedIn$Add.ToggleFrequency))]),
+ _L.fromArray([A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "punctual"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "selected"
+ ,_1: _U.eq(addPayment.frequency,
+ $Model$View$LoggedIn$Add.Punctual)}]))]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "Punctual",
+ model.translations))]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "monthly"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "selected"
+ ,_1: _U.eq(addPayment.frequency,
+ $Model$View$LoggedIn$Add.Monthly)}]))]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "Monthly",
+ model.translations))]))]));
+ });
+ var addPaymentCost = F2(function (model,
+ addPayment) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "cost"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "error"
+ ,_1: $Utils$Maybe.isJust(addPayment.costError)}]))]),
+ _L.fromArray([A2($Html.input,
+ _L.fromArray([$Html$Attributes.id("costInput")
+ ,$Html$Attributes.value(addPayment.cost)
+ ,A3($Html$Events.on,
+ "input",
+ $Html$Events.targetValue,
+ function ($) {
+ return $Signal.message($Update.actions.address)($Update.UpdateLoggedIn($Update$LoggedIn.UpdateAdd($Update$LoggedIn$Add.UpdateCost($))));
+ })
+ ,$Html$Attributes.maxlength(7)]),
+ _L.fromArray([]))
+ ,A2($Html.label,
+ _L.fromArray([$Html$Attributes.$for("costInput")]),
+ _L.fromArray([$Html.text(model.config.currency)]))
+ ,function () {
+ var _v0 = addPayment.costError;
+ switch (_v0.ctor)
+ {case "Just":
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("errorMessage")]),
+ _L.fromArray([$Html.text(_v0._0)]));
+ case "Nothing":
+ return $Html.text("");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()]));
+ });
+ var addPaymentName = function (addPayment) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "name"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "error"
+ ,_1: $Utils$Maybe.isJust(addPayment.nameError)}]))]),
+ _L.fromArray([A2($Html.input,
+ _L.fromArray([$Html$Attributes.id("nameInput")
+ ,$Html$Attributes.value(addPayment.name)
+ ,A3($Html$Events.on,
+ "input",
+ $Html$Events.targetValue,
+ function ($) {
+ return $Signal.message($Update.actions.address)($Update.UpdateLoggedIn($Update$LoggedIn.UpdateAdd($Update$LoggedIn$Add.UpdateName($))));
+ })
+ ,$Html$Attributes.maxlength(20)]),
+ _L.fromArray([]))
+ ,A2($Html.label,
+ _L.fromArray([$Html$Attributes.$for("nameInput")]),
+ _L.fromArray([$View$Icon.renderIcon("shopping-cart")]))
+ ,function () {
+ var _v2 = addPayment.nameError;
+ switch (_v2.ctor)
+ {case "Just":
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("errorMessage")]),
+ _L.fromArray([$Html.text(_v2._0)]));
+ case "Nothing":
+ return $Html.text("");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()]));
+ };
+ var addPayment = F2(function (model,
+ loggedInView) {
+ return A2($Html.form,
+ _L.fromArray([function () {
+ var _v4 = {ctor: "_Tuple2"
+ ,_0: A2($Model$View$LoggedIn$Add.validateName,
+ loggedInView.add.name,
+ model.translations)
+ ,_1: A2($Model$View$LoggedIn$Add.validateCost,
+ loggedInView.add.cost,
+ model.translations)};
+ switch (_v4.ctor)
+ {case "_Tuple2":
+ switch (_v4._0.ctor)
+ {case "Ok": switch (_v4._1.ctor)
+ {case "Ok":
+ var action = function () {
+ var _v9 = loggedInView.add.frequency;
+ switch (_v9.ctor)
+ {case "Monthly":
+ return A2($ServerCommunication.AddMonthlyPayment,
+ _v4._0._0,
+ _v4._1._0);
+ case "Punctual":
+ return A3($ServerCommunication.AddPayment,
+ loggedInView.account.me,
+ _v4._0._0,
+ _v4._1._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }();
+ return A2($View$Events.onSubmitPrevDefault,
+ $ServerCommunication.serverCommunications.address,
+ action);}
+ break;}
+ return A2($View$Events.onSubmitPrevDefault,
+ $Update.actions.address,
+ $Update.UpdateLoggedIn($Update$LoggedIn.UpdateAdd(A2($Update$LoggedIn$Add.AddError,
+ $Utils$Either.toMaybeError(_v4._0),
+ $Utils$Either.toMaybeError(_v4._1)))));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ }()
+ ,$Html$Attributes.$class("addPayment")]),
+ _L.fromArray([addPaymentName(loggedInView.add)
+ ,A2(addPaymentCost,
+ model,
+ loggedInView.add)
+ ,A2(paymentFrequency,
+ model,
+ loggedInView.add)
+ ,A2($Html.button,
+ _L.fromArray([$Html$Attributes.type$("submit")
+ ,$Html$Attributes.$class("add")]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "Add",
+ model.translations))]))]));
+ });
+ _elm.View.LoggedIn.Add.values = {_op: _op
+ ,addPayment: addPayment};
+ return _elm.View.LoggedIn.Add.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.LoggedIn = Elm.View.LoggedIn || {};
+Elm.View.LoggedIn.Monthly = Elm.View.LoggedIn.Monthly || {};
+Elm.View.LoggedIn.Monthly.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.LoggedIn = _elm.View.LoggedIn || {};
+ _elm.View.LoggedIn.Monthly = _elm.View.LoggedIn.Monthly || {};
+ if (_elm.View.LoggedIn.Monthly.values)
+ return _elm.View.LoggedIn.Monthly.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.LoggedIn.Monthly",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$View$LoggedIn$Monthly = Elm.Model.View.LoggedIn.Monthly.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm),
+ $Update = Elm.Update.make(_elm),
+ $Update$LoggedIn = Elm.Update.LoggedIn.make(_elm),
+ $Update$LoggedIn$Monthly = Elm.Update.LoggedIn.Monthly.make(_elm),
+ $View$Expand = Elm.View.Expand.make(_elm),
+ $View$Icon = Elm.View.Icon.make(_elm),
+ $View$Price = Elm.View.Price.make(_elm);
+ var paymentLine = F3(function (model,
+ loggedInView,
+ payment) {
+ return A2($Html.a,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "row"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "edition"
+ ,_1: _U.eq(loggedInView.paymentEdition,
+ $Maybe.Just(payment.id))}]))
+ ,A2($Html$Events.onClick,
+ $Update.actions.address,
+ $Update.UpdateLoggedIn($Update$LoggedIn.ToggleEdit(payment.id)))]),
+ _L.fromArray([A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell category")]),
+ _L.fromArray([$Html.text(payment.name)]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "cell cost"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "refund"
+ ,_1: _U.cmp(payment.cost,
+ 0) < 0}]))]),
+ _L.fromArray([$Html.text(A2($View$Price.price,
+ model,
+ payment.cost))]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell delete")
+ ,A2($Html$Events.onClick,
+ $ServerCommunication.serverCommunications.address,
+ $ServerCommunication.DeleteMonthlyPayment(payment.id))]),
+ _L.fromArray([A2($Html.button,
+ _L.fromArray([]),
+ _L.fromArray([$View$Icon.renderIcon("times")]))]))]));
+ });
+ var paymentsTable = F3(function (model,
+ loggedInView,
+ monthly) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("table")]),
+ $List.map(A2(paymentLine,
+ model,
+ loggedInView))($List.sortBy(function ($) {
+ return $String.toLower(function (_) {
+ return _.name;
+ }($));
+ })(monthly.payments)));
+ });
+ var monthlyCount = F2(function (model,
+ monthly) {
+ var total = function ($) {
+ return $List.sum($List.map(function (_) {
+ return _.cost;
+ })($));
+ }(monthly.payments);
+ var count = $List.length(monthly.payments);
+ var key = _U.cmp(count,
+ 1) > 0 ? "PluralMonthlyCount" : "SingularMonthlyCount";
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("header")
+ ,A2($Html$Events.onClick,
+ $Update.actions.address,
+ function ($) {
+ return $Update.UpdateLoggedIn($Update$LoggedIn.UpdateMonthly($));
+ }($Update$LoggedIn$Monthly.ToggleDetail))]),
+ _L.fromArray([$Html.text(A3($Model$Translations.getParamMessage,
+ _L.fromArray([$Basics.toString(count)
+ ,A2($View$Price.price,
+ model,
+ total)]),
+ key,
+ model.translations))
+ ,A2($View$Expand.expand,
+ $View$Expand.ExpandDown,
+ monthly.visibleDetail)]));
+ });
+ var monthlyPayments = F2(function (model,
+ loggedInView) {
+ var monthly = loggedInView.monthly;
+ return _U.eq($List.length(monthly.payments),
+ 0) ? $Html.text("") : A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "monthlyPayments"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "detail"
+ ,_1: monthly.visibleDetail}]))]),
+ _L.fromArray([A2(monthlyCount,
+ model,
+ monthly)
+ ,monthly.visibleDetail ? A3(paymentsTable,
+ model,
+ loggedInView,
+ monthly) : $Html.text("")]));
+ });
+ _elm.View.LoggedIn.Monthly.values = {_op: _op
+ ,monthlyPayments: monthlyPayments};
+ return _elm.View.LoggedIn.Monthly.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.LoggedIn = Elm.View.LoggedIn || {};
+Elm.View.LoggedIn.Paging = Elm.View.LoggedIn.Paging || {};
+Elm.View.LoggedIn.Paging.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.LoggedIn = _elm.View.LoggedIn || {};
+ _elm.View.LoggedIn.Paging = _elm.View.LoggedIn.Paging || {};
+ if (_elm.View.LoggedIn.Paging.values)
+ return _elm.View.LoggedIn.Paging.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.LoggedIn.Paging",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $View$Icon = Elm.View.Icon.make(_elm);
+ var paymentsPage = F2(function (loggedInView,
+ page) {
+ var onCurrentPage = _U.eq(page,
+ loggedInView.currentPage);
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "page"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "current"
+ ,_1: onCurrentPage}]))
+ ,$Html$Events.onClick($ServerCommunication.serverCommunications.address)(onCurrentPage ? $ServerCommunication.NoCommunication : $ServerCommunication.UpdatePage(page))]),
+ _L.fromArray([$Html.text($Basics.toString(page))]));
+ });
+ var lastPage = function (maxPage) {
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("page")
+ ,A2($Html$Events.onClick,
+ $ServerCommunication.serverCommunications.address,
+ $ServerCommunication.UpdatePage(maxPage))]),
+ _L.fromArray([$View$Icon.renderIcon("fast-forward")]));
+ };
+ var nextPage = function (loggedInView) {
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("page")
+ ,A2($Html$Events.onClick,
+ $ServerCommunication.serverCommunications.address,
+ $ServerCommunication.UpdatePage(loggedInView.currentPage + 1))]),
+ _L.fromArray([$View$Icon.renderIcon("forward")]));
+ };
+ var previousPage = function (loggedInView) {
+ return A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("page")
+ ,A2($Html$Events.onClick,
+ $ServerCommunication.serverCommunications.address,
+ $ServerCommunication.UpdatePage(loggedInView.currentPage - 1))]),
+ _L.fromArray([$View$Icon.renderIcon("backward")]));
+ };
+ var firstPage = A2($Html.button,
+ _L.fromArray([$Html$Attributes.$class("page")
+ ,A2($Html$Events.onClick,
+ $ServerCommunication.serverCommunications.address,
+ $ServerCommunication.UpdatePage(1))]),
+ _L.fromArray([$View$Icon.renderIcon("fast-backward")]));
+ var showedPages = 5;
+ var truncatePages = F2(function (currentPage,
+ pages) {
+ var showedRightPages = $Basics.floor(($Basics.toFloat(showedPages) - 1) / 2);
+ var showedLeftPages = $Basics.ceiling(($Basics.toFloat(showedPages) - 1) / 2);
+ var totalPages = $List.length(pages);
+ var truncatedPages = _U.cmp(currentPage,
+ showedLeftPages) < 0 ? _L.range(1,
+ showedPages) : _U.cmp(currentPage,
+ totalPages - showedRightPages) > 0 ? _L.range(totalPages - showedPages,
+ totalPages) : _L.range(currentPage - showedLeftPages,
+ currentPage + showedRightPages);
+ return A2($List.filter,
+ A2($Basics.flip,
+ $List.member,
+ pages),
+ truncatedPages);
+ });
+ var paymentsPaging = function (loggedInView) {
+ var maxPage = $Basics.ceiling($Basics.toFloat(loggedInView.paymentsCount) / $Basics.toFloat($Model$Payment.perPage));
+ var pages = A2(truncatePages,
+ loggedInView.currentPage,
+ _L.range(1,maxPage));
+ return _U.eq(maxPage,
+ 1) ? $Html.text("") : A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("pages")]),
+ A2($Basics._op["++"],
+ _U.cmp(loggedInView.currentPage,
+ 1) > 0 ? _L.fromArray([firstPage
+ ,previousPage(loggedInView)]) : _L.fromArray([]),
+ A2($Basics._op["++"],
+ A2($List.map,
+ paymentsPage(loggedInView),
+ pages),
+ _U.cmp(loggedInView.currentPage,
+ maxPage) < 0 ? _L.fromArray([nextPage(loggedInView)
+ ,lastPage(maxPage)]) : _L.fromArray([]))));
+ };
+ _elm.View.LoggedIn.Paging.values = {_op: _op
+ ,paymentsPaging: paymentsPaging};
+ return _elm.View.LoggedIn.Paging.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.LoggedIn = Elm.View.LoggedIn || {};
+Elm.View.LoggedIn.Table = Elm.View.LoggedIn.Table || {};
+Elm.View.LoggedIn.Table.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.LoggedIn = _elm.View.LoggedIn || {};
+ _elm.View.LoggedIn.Table = _elm.View.LoggedIn.Table || {};
+ if (_elm.View.LoggedIn.Table.values)
+ return _elm.View.LoggedIn.Table.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.LoggedIn.Table",
+ $Basics = Elm.Basics.make(_elm),
+ $Date = Elm.Date.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $Html$Events = Elm.Html.Events.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Payment = Elm.Model.Payment.make(_elm),
+ $Model$User = Elm.Model.User.make(_elm),
+ $Model$View$LoggedInView = Elm.Model.View.LoggedInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $ServerCommunication = Elm.ServerCommunication.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $Update = Elm.Update.make(_elm),
+ $Update$LoggedIn = Elm.Update.LoggedIn.make(_elm),
+ $View$Date = Elm.View.Date.make(_elm),
+ $View$Icon = Elm.View.Icon.make(_elm),
+ $View$Price = Elm.View.Price.make(_elm);
+ var paymentLine = F3(function (model,
+ loggedInView,
+ payment) {
+ return A2($Html.a,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "row"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "edition"
+ ,_1: _U.eq(loggedInView.paymentEdition,
+ $Maybe.Just(payment.id))}]))
+ ,A2($Html$Events.onClick,
+ $Update.actions.address,
+ $Update.UpdateLoggedIn($Update$LoggedIn.ToggleEdit(payment.id)))]),
+ _L.fromArray([A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell category")]),
+ _L.fromArray([$Html.text(payment.name)]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.classList(_L.fromArray([{ctor: "_Tuple2"
+ ,_0: "cell cost"
+ ,_1: true}
+ ,{ctor: "_Tuple2"
+ ,_0: "refund"
+ ,_1: _U.cmp(payment.cost,
+ 0) < 0}]))]),
+ _L.fromArray([$Html.text(A2($View$Price.price,
+ model,
+ payment.cost))]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell user")]),
+ _L.fromArray([$Html.text($Maybe.withDefault("−")($Model$User.getUserName(loggedInView.users)(payment.userId)))]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell date")]),
+ _L.fromArray([A2($Html.span,
+ _L.fromArray([$Html$Attributes.$class("shortDate")]),
+ _L.fromArray([$Html.text(A2($View$Date.renderShortDate,
+ payment.creation,
+ model.translations))]))
+ ,A2($Html.span,
+ _L.fromArray([$Html$Attributes.$class("longDate")]),
+ _L.fromArray([$Html.text(A2($View$Date.renderLongDate,
+ payment.creation,
+ model.translations))]))]))
+ ,_U.eq(loggedInView.account.me,
+ payment.userId) ? A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell delete")]),
+ _L.fromArray([A2($Html.button,
+ _L.fromArray([A2($Html$Events.onClick,
+ $ServerCommunication.serverCommunications.address,
+ A2($ServerCommunication.DeletePayment,
+ payment,
+ loggedInView.currentPage))]),
+ _L.fromArray([$View$Icon.renderIcon("times")]))])) : A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell")]),
+ _L.fromArray([]))]));
+ });
+ var paymentLines = F2(function (model,
+ loggedInView) {
+ return $List.map(A2(paymentLine,
+ model,
+ loggedInView))($List.reverse($List.sortBy(function ($) {
+ return $Date.toTime(function (_) {
+ return _.creation;
+ }($));
+ })(loggedInView.payments)));
+ });
+ var headerLine = function (model) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("header")]),
+ _L.fromArray([A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell category")]),
+ _L.fromArray([$View$Icon.renderIcon("shopping-cart")]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell cost")]),
+ _L.fromArray([$Html.text(model.config.currency)]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell user")]),
+ _L.fromArray([$View$Icon.renderIcon("user")]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell date")]),
+ _L.fromArray([$View$Icon.renderIcon("calendar")]))
+ ,A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("cell")]),
+ _L.fromArray([]))]));
+ };
+ var paymentsTable = F2(function (model,
+ loggedInView) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("table")]),
+ A2($List._op["::"],
+ headerLine(model),
+ A2(paymentLines,
+ model,
+ loggedInView)));
+ });
+ _elm.View.LoggedIn.Table.values = {_op: _op
+ ,paymentsTable: paymentsTable};
+ return _elm.View.LoggedIn.Table.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Page = Elm.View.Page || {};
+Elm.View.Page.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Page = _elm.View.Page || {};
+ if (_elm.View.Page.values)
+ return _elm.View.Page.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Page",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$View = Elm.Model.View.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $View$Header = Elm.View.Header.make(_elm),
+ $View$Loading = Elm.View.Loading.make(_elm),
+ $View$LoggedIn = Elm.View.LoggedIn.make(_elm),
+ $View$SignIn = Elm.View.SignIn.make(_elm);
+ var renderMain = function (model) {
+ var _v0 = model.view;
+ switch (_v0.ctor)
+ {case "LoadingView":
+ return $View$Loading.renderLoading;
+ case "LoggedInView":
+ return A2($View$LoggedIn.renderLoggedIn,
+ model,
+ _v0._0);
+ case "SignInView":
+ return A2($View$SignIn.renderSignIn,
+ model,
+ _v0._0);}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ };
+ var renderPage = function (model) {
+ return A2($Html.div,
+ _L.fromArray([]),
+ _L.fromArray([$View$Header.renderHeader(model)
+ ,renderMain(model)]));
+ };
+ _elm.View.Page.values = {_op: _op
+ ,renderPage: renderPage};
+ return _elm.View.Page.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.Price = Elm.View.Price || {};
+Elm.View.Price.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.Price = _elm.View.Price || {};
+ if (_elm.View.Price.values)
+ return _elm.View.Price.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.Price",
+ $Basics = Elm.Basics.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm),
+ $String = Elm.String.make(_elm);
+ var group = F2(function (n,xs) {
+ if (_U.cmp($List.length(xs),
+ n) < 1)
+ return _L.fromArray([xs]);
+ else {
+ var drop = A2($List.drop,
+ n,
+ xs);
+ var take = A2($List.take,n,xs);
+ return A2($List._op["::"],
+ take,
+ A2(group,n,drop));
+ }
+ });
+ var formatInt = function (n) {
+ return $String.append(_U.cmp(n,
+ 0) < 0 ? "-" : "")($String.fromList($List.reverse($List.concat($List.intersperse(_L.fromArray([_U.chr(" ")]))(group(3)($List.reverse($String.toList($Basics.toString($Basics.abs(n))))))))));
+ };
+ var price = F2(function (model,
+ amount) {
+ return A2($Basics._op["++"],
+ formatInt(amount),
+ A2($Basics._op["++"],
+ " ",
+ model.config.currency));
+ });
+ _elm.View.Price.values = {_op: _op
+ ,price: price};
+ return _elm.View.Price.values;
+};
+Elm.View = Elm.View || {};
+Elm.View.SignIn = Elm.View.SignIn || {};
+Elm.View.SignIn.make = function (_elm) {
+ "use strict";
+ _elm.View = _elm.View || {};
+ _elm.View.SignIn = _elm.View.SignIn || {};
+ if (_elm.View.SignIn.values)
+ return _elm.View.SignIn.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "View.SignIn",
+ $Basics = Elm.Basics.make(_elm),
+ $Html = Elm.Html.make(_elm),
+ $Html$Attributes = Elm.Html.Attributes.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Model = Elm.Model.make(_elm),
+ $Model$Translations = Elm.Model.Translations.make(_elm),
+ $Model$View$SignInView = Elm.Model.View.SignInView.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var signInResult = F2(function (model,
+ signInView) {
+ var _v0 = signInView.result;
+ switch (_v0.ctor)
+ {case "Just":
+ switch (_v0._0.ctor)
+ {case "Err":
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("error")]),
+ _L.fromArray([$Html.text(_v0._0._0)]));
+ case "Ok": return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("success")]),
+ _L.fromArray([$Html.text(A2($Model$Translations.getMessage,
+ "SignInEmailSent",
+ model.translations))]));}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ case "Nothing":
+ return $Html.text("");}
+ _U.badCase($moduleName,
+ "bugs in reporting the exact location right now");
+ });
+ var renderSignIn = F2(function (model,
+ signInView) {
+ return A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("signIn")]),
+ _L.fromArray([A2($Html.div,
+ _L.fromArray([$Html$Attributes.$class("result")]),
+ _L.fromArray([A2(signInResult,
+ model,
+ signInView)]))]));
+ });
+ _elm.View.SignIn.values = {_op: _op
+ ,renderSignIn: renderSignIn};
+ return _elm.View.SignIn.values;
+};
+Elm.VirtualDom = Elm.VirtualDom || {};
+Elm.VirtualDom.make = function (_elm) {
+ "use strict";
+ _elm.VirtualDom = _elm.VirtualDom || {};
+ if (_elm.VirtualDom.values)
+ return _elm.VirtualDom.values;
+ var _op = {},
+ _N = Elm.Native,
+ _U = _N.Utils.make(_elm),
+ _L = _N.List.make(_elm),
+ $moduleName = "VirtualDom",
+ $Basics = Elm.Basics.make(_elm),
+ $Graphics$Element = Elm.Graphics.Element.make(_elm),
+ $Json$Decode = Elm.Json.Decode.make(_elm),
+ $List = Elm.List.make(_elm),
+ $Maybe = Elm.Maybe.make(_elm),
+ $Native$VirtualDom = Elm.Native.VirtualDom.make(_elm),
+ $Result = Elm.Result.make(_elm),
+ $Signal = Elm.Signal.make(_elm);
+ var lazy3 = $Native$VirtualDom.lazy3;
+ var lazy2 = $Native$VirtualDom.lazy2;
+ var lazy = $Native$VirtualDom.lazy;
+ var defaultOptions = {_: {}
+ ,preventDefault: false
+ ,stopPropagation: false};
+ var Options = F2(function (a,
+ b) {
+ return {_: {}
+ ,preventDefault: b
+ ,stopPropagation: a};
+ });
+ var onWithOptions = $Native$VirtualDom.on;
+ var on = F3(function (eventName,
+ decoder,
+ toMessage) {
+ return A4($Native$VirtualDom.on,
+ eventName,
+ defaultOptions,
+ decoder,
+ toMessage);
+ });
+ var attribute = $Native$VirtualDom.attribute;
+ var property = $Native$VirtualDom.property;
+ var Property = {ctor: "Property"};
+ var fromElement = $Native$VirtualDom.fromElement;
+ var toElement = $Native$VirtualDom.toElement;
+ var text = $Native$VirtualDom.text;
+ var node = $Native$VirtualDom.node;
+ var Node = {ctor: "Node"};
+ _elm.VirtualDom.values = {_op: _op
+ ,text: text
+ ,node: node
+ ,toElement: toElement
+ ,fromElement: fromElement
+ ,property: property
+ ,attribute: attribute
+ ,on: on
+ ,onWithOptions: onWithOptions
+ ,defaultOptions: defaultOptions
+ ,lazy: lazy
+ ,lazy2: lazy2
+ ,lazy3: lazy3
+ ,Options: Options};
+ return _elm.VirtualDom.values;
+};
diff --git a/public/javascripts/elmLauncher.js b/public/javascripts/elmLauncher.js
deleted file mode 100644
index bdcb479..0000000
--- a/public/javascripts/elmLauncher.js
+++ /dev/null
@@ -1,13 +0,0 @@
-Elm.fullscreen(Elm.Main, {
- signInError: getParameterByName('signInError'),
- initialTime: new Date().getTime(),
- translations: document.getElementById('messages').innerHTML,
- config: document.getElementById('config').innerHTML
-});
-
-function getParameterByName(name) {
- name = name.replace(/[\[]/, "\\[").replace(/[\]]/, "\\]");
- var regex = new RegExp("[\\?&]" + name + "=([^&#]*)"),
- results = regex.exec(location.search);
- return results && decodeURIComponent(results[1].replace(/\+/g, " "));
-}
diff --git a/public/javascripts/main.js b/public/javascripts/main.js
new file mode 100644
index 0000000..12593e6
--- /dev/null
+++ b/public/javascripts/main.js
@@ -0,0 +1,28 @@
+var app = Elm.fullscreen(Elm.Main, {
+ initialTime: new Date().getTime(),
+ translations: document.getElementById('messages').innerHTML,
+ config: document.getElementById('config').innerHTML,
+ sign: null
+});
+
+navigator.id.watch({
+ loggedInUser: null,
+ onlogin: function(assertion) {
+ app.ports.sign.send({
+ operation: 'SignIn',
+ assertion: assertion
+ });
+ },
+ onlogout: function() {}
+});
+
+app.ports.persona.subscribe(function(communication) {
+ if(communication === 'SignIn') {
+ navigator.id.request();
+ } else if(communication === 'SignOut') {
+ navigator.id.logout();
+ app.ports.sign.send({
+ operation: 'SignOut'
+ });
+ }
+});
diff --git a/sharedCost.cabal b/sharedCost.cabal
index 8b35975..3303568 100644
--- a/sharedCost.cabal
+++ b/sharedCost.cabal
@@ -11,30 +11,31 @@ executable sharedCost
hs-source-dirs: src/server
ghc-options: -Wall -fwarn-incomplete-uni-patterns
build-depends: base
- , scotty == 0.10.1
- , wai == 3.0.3.0
- , wai-middleware-static == 0.7.0.1
- , http-types == 0.8.6
- , time == 1.5.0.1
- , text == 1.2.1.1
- , persistent == 2.2
- , persistent-sqlite == 2.2
- , persistent-template == 2.1.3.4
- , esqueleto == 2.2.7
- , monad-logger == 0.3.13.1
- , resourcet == 1.1.5
- , transformers == 0.4.2.0
- , blaze-html == 0.8.0.2
- , clay == 0.10.1
- , aeson == 0.9.0.1
- , scotty-cookie == 0.1.0.3
- , clientsession == 0.9.1.1
- , uuid == 1.3.10
- , email-validate == 2.1.3
- , mime-mail == 0.4.9
- , ConfigFile == 1.1.4
- , mtl == 2.2.1
- , lens == 4.12.3
- , parsec == 3.1.9
- , unordered-containers == 0.2.5.1
- , containers == 0.5.6.2
+ , scotty
+ , wai
+ , wai-middleware-static
+ , http-types
+ , http-conduit
+ , time
+ , text
+ , bytestring
+ , persistent
+ , persistent-sqlite
+ , persistent-template
+ , esqueleto
+ , monad-logger
+ , resourcet
+ , transformers
+ , blaze-html
+ , clay
+ , aeson
+ , scotty-cookie
+ , clientsession
+ , uuid
+ , mime-mail
+ , ConfigFile
+ , mtl
+ , lens
+ , parsec
+ , unordered-containers
+ , containers
diff --git a/src/client/Main.elm b/src/client/Main.elm
deleted file mode 100644
index 4f96675..0000000
--- a/src/client/Main.elm
+++ /dev/null
@@ -1,101 +0,0 @@
-module Main
- ( main
- ) where
-
-import Graphics.Element exposing (..)
-
-import Html exposing (Html)
-
-import Http
-import Task exposing (..)
-import Time exposing (..)
-import Json.Decode as Json exposing ((:=))
-import Dict
-
-import Model exposing (Model, initialModel)
-import Model.User exposing (Users, usersDecoder, UserId, userIdDecoder)
-import Model.Payment exposing (Payments, paymentsDecoder, perPage)
-import Model.Payer exposing (Payers, payersDecoder)
-import Model.Translations exposing (..)
-import Model.Config exposing (..)
-
-import Update exposing (Action(..), actions, updateModel)
-import Update.SignIn exposing (..)
-
-import View.Page exposing (renderPage)
-
-import ServerCommunication exposing (serverCommunications, sendRequest)
-
-main : Signal Html
-main = Signal.map renderPage model
-
-model : Signal Model
-model = Signal.foldp updateModel (initialModel initialTime translations config) update
-
-update : Signal Action
-update = Signal.mergeMany
- [ Signal.map UpdateTime (Time.every 1000)
- , actions.signal
- ]
-
----------------------------------------
-
-port signInError : Maybe String
-
----------------------------------------
-
-port initialTime : Time
-
----------------------------------------
-
-port translations : String
-
----------------------------------------
-
-port config : String
-
----------------------------------------
-
-port initView : Task Http.Error ()
-port initView =
- case signInError of
- Just msg ->
- Signal.send actions.address (SignInError msg)
- Nothing ->
- Task.onError goLoggedInView (\_ -> Signal.send actions.address GoSignInView)
-
-goLoggedInView : Task Http.Error ()
-goLoggedInView =
- Task.andThen getUsers <| \users ->
- Task.andThen whoAmI <| \me ->
- Task.andThen getMonthlyPayments <| \monthlyPayments ->
- Task.andThen getPayments <| \payments ->
- Task.andThen getPaymentsCount <| \paymentsCount ->
- Task.andThen getPayers <| \payers ->
- Signal.send actions.address (GoLoggedInView users me monthlyPayments payments paymentsCount payers)
-
-getUsers : Task Http.Error Users
-getUsers = Http.get usersDecoder "/users"
-
-whoAmI : Task Http.Error UserId
-whoAmI = Http.get ("id" := userIdDecoder) "/whoAmI"
-
-getMonthlyPayments : Task Http.Error Payments
-getMonthlyPayments = Http.get paymentsDecoder "/monthlyPayments"
-
-getPayments : Task Http.Error Payments
-getPayments = Http.get paymentsDecoder ("/payments?page=1&perPage=" ++ toString perPage)
-
-getPaymentsCount : Task Http.Error Int
-getPaymentsCount = Http.get ("number" := Json.int) "/payments/count"
-
-getPayers : Task Http.Error Payers
-getPayers = Http.get payersDecoder "/payers"
-
----------------------------------------
-
-port serverCommunicationsPort : Signal (Task Http.RawError ())
-port serverCommunicationsPort =
- Signal.map
- (\comm -> sendRequest comm `Task.andThen` (Signal.send actions.address))
- serverCommunications.signal
diff --git a/src/client/ServerCommunication.elm b/src/client/ServerCommunication.elm
deleted file mode 100644
index 55bf947..0000000
--- a/src/client/ServerCommunication.elm
+++ /dev/null
@@ -1,143 +0,0 @@
-module ServerCommunication
- ( Communication(..)
- , sendRequest
- , serverCommunications
- ) where
-
-import Signal
-import Task as Task exposing (Task)
-import Http
-import Json.Decode exposing (..)
-import Date
-import Time exposing (Time)
-
-import Model.User exposing (UserId)
-import Model.Payment exposing (..)
-import Model.View.LoggedIn.Add exposing (Frequency(..))
-
-import Update as U
-import Update.SignIn exposing (..)
-import Update.LoggedIn as UL
-import Update.LoggedIn.Monthly as UM
-import Update.LoggedIn.Account as UA
-
-type Communication =
- NoCommunication
- | SignIn String
- | AddPayment UserId String Int
- | AddMonthlyPayment String Int
- | SetIncome Time Int
- | DeletePayment Payment Int
- | DeleteMonthlyPayment PaymentId
- | UpdatePage Int
- | SignOut
-
-serverCommunications : Signal.Mailbox Communication
-serverCommunications = Signal.mailbox NoCommunication
-
-sendRequest : Communication -> Task Http.RawError U.Action
-sendRequest communication =
- case getRequest communication of
- Nothing ->
- Task.succeed U.NoOp
- Just request ->
- Http.send Http.defaultSettings request
- |> flip Task.andThen (serverResult communication)
-
-getRequest : Communication -> Maybe Http.Request
-getRequest communication =
- case communication of
- NoCommunication -> Nothing
- SignIn login -> Just (simple "post" ("/signIn?login=" ++ login))
- AddPayment userId name cost -> Just (addPaymentRequest name cost Punctual)
- AddMonthlyPayment name cost -> Just (addPaymentRequest name cost Monthly)
- SetIncome _ amount -> Just (simple "post" ("/income?amount=" ++ (toString amount)))
- DeletePayment payment _ -> Just (deletePaymentRequest payment.id)
- DeleteMonthlyPayment paymentId -> Just (deletePaymentRequest paymentId)
- UpdatePage page -> Just (updatePageRequest page)
- SignOut -> Just (simple "post" "/signOut")
-
-addPaymentRequest : String -> Int -> Frequency -> Http.Request
-addPaymentRequest name cost frequency =
- simple "post" ("/payment/add?name=" ++ name ++ "&cost=" ++ (toString cost) ++ "&frequency=" ++ (toString frequency))
-
-deletePaymentRequest : PaymentId -> Http.Request
-deletePaymentRequest id =
- simple "post" ("payment/delete?id=" ++ (toString id))
-
-updatePageRequest : Int -> Http.Request
-updatePageRequest page =
- simple "get" ("payments?page=" ++ toString page ++ "&perPage=" ++ toString perPage)
-
-simple : String -> String -> Http.Request
-simple method url =
- { verb = method
- , headers = []
- , url = url
- , body = Http.empty
- }
-
-serverResult : Communication -> Http.Response -> Task Http.RawError U.Action
-serverResult communication response =
- case response.status of
- 200 ->
- case communication of
- NoCommunication ->
- Task.succeed U.NoOp
- SignIn login ->
- Task.succeed << U.UpdateSignIn <| ValidLogin login
- AddPayment userId name cost ->
- Http.send Http.defaultSettings (updatePageRequest 1)
- |> flip Task.andThen (decodeOkResponse paymentsDecoder (\payments ->
- Task.succeed <| U.UpdateLoggedIn (UL.AddPayment userId name cost payments)
- ))
- AddMonthlyPayment name cost ->
- decodeResponse
- ("id" := paymentIdDecoder)
- (\id -> Task.succeed <| U.UpdateLoggedIn (UL.AddMonthlyPayment id name cost))
- response
- SetIncome currentTime amount ->
- Task.succeed <| U.UpdateLoggedIn (UL.UpdateAccount (UA.UpdateIncome currentTime amount))
- DeletePayment payment currentPage ->
- Http.send Http.defaultSettings (updatePageRequest currentPage)
- |> flip Task.andThen (decodeOkResponse paymentsDecoder (\payments ->
- Task.succeed <| U.UpdateLoggedIn (UL.DeletePayment payment payments)
- ))
- DeleteMonthlyPayment id ->
- Task.succeed <| U.UpdateLoggedIn (UL.UpdateMonthly (UM.DeletePayment id))
- UpdatePage page ->
- decodeResponse
- paymentsDecoder
- (\payments -> Task.succeed <| U.UpdateLoggedIn (UL.UpdatePage page payments))
- response
- SignOut ->
- Task.succeed (U.GoSignInView)
- errorStatus ->
- case communication of
- SignIn _ ->
- decodeResponse
- ("error" := string)
- (\error ->
- Task.succeed <| U.UpdateSignIn (ErrorLogin error)
- )
- response
- _ ->
- Task.succeed <| U.NoOp
-
-decodeOkResponse : Decoder a -> (a -> Task b U.Action) -> Http.Response -> Task b U.Action
-decodeOkResponse decoder responseToAction response =
- if response.status == 200
- then decodeResponse decoder responseToAction response
- else Task.succeed U.NoOp
-
-decodeResponse : Decoder a -> (a -> Task b U.Action) -> Http.Response -> Task b U.Action
-decodeResponse decoder responseToAction response =
- case response.value of
- Http.Text text ->
- case decodeString decoder text of
- Ok x ->
- responseToAction x
- Err _ ->
- Task.succeed U.NoOp
- Http.Blob _ ->
- Task.succeed U.NoOp
diff --git a/src/client/elm/InitViewAction.elm b/src/client/elm/InitViewAction.elm
new file mode 100644
index 0000000..7c353a7
--- /dev/null
+++ b/src/client/elm/InitViewAction.elm
@@ -0,0 +1,25 @@
+module InitViewAction
+ ( initViewAction
+ ) where
+
+import Task exposing (..)
+import Http
+import Json.Decode as Json exposing ((:=))
+
+import Update exposing (Action(GoLoggedInView, GoSignInView))
+
+import Model.Payment exposing (Payments, paymentsDecoder, perPage)
+import Model.Payer exposing (Payers, payersDecoder)
+import Model.User exposing (Users, usersDecoder, UserId, userIdDecoder)
+
+initViewAction : Task Http.Error Action
+initViewAction = Task.onError loggedInView (always <| Task.succeed GoSignInView)
+
+loggedInView : Task Http.Error Action
+loggedInView =
+ Task.map GoLoggedInView (Http.get usersDecoder "/users")
+ `Task.andMap` (Http.get ("id" := userIdDecoder) "/whoAmI")
+ `Task.andMap` (Http.get paymentsDecoder "/monthlyPayments")
+ `Task.andMap` (Http.get paymentsDecoder ("/payments?page=1&perPage=" ++ toString perPage))
+ `Task.andMap` (Http.get ("number" := Json.int) "/payments/count")
+ `Task.andMap` (Http.get payersDecoder "/payers")
diff --git a/src/client/elm/Main.elm b/src/client/elm/Main.elm
new file mode 100644
index 0000000..f79d6a0
--- /dev/null
+++ b/src/client/elm/Main.elm
@@ -0,0 +1,89 @@
+module Main
+ ( main
+ ) where
+
+import Graphics.Element exposing (..)
+
+import Html exposing (Html)
+
+import Http
+import Task exposing (..)
+import Time exposing (..)
+import Json.Decode as Json
+import Dict
+import String
+
+import Model exposing (Model, initialModel)
+import Model.Translations exposing (..)
+import Model.Config exposing (..)
+
+import Update exposing (Action(..), actions, updateModel)
+import Update.SignIn exposing (..)
+
+import View.Page exposing (renderPage)
+
+import ServerCommunication as SC exposing (serverCommunications, sendRequest)
+
+import Persona as Persona exposing (operations)
+
+import InitViewAction exposing (initViewAction)
+
+import Sign
+
+main : Signal Html
+main = Signal.map renderPage model
+
+model : Signal Model
+model = Signal.foldp updateModel (initialModel initialTime translations config) update
+
+update : Signal Action
+update = Signal.mergeMany
+ [ Signal.map UpdateTime (Time.every 1000)
+ , actions.signal
+ ]
+
+---------------------------------------
+
+port initialTime : Time
+
+---------------------------------------
+
+port translations : String
+
+---------------------------------------
+
+port config : String
+
+---------------------------------------
+
+port ready : Signal String
+port ready = Signal.constant "ready"
+
+---------------------------------------
+
+port initView : Task Http.Error ()
+port initView = initViewAction `Task.andThen` (Signal.send actions.address)
+
+---------------------------------------
+
+port serverCommunicationsPort : Signal (Task Http.Error ())
+port serverCommunicationsPort =
+ Signal.map
+ (\comm ->
+ sendRequest comm
+ |> flip Task.andThen (\action -> Signal.send actions.address action)
+ )
+ (Signal.merge signCommunication serverCommunications.signal)
+
+---------------------------------------
+
+port persona : Signal String
+port persona = Signal.map Persona.toString operations.signal
+
+---------------------------------------
+
+port sign : Signal Json.Value
+
+signCommunication : Signal SC.Communication
+signCommunication =
+ Signal.map (Sign.toServerCommunication << Sign.decodeOperation) sign
diff --git a/src/client/Model.elm b/src/client/elm/Model.elm
index 43a19c5..43a19c5 100644
--- a/src/client/Model.elm
+++ b/src/client/elm/Model.elm
diff --git a/src/client/Model/Config.elm b/src/client/elm/Model/Config.elm
index e47b032..e47b032 100644
--- a/src/client/Model/Config.elm
+++ b/src/client/elm/Model/Config.elm
diff --git a/src/client/Model/Date.elm b/src/client/elm/Model/Date.elm
index 1c56de4..1c56de4 100644
--- a/src/client/Model/Date.elm
+++ b/src/client/elm/Model/Date.elm
diff --git a/src/client/Model/Income.elm b/src/client/elm/Model/Income.elm
index 97a5652..97a5652 100644
--- a/src/client/Model/Income.elm
+++ b/src/client/elm/Model/Income.elm
diff --git a/src/client/Model/Payer.elm b/src/client/elm/Model/Payer.elm
index 9fd1bb5..9fd1bb5 100644
--- a/src/client/Model/Payer.elm
+++ b/src/client/elm/Model/Payer.elm
diff --git a/src/client/Model/Payment.elm b/src/client/elm/Model/Payment.elm
index c4a8963..c4a8963 100644
--- a/src/client/Model/Payment.elm
+++ b/src/client/elm/Model/Payment.elm
diff --git a/src/client/Model/Translations.elm b/src/client/elm/Model/Translations.elm
index bec8c9b..bec8c9b 100644
--- a/src/client/Model/Translations.elm
+++ b/src/client/elm/Model/Translations.elm
diff --git a/src/client/Model/User.elm b/src/client/elm/Model/User.elm
index 1412913..1412913 100644
--- a/src/client/Model/User.elm
+++ b/src/client/elm/Model/User.elm
diff --git a/src/client/Model/View.elm b/src/client/elm/Model/View.elm
index 90c0e53..90c0e53 100644
--- a/src/client/Model/View.elm
+++ b/src/client/elm/Model/View.elm
diff --git a/src/client/Model/View/LoggedIn/Account.elm b/src/client/elm/Model/View/LoggedIn/Account.elm
index 2bb3ae7..2bb3ae7 100644
--- a/src/client/Model/View/LoggedIn/Account.elm
+++ b/src/client/elm/Model/View/LoggedIn/Account.elm
diff --git a/src/client/Model/View/LoggedIn/Add.elm b/src/client/elm/Model/View/LoggedIn/Add.elm
index 5598084..5598084 100644
--- a/src/client/Model/View/LoggedIn/Add.elm
+++ b/src/client/elm/Model/View/LoggedIn/Add.elm
diff --git a/src/client/Model/View/LoggedIn/Edition.elm b/src/client/elm/Model/View/LoggedIn/Edition.elm
index da6d7b0..da6d7b0 100644
--- a/src/client/Model/View/LoggedIn/Edition.elm
+++ b/src/client/elm/Model/View/LoggedIn/Edition.elm
diff --git a/src/client/Model/View/LoggedIn/Monthly.elm b/src/client/elm/Model/View/LoggedIn/Monthly.elm
index 3c6f66a..3c6f66a 100644
--- a/src/client/Model/View/LoggedIn/Monthly.elm
+++ b/src/client/elm/Model/View/LoggedIn/Monthly.elm
diff --git a/src/client/Model/View/LoggedInView.elm b/src/client/elm/Model/View/LoggedInView.elm
index 122c4be..122c4be 100644
--- a/src/client/Model/View/LoggedInView.elm
+++ b/src/client/elm/Model/View/LoggedInView.elm
diff --git a/src/client/Model/View/SignInView.elm b/src/client/elm/Model/View/SignInView.elm
index 0fbce39..0fbce39 100644
--- a/src/client/Model/View/SignInView.elm
+++ b/src/client/elm/Model/View/SignInView.elm
diff --git a/src/client/Native/Reads.js b/src/client/elm/Native/Reads.js
index 5785aed..5785aed 100644
--- a/src/client/Native/Reads.js
+++ b/src/client/elm/Native/Reads.js
diff --git a/src/client/elm/Persona.elm b/src/client/elm/Persona.elm
new file mode 100644
index 0000000..51b5fc6
--- /dev/null
+++ b/src/client/elm/Persona.elm
@@ -0,0 +1,28 @@
+module Persona
+ ( Operation(..)
+ , operations
+ , fromString
+ , toString
+ ) where
+
+type Operation =
+ NoOp
+ | SignIn
+ | SignOut
+
+operations : Signal.Mailbox Operation
+operations = Signal.mailbox NoOp
+
+fromString : String -> Operation
+fromString str =
+ case str of
+ "SignIn" -> SignIn
+ "SignOut" -> SignOut
+ _ -> NoOp
+
+toString : Operation -> String
+toString operation =
+ case operation of
+ SignIn -> "SignIn"
+ SignOut -> "SignOut"
+ _ -> "NoOp"
diff --git a/src/client/Reads.elm b/src/client/elm/Reads.elm
index f855802..f855802 100644
--- a/src/client/Reads.elm
+++ b/src/client/elm/Reads.elm
diff --git a/src/client/elm/ServerCommunication.elm b/src/client/elm/ServerCommunication.elm
new file mode 100644
index 0000000..70612cb
--- /dev/null
+++ b/src/client/elm/ServerCommunication.elm
@@ -0,0 +1,95 @@
+module ServerCommunication
+ ( Communication(..)
+ , sendRequest
+ , serverCommunications
+ ) where
+
+import Signal
+import Task as Task exposing (Task)
+import Http
+import Json.Decode exposing (..)
+import Date
+import Time exposing (Time)
+import Debug
+
+import SimpleHTTP exposing (..)
+
+import Model.User exposing (UserId)
+import Model.Payment exposing (..)
+import Model.View.LoggedIn.Add exposing (Frequency(..))
+
+import Update as U
+import Update.SignIn exposing (..)
+import Update.LoggedIn as UL
+import Update.LoggedIn.Monthly as UM
+import Update.LoggedIn.Account as UA
+
+import InitViewAction exposing (initViewAction)
+
+type Communication =
+ NoCommunication
+ | SignIn String
+ | AddPayment UserId String Int
+ | AddMonthlyPayment String Int
+ | SetIncome Time Int
+ | DeletePayment Payment Int
+ | DeleteMonthlyPayment PaymentId
+ | UpdatePage Int
+ | SignOut
+
+serverCommunications : Signal.Mailbox Communication
+serverCommunications = Signal.mailbox NoCommunication
+
+sendRequest : Communication -> Task Http.Error U.Action
+sendRequest communication =
+ case communication of
+
+ NoCommunication ->
+ Task.succeed U.NoOp
+
+ SignIn assertion ->
+ post ("/signIn?assertion=" ++ assertion)
+ |> flip Task.andThen (always initViewAction)
+
+ AddPayment userId name cost ->
+ post (addPaymentURL name cost Punctual)
+ |> flip Task.andThen (always (getPaymentsAtPage 1))
+ |> Task.map (\payments -> U.UpdateLoggedIn (UL.AddPayment userId name cost payments))
+
+ AddMonthlyPayment name cost ->
+ post (addPaymentURL name cost Monthly)
+ |> flip Task.andThen (decodeHttpValue <| "id" := paymentIdDecoder)
+ |> Task.map (\id -> U.UpdateLoggedIn (UL.AddMonthlyPayment id name cost))
+
+ DeletePayment payment currentPage ->
+ post (deletePaymentURL payment.id)
+ |> flip Task.andThen (always (getPaymentsAtPage currentPage))
+ |> Task.map (\payments -> U.UpdateLoggedIn (UL.DeletePayment payment payments))
+
+ DeleteMonthlyPayment id ->
+ post (deletePaymentURL id)
+ |> Task.map (always (U.UpdateLoggedIn (UL.UpdateMonthly (UM.DeletePayment id))))
+
+ UpdatePage page ->
+ getPaymentsAtPage page
+ |> flip Task.andThen (Task.succeed << U.UpdateLoggedIn << UL.UpdatePage page)
+
+ SetIncome currentTime amount ->
+ post ("/income?amount=" ++ (toString amount))
+ |> Task.map (always (U.UpdateLoggedIn (UL.UpdateAccount (UA.UpdateIncome currentTime amount))))
+
+ SignOut ->
+ post "/signOut"
+ |> Task.map (always U.GoSignInView)
+
+getPaymentsAtPage : Int -> Task Http.Error Payments
+getPaymentsAtPage page =
+ Http.get paymentsDecoder ("payments?page=" ++ toString page ++ "&perPage=" ++ toString perPage)
+
+addPaymentURL : String -> Int -> Frequency -> String
+addPaymentURL name cost frequency =
+ "/payment/add?name=" ++ name ++ "&cost=" ++ (toString cost) ++ "&frequency=" ++ (toString frequency)
+
+deletePaymentURL : PaymentId -> String
+deletePaymentURL id =
+ "payment/delete?id=" ++ (toString id)
diff --git a/src/client/elm/Sign.elm b/src/client/elm/Sign.elm
new file mode 100644
index 0000000..44f23b8
--- /dev/null
+++ b/src/client/elm/Sign.elm
@@ -0,0 +1,43 @@
+module Sign
+ ( Operation(..)
+ , decodeOperation
+ , toServerCommunication
+ ) where
+
+import Json.Decode as Json
+import Json.Decode exposing (Value, Decoder, (:=))
+import Maybe
+
+import ServerCommunication as SC
+
+type Operation =
+ NoOp
+ | SignIn String
+ | SignOut
+
+decodeOperation : Value -> Operation
+decodeOperation value =
+ Json.decodeValue operationDecoder value
+ |> Result.toMaybe
+ |> Maybe.withDefault NoOp
+
+toServerCommunication : Operation -> SC.Communication
+toServerCommunication operation =
+ case operation of
+ NoOp -> SC.NoCommunication
+ SignIn assertion -> SC.SignIn assertion
+ SignOut -> SC.SignOut
+
+operationDecoder : Decoder Operation
+operationDecoder =
+ ("operation" := Json.string) `Json.andThen` operationDecoderWithTag
+
+operationDecoderWithTag : String -> Decoder Operation
+operationDecoderWithTag operation =
+ case operation of
+ "SignIn" ->
+ Json.map SignIn ("assertion" := Json.string)
+ "SignOut" ->
+ Json.succeed SignOut
+ _ ->
+ Json.succeed NoOp
diff --git a/src/client/elm/SimpleHTTP.elm b/src/client/elm/SimpleHTTP.elm
new file mode 100644
index 0000000..99a7056
--- /dev/null
+++ b/src/client/elm/SimpleHTTP.elm
@@ -0,0 +1,41 @@
+module SimpleHTTP
+ ( post
+ , decodeHttpValue
+ ) where
+
+import Http exposing (..)
+import Task exposing (..)
+import Json.Decode as Json exposing (Decoder)
+
+post : String -> Task Error Value
+post url =
+ { verb = "POST"
+ , headers = []
+ , url = url
+ , body = empty
+ }
+ |> Http.send defaultSettings
+ |> mapError promoteError
+ |> flip Task.andThen handleResponse
+
+handleResponse : Response -> Task Error Value
+handleResponse response =
+ if 200 <= response.status && response.status < 300
+ then Task.succeed response.value
+ else fail (BadResponse response.status response.statusText)
+
+promoteError : RawError -> Error
+promoteError rawError =
+ case rawError of
+ RawTimeout -> Timeout
+ RawNetworkError -> NetworkError
+
+decodeHttpValue : Decoder a -> Value -> Task Error a
+decodeHttpValue decoder value =
+ case value of
+ Text str ->
+ case Json.decodeString decoder str of
+ Ok v -> succeed v
+ Err msg -> fail (UnexpectedPayload msg)
+ _ ->
+ fail (UnexpectedPayload "Response body is a blob, expecting a string.")
diff --git a/src/client/Update.elm b/src/client/elm/Update.elm
index 3c4614a..3c4614a 100644
--- a/src/client/Update.elm
+++ b/src/client/elm/Update.elm
diff --git a/src/client/Update/LoggedIn.elm b/src/client/elm/Update/LoggedIn.elm
index e477094..e477094 100644
--- a/src/client/Update/LoggedIn.elm
+++ b/src/client/elm/Update/LoggedIn.elm
diff --git a/src/client/Update/LoggedIn/Account.elm b/src/client/elm/Update/LoggedIn/Account.elm
index cf4c834..cf4c834 100644
--- a/src/client/Update/LoggedIn/Account.elm
+++ b/src/client/elm/Update/LoggedIn/Account.elm
diff --git a/src/client/Update/LoggedIn/Add.elm b/src/client/elm/Update/LoggedIn/Add.elm
index 1f28997..1f28997 100644
--- a/src/client/Update/LoggedIn/Add.elm
+++ b/src/client/elm/Update/LoggedIn/Add.elm
diff --git a/src/client/Update/LoggedIn/Monthly.elm b/src/client/elm/Update/LoggedIn/Monthly.elm
index 1379323..1379323 100644
--- a/src/client/Update/LoggedIn/Monthly.elm
+++ b/src/client/elm/Update/LoggedIn/Monthly.elm
diff --git a/src/client/Update/SignIn.elm b/src/client/elm/Update/SignIn.elm
index 0aa7c84..cabe4cb 100644
--- a/src/client/Update/SignIn.elm
+++ b/src/client/elm/Update/SignIn.elm
@@ -6,19 +6,10 @@ module Update.SignIn
import Model.View.SignInView exposing (..)
type SignInAction =
- UpdateLogin String
- | ValidLogin String
- | ErrorLogin String
+ ErrorLogin String
updateSignIn : SignInAction -> SignInView -> SignInView
updateSignIn action signInView =
case action of
- UpdateLogin login ->
- { signInView | login <- login }
- ValidLogin message ->
- { signInView
- | login <- ""
- , result <- Just (Ok message)
- }
ErrorLogin message ->
{ signInView | result <- Just (Err message) }
diff --git a/src/client/Utils/Dict.elm b/src/client/elm/Utils/Dict.elm
index dc01b17..dc01b17 100644
--- a/src/client/Utils/Dict.elm
+++ b/src/client/elm/Utils/Dict.elm
diff --git a/src/client/Utils/Either.elm b/src/client/elm/Utils/Either.elm
index 10c40e3..10c40e3 100644
--- a/src/client/Utils/Either.elm
+++ b/src/client/elm/Utils/Either.elm
diff --git a/src/client/Utils/Maybe.elm b/src/client/elm/Utils/Maybe.elm
index d954ae0..d954ae0 100644
--- a/src/client/Utils/Maybe.elm
+++ b/src/client/elm/Utils/Maybe.elm
diff --git a/src/client/Utils/Validation.elm b/src/client/elm/Utils/Validation.elm
index b9bccb3..b9bccb3 100644
--- a/src/client/Utils/Validation.elm
+++ b/src/client/elm/Utils/Validation.elm
diff --git a/src/client/View/Date.elm b/src/client/elm/View/Date.elm
index 81c5112..81c5112 100644
--- a/src/client/View/Date.elm
+++ b/src/client/elm/View/Date.elm
diff --git a/src/client/View/Events.elm b/src/client/elm/View/Events.elm
index 1eb9027..1eb9027 100644
--- a/src/client/View/Events.elm
+++ b/src/client/elm/View/Events.elm
diff --git a/src/client/View/Expand.elm b/src/client/elm/View/Expand.elm
index 53b4fe5..53b4fe5 100644
--- a/src/client/View/Expand.elm
+++ b/src/client/elm/View/Expand.elm
diff --git a/src/client/View/Header.elm b/src/client/elm/View/Header.elm
index 9d31183..3a6241b 100644
--- a/src/client/View/Header.elm
+++ b/src/client/elm/View/Header.elm
@@ -6,8 +6,7 @@ import Html exposing (..)
import Html.Attributes exposing (..)
import Html.Events exposing (..)
-import ServerCommunication as SC
-import ServerCommunication exposing (serverCommunications)
+import Persona exposing (operations)
import Model exposing (Model)
import Model.View exposing (..)
@@ -26,11 +25,15 @@ renderHeader model =
LoadingView ->
text ""
SignInView _ ->
- text ""
+ button
+ [ class "icon"
+ , onClick operations.address Persona.SignIn
+ ]
+ [ renderIcon "sign-in" ]
LoggedInView _ ->
button
- [ class "signOut"
- , onClick serverCommunications.address SC.SignOut
+ [ class "icon"
+ , onClick operations.address Persona.SignOut
]
- [ renderIcon "power-off" ]
+ [ renderIcon "sign-out" ]
]
diff --git a/src/client/View/Icon.elm b/src/client/elm/View/Icon.elm
index f22c1a2..f22c1a2 100644
--- a/src/client/View/Icon.elm
+++ b/src/client/elm/View/Icon.elm
diff --git a/src/client/View/Loading.elm b/src/client/elm/View/Loading.elm
index f8c6cd6..f8c6cd6 100644
--- a/src/client/View/Loading.elm
+++ b/src/client/elm/View/Loading.elm
diff --git a/src/client/View/LoggedIn.elm b/src/client/elm/View/LoggedIn.elm
index 96916e0..96916e0 100644
--- a/src/client/View/LoggedIn.elm
+++ b/src/client/elm/View/LoggedIn.elm
diff --git a/src/client/View/LoggedIn/Account.elm b/src/client/elm/View/LoggedIn/Account.elm
index 706f7cc..706f7cc 100644
--- a/src/client/View/LoggedIn/Account.elm
+++ b/src/client/elm/View/LoggedIn/Account.elm
diff --git a/src/client/View/LoggedIn/Add.elm b/src/client/elm/View/LoggedIn/Add.elm
index 572bdf6..572bdf6 100644
--- a/src/client/View/LoggedIn/Add.elm
+++ b/src/client/elm/View/LoggedIn/Add.elm
diff --git a/src/client/View/LoggedIn/Monthly.elm b/src/client/elm/View/LoggedIn/Monthly.elm
index a274015..a274015 100644
--- a/src/client/View/LoggedIn/Monthly.elm
+++ b/src/client/elm/View/LoggedIn/Monthly.elm
diff --git a/src/client/View/LoggedIn/Paging.elm b/src/client/elm/View/LoggedIn/Paging.elm
index 93d7f1d..93d7f1d 100644
--- a/src/client/View/LoggedIn/Paging.elm
+++ b/src/client/elm/View/LoggedIn/Paging.elm
diff --git a/src/client/View/LoggedIn/Table.elm b/src/client/elm/View/LoggedIn/Table.elm
index f5a08b5..f5a08b5 100644
--- a/src/client/View/LoggedIn/Table.elm
+++ b/src/client/elm/View/LoggedIn/Table.elm
diff --git a/src/client/View/Page.elm b/src/client/elm/View/Page.elm
index 763734d..763734d 100644
--- a/src/client/View/Page.elm
+++ b/src/client/elm/View/Page.elm
diff --git a/src/client/View/Price.elm b/src/client/elm/View/Price.elm
index 286bcaa..286bcaa 100644
--- a/src/client/View/Price.elm
+++ b/src/client/elm/View/Price.elm
diff --git a/src/client/View/SignIn.elm b/src/client/elm/View/SignIn.elm
index 2a6cbca..8fcac16 100644
--- a/src/client/View/SignIn.elm
+++ b/src/client/elm/View/SignIn.elm
@@ -24,18 +24,7 @@ renderSignIn : Model -> SignInView -> Html
renderSignIn model signInView =
div
[ class "signIn" ]
- [ H.form
- [ onSubmitPrevDefault serverCommunications.address (SC.SignIn signInView.login) ]
- [ input
- [ value signInView.login
- , on "input" targetValue (Signal.message actions.address << UpdateSignIn << UpdateLogin)
- ]
- []
- , button
- []
- [ text (getMessage "SignIn" model.translations)]
- ]
- , div
+ [ div
[ class "result" ]
[ signInResult model signInView ]
]
diff --git a/src/client/js/main.js b/src/client/js/main.js
new file mode 100644
index 0000000..12593e6
--- /dev/null
+++ b/src/client/js/main.js
@@ -0,0 +1,28 @@
+var app = Elm.fullscreen(Elm.Main, {
+ initialTime: new Date().getTime(),
+ translations: document.getElementById('messages').innerHTML,
+ config: document.getElementById('config').innerHTML,
+ sign: null
+});
+
+navigator.id.watch({
+ loggedInUser: null,
+ onlogin: function(assertion) {
+ app.ports.sign.send({
+ operation: 'SignIn',
+ assertion: assertion
+ });
+ },
+ onlogout: function() {}
+});
+
+app.ports.persona.subscribe(function(communication) {
+ if(communication === 'SignIn') {
+ navigator.id.request();
+ } else if(communication === 'SignOut') {
+ navigator.id.logout();
+ app.ports.sign.send({
+ operation: 'SignOut'
+ });
+ }
+});
diff --git a/src/server/Config.hs b/src/server/Config.hs
index bd7f325..37f57ec 100644
--- a/src/server/Config.hs
+++ b/src/server/Config.hs
@@ -18,7 +18,6 @@ import Control.Arrow (left)
data Config = Config
{ hostname :: Text
, port :: Int
- , signInExpirationMn :: Int
, currency :: Text
} deriving (Read, Eq, Show)
@@ -29,6 +28,5 @@ getConfig filePath =
Config <$>
(T.pack <$> get cp "DEFAULT" "hostname") <*>
(get cp "DEFAULT" "port") <*>
- (get cp "DEFAULT" "sign-in-expiration-mn") <*>
(T.pack <$> get cp "DEFAULT" "currency")
)
diff --git a/src/server/Controller/SignIn.hs b/src/server/Controller/SignIn.hs
index 31cd510..8eceb56 100644
--- a/src/server/Controller/SignIn.hs
+++ b/src/server/Controller/SignIn.hs
@@ -2,32 +2,21 @@
module Controller.SignIn
( signIn
- , validateSignIn
) where
import Web.Scotty
import Network.HTTP.Types.Status (ok200)
-import Database.Persist
-
import Control.Monad.IO.Class (liftIO)
import Data.Text (Text)
-import qualified Data.Text as T
-import qualified Data.Text.Lazy as TL
-import qualified Data.Text.Encoding as TE
-import Data.Time.Clock (getCurrentTime, diffUTCTime)
import Data.Maybe (isJust)
import qualified LoginSession
import Config
-import SendMail
-
-import Text.Email.Validate as Email
-
import Model.Database
import Model.User
import Model.SignIn
@@ -36,65 +25,20 @@ import Model.Message (getMessage)
import Json (jsonError)
-import Secure (getUserFromToken)
-
-import qualified View.Mail.SignIn as SignIn
+import Persona (verifyEmail)
signIn :: Config -> Text -> ActionM ()
-signIn config login =
- if Email.isValid (TE.encodeUtf8 login)
- then do
- maybeUser <- liftIO . runDb $ getUser login
- case maybeUser of
- Just user -> do
- token <- liftIO . runDb $ createSignInToken login
- let url = T.concat ["http://", hostname config, "/validateSignIn?token=", token]
- maybeSentMail <- liftIO . sendMail $ SignIn.getMail (entityVal user) url [login]
- case maybeSentMail of
- Right _ ->
- status ok200
- Left _ ->
- jsonError (getMessage SendEmailFail)
- Nothing ->
- jsonError (getMessage Unauthorized)
- else
- jsonError (getMessage EnterValidEmail)
-
-validateSignIn :: Config -> Text -> ActionM ()
-validateSignIn config textToken = do
- alreadySigned <- isAlreadySigned
- if alreadySigned
- then
- redirect "/"
- else do
- mbSignIn <- liftIO . runDb $ getSignInToken textToken
- now <- liftIO getCurrentTime
- case mbSignIn of
- Just signIn ->
- if signInIsUsed . entityVal $ signIn
- then
- redirectError (getMessage SignInUsed)
- else
- let diffTime = now `diffUTCTime` (signInCreation . entityVal $ signIn)
- in if diffTime > (fromIntegral $ (signInExpirationMn config) * 60)
- then
- redirectError (getMessage SignInExpired)
- else do
- LoginSession.put (signInToken . entityVal $ signIn)
- liftIO . runDb . signInTokenToUsed . entityKey $ signIn
- redirect "/"
- Nothing ->
- redirectError (getMessage SignInInvalid)
-
-isAlreadySigned :: ActionM Bool
-isAlreadySigned = do
- mbToken <- LoginSession.get
- case mbToken of
+signIn config assertion = do
+ mbEmail <- liftIO $ verifyEmail config assertion
+ case mbEmail of
Nothing ->
- return False
- Just token -> do
- liftIO . runDb . fmap isJust $ getUserFromToken token
-
-redirectError :: Text -> ActionM ()
-redirectError msg =
- redirect . TL.fromStrict . T.concat $ ["/?signInError=", msg]
+ jsonError (getMessage InvalidEmail)
+ Just email -> do
+ isAuthorized <- liftIO . fmap isJust . runDb $ getUser email
+ if isAuthorized
+ then do
+ token <- liftIO . runDb $ createSignInToken email
+ LoginSession.put token
+ status ok200
+ else
+ jsonError (getMessage Unauthorized)
diff --git a/src/server/Design/Header.hs b/src/server/Design/Header.hs
index 7b82577..9f83778 100644
--- a/src/server/Design/Header.hs
+++ b/src/server/Design/Header.hs
@@ -25,7 +25,7 @@ headerDesign =
marginBottom blockMarginBottom
paddingLeft sidePercent
- button # ".signOut" ? do
+ button # ".icon" ? do
let iconHeight = 50
let sideMargin = ((headerHeight - iconHeight) `Prelude.div` 2)
position absolute
diff --git a/src/server/Design/SignIn.hs b/src/server/Design/SignIn.hs
index 6bacc3a..7aff720 100644
--- a/src/server/Design/SignIn.hs
+++ b/src/server/Design/SignIn.hs
@@ -15,26 +15,6 @@ signInDesign =
".signIn" ? do
- opacityAnimation
-
- form ? do
- let inputHeight = 50
- width (px 500)
- marginTop (px 100)
- marginLeft auto
- marginRight auto
-
- input ? do
- defaultInput inputHeight
- display block
- width (pct 100)
- marginBottom (px 10)
-
- button ? do
- defaultButton C.red C.white (px inputHeight)
- display block
- width (pct 100)
-
".result" ? do
marginTop (px 40)
textAlign (alignSide sideCenter)
diff --git a/src/server/Main.hs b/src/server/Main.hs
index 3d61481..3539120 100644
--- a/src/server/Main.hs
+++ b/src/server/Main.hs
@@ -8,7 +8,7 @@ import Control.Concurrent (forkIO)
import MonthlyPaymentJob (monthlyPaymentJobListener)
import Data.Text (Text)
-import qualified Data.Text.IO as TIO
+import qualified Data.Text.IO as T
import Controller.Index
import Controller.SignIn
@@ -28,7 +28,7 @@ main = do
eitherConfig <- Config.getConfig "config.txt"
case eitherConfig of
Left errorMessage ->
- TIO.putStrLn errorMessage
+ T.putStrLn errorMessage
Right config -> do
scotty (Config.port config) $ do
middleware $
@@ -40,12 +40,8 @@ main = do
-- SignIn
post "/signIn" $ do
- login <- param "login" :: ActionM Text
- signIn config login
-
- get "/validateSignIn" $ do
- token <- param "token" :: ActionM Text
- validateSignIn config token
+ assertion <- param "assertion" :: ActionM Text
+ signIn config assertion
-- Users
diff --git a/src/server/Model/Database.hs b/src/server/Model/Database.hs
index 8d1da25..67cc8b3 100644
--- a/src/server/Model/Database.hs
+++ b/src/server/Model/Database.hs
@@ -44,7 +44,6 @@ SignIn
token Text
creation UTCTime
email Text
- isUsed Bool
UniqSignInToken token
deriving Show
Job
diff --git a/src/server/Model/Message/Key.hs b/src/server/Model/Message/Key.hs
index e9f8ef6..7f49ae7 100644
--- a/src/server/Model/Message/Key.hs
+++ b/src/server/Model/Message/Key.hs
@@ -12,12 +12,8 @@ data Key =
| SharedCost
| SignIn
- | SendEmailFail
+ | InvalidEmail
| Unauthorized
- | EnterValidEmail
- | SignInUsed
- | SignInExpired
- | SignInInvalid
| SignInMailTitle
| SignInMail
| SignInEmailSent
diff --git a/src/server/Model/Message/Translations.hs b/src/server/Model/Message/Translations.hs
index a2e9a30..29b21ea 100644
--- a/src/server/Model/Message/Translations.hs
+++ b/src/server/Model/Message/Translations.hs
@@ -34,36 +34,16 @@ m l SignIn =
English -> "Sign in"
French -> "Connexion"
-m l SendEmailFail =
+m l InvalidEmail =
case l of
- English -> "Sorry, we failed to send you the sign up email."
- French -> "Désolé, nous n'avons pas pu t'envoyer le courriel de connexion."
+ English -> "Your email is not valid."
+ French -> "Votre courriel n'est pas valide."
m l Unauthorized =
case l of
English -> "You are not authorized to sign in."
French -> "Tu n'es pas autorisé à te connecter."
-m l EnterValidEmail =
- case l of
- English -> "Please enter a valid email address."
- French -> "Ton courriel n'est pas valide."
-
-m l SignInUsed =
- case l of
- English -> "You already used this link, please sign in again."
- French -> "Tu as déjà utilisé ce lien, connecte-toi à nouveau."
-
-m l SignInExpired =
- case l of
- English -> "The link expired, please sign in again."
- French -> "Le lien sur lequel tu as cliqué a expiré, connecte-toi à nouveau."
-
-m l SignInInvalid =
- case l of
- English -> "The link is invalid, please sign in again."
- French -> "Le lien sur lequel tu as cliqué est invalide, connecte-toi à nouveau."
-
m l SignInMailTitle =
case l of
English -> T.concat ["Sign in to ", m l SharedCost]
diff --git a/src/server/Model/SignIn.hs b/src/server/Model/SignIn.hs
index 117b8b5..b475fdb 100644
--- a/src/server/Model/SignIn.hs
+++ b/src/server/Model/SignIn.hs
@@ -1,8 +1,6 @@
module Model.SignIn
( createSignInToken
, getSignInToken
- , signInTokenToUsed
- , isLastValidToken
) where
import Data.Text (Text)
@@ -19,22 +17,9 @@ createSignInToken :: Text -> Persist Text
createSignInToken email = do
now <- liftIO getCurrentTime
token <- liftIO generateUUID
- _ <- insert $ SignIn token now email False
+ _ <- insert $ SignIn token now email
return token
getSignInToken :: Text -> Persist (Maybe (Entity SignIn))
getSignInToken token =
selectFirst [SignInToken ==. token] []
-
-signInTokenToUsed :: SignInId -> Persist ()
-signInTokenToUsed tokenId =
- update tokenId [SignInIsUsed =. True]
-
-isLastValidToken :: SignIn -> Persist Bool
-isLastValidToken signIn = do
- maybe False ((== (signInToken signIn)) . signInToken . entityVal) <$>
- selectFirst
- [ SignInEmail ==. (signInEmail signIn)
- , SignInIsUsed ==. True
- ]
- [ Desc SignInCreation ]
diff --git a/src/server/Persona.hs b/src/server/Persona.hs
new file mode 100644
index 0000000..8055e8b
--- /dev/null
+++ b/src/server/Persona.hs
@@ -0,0 +1,42 @@
+{-# LANGUAGE OverloadedStrings #-}
+
+module Persona
+ ( verifyEmail
+ ) where
+
+import Control.Monad (guard)
+
+import Network.HTTP.Conduit
+
+import Data.Text (Text)
+import qualified Data.Text as T
+import Data.ByteString.Lazy (fromStrict, toStrict)
+import Data.Text.Encoding (encodeUtf8, decodeUtf8)
+import Data.Aeson
+import Data.Aeson.Types (parseMaybe)
+
+import Config
+
+verifyEmail :: Config -> Text -> IO (Maybe Text)
+verifyEmail config assertion = do
+
+ initReq <- parseUrl "https://verifier.login.persona.org/verify"
+
+ let request =
+ (flip urlEncodedBody) initReq $
+ [ ("assertion", encodeUtf8 $ assertion)
+ , ("audience", encodeUtf8 $ hostname config)
+ ]
+
+ manager <- newManager tlsManagerSettings
+ response <- httpLbs request manager
+
+ return . parseEmail . decodeUtf8 . toStrict . responseBody $ response
+
+parseEmail :: Text -> Maybe Text
+parseEmail payload = do
+ result <- decode . fromStrict . encodeUtf8 $ payload
+ flip parseMaybe result $ \obj -> do
+ status <- T.pack <$> obj .: "status"
+ guard (status == "okay")
+ obj .: "email"
diff --git a/src/server/Secure.hs b/src/server/Secure.hs
index 192fa10..7b6e6de 100644
--- a/src/server/Secure.hs
+++ b/src/server/Secure.hs
@@ -12,7 +12,7 @@ import Network.HTTP.Types.Status (forbidden403)
import Database.Persist (Entity, entityVal)
import Model.User (getUser)
-import Model.SignIn (getSignInToken, isLastValidToken)
+import Model.SignIn (getSignInToken)
import Model.Database
import Control.Monad.IO.Class (liftIO)
@@ -44,9 +44,6 @@ getUserFromToken token = do
mbSignIn <- fmap entityVal <$> getSignInToken token
case mbSignIn of
Just signIn -> do
- isValid <- isLastValidToken signIn
- if isValid
- then getUser (signInEmail signIn)
- else return Nothing
+ getUser (signInEmail signIn)
Nothing ->
return Nothing
diff --git a/src/server/View/Page.hs b/src/server/View/Page.hs
index 2865337..7310fbb 100644
--- a/src/server/View/Page.hs
+++ b/src/server/View/Page.hs
@@ -26,7 +26,9 @@ page config =
renderHtml . docTypeHtml $ do
H.head $ do
meta ! charset "UTF-8"
+ meta ! httpEquiv "X-UA-Compatible" ! content "IE=Edge" -- IE8+ only is valid to use with persona
H.title (toHtml $ getMessage SharedCost)
+ script ! src "https://login.persona.org/include.js" $ ""
script ! src "javascripts/client.js" $ ""
script ! A.id "messages" ! type_ "application/json" $ toHtml . decodeUtf8 . encode $ getTranslations
script ! A.id "config" ! type_ "application/json" $ toHtml . decodeUtf8 . encode $ config
@@ -35,4 +37,4 @@ page config =
link ! rel "icon" ! type_ "image/png" ! href "images/icon.png"
H.style $ toHtml globalDesign
body $ do
- script ! src "javascripts/elmLauncher.js" $ ""
+ script ! src "javascripts/main.js" $ ""