Kenji TOKUDOME avatar Kenji TOKUDOME committed e23a088

move to js_of_ocaml_game1.

Comments (0)

Files changed (8)

 .PHONY: all install clean
 
 USE_OCAMLFIND = true
-
-FILES[] =
-	game
-
-PROGRAM = testcase
-
-OCAMLPACKS[] += lwt js_of_ocaml js_of_ocaml.deriving
-# OCAMLPACKS[] += pcre batteries cryptokit
-# OCAMLFLAGS += -thread
+BYTE_ENABLED = true
+NATIVE_ENABLED = false
 
 # ignore the warning.
 OCAMLFLAGS[] += -w ae
+#OCAMLFLAGS   = -annot -w A-4-32
 
 OCAML_LIBS += 
 OCAML_CLIBS +=
 OCAML_OTHER_LIBS +=
 OCAML_LIB_FLAGS +=
 
-OCAMLDEPFLAGS= -syntax camlp4o -package lwt,js_of_ocaml.syntax,js_of_ocaml.deriving.syntax
-OCAMLPPFLAGS= -syntax camlp4o -package lwt,js_of_ocaml.syntax,js_of_ocaml.deriving.syntax
-# public.OCAML_BYTE_LINK_FLAGS = -linkpkg # removes -custom
+OCAMLDEPFLAGS= -syntax camlp4o -package lwt,js_of_ocaml.syntax
+OCAMLPPFLAGS= -syntax camlp4o -package lwt,js_of_ocaml.syntax
 
-BYTE_ENABLED = true
-NATIVE_ENABLED = false
+MyOCamlJSProgram(name, files) =
+	#OCAML_PREINSTALLED_PACKS[] +=
+	OCAMLPACKS[] += lwt js_of_ocaml
+
+	public.OCAML_BYTE_LINK_FLAGS = -linkpkg # removes -custom
+
+	clean:
+		rm -f *~ $(name) *.run *.opt *.cmi *.cmo *.cmx *.o *.omc *.cmt *.cmti *.annot
+
+	.DEFAULT: $(OCamlProgram $(name), $(files))
+
+	export # Need to export the rules for lwt and others
+
+
+	$(name).js: $(name).run
+		js_of_ocaml $<
 
-clean:
-	rm -f *~ $(PROGRAM) *.run *.opt *.cmi *.cmo *.cmx *.o *.omc *.cmt *.cmti *.annot
+	.DEFAULT: $(name).js
 
-.DEFAULT: $(OCamlProgram $(PROGRAM), $(FILES))
-	js_of_ocaml ./$(PROGRAM)
+	export
 
+.SUBDIRS: js_of_ocaml_game1

game.ml

-(* see alse, The original code is below.
- * http://d.hatena.ne.jp/sunflat/20110305/p1 
- * http://www2.sunflat.net/files/ocamljs_game1/game1.html *)
-
-(*
- * The changes,
- * - not use mutable.
- * - change to js_of_ocaml from OCamlJS.
- *)
-
-let debug f = Printf.ksprintf (fun s -> Firebug.console##log(Js.string s)) f
-let (@@) f x = f x
-let ($) g f = fun x -> g (f x)
-let id x = x
-let tee f x = ignore @@ f x; x
-let (|>) x f = f x
-
-let fint = float_of_int
-let sint = string_of_int
-
-type pos_t = {
-  x : int;
-  y : int;
-}
-
-type gameState = GameInit | GameMain | GameOver
-
-type gameObject =
-| Ship of pos_t
-| Bullet of pos_t
-| Enemy of pos_t
-
-type gameVariable = {
-  canvas : Dom_html.canvasElement Js.t;
-  os : gameObject list;
-  cleft: int;
-  ctop: int;
-  cwidth: int;
-  cheight: int;
-  score : int;
-  mouse : pos_t;
-  mousePressed : bool;
-  state : gameState;
-}
-
-let bulletSpeed g = 5
-
-let enemySpeed g = 1+(g.score / 5)
-
-let getPos = function
-  | Ship pos
-  | Bullet pos
-  | Enemy pos -> pos
-
-let getSize = function
-  | Ship _      -> {x=16; y=16}
-  | Bullet _    -> {x=4; y=4}
-  | Enemy _     -> {x=8; y=8}
-
-let getShip g =
-  let f = function
-    | Ship _ -> true
-    | _ -> false
-  in
-  List.find f g.os
-
-let moveObject g obj =
-  match obj with
-  | Bullet pos -> 
-      Bullet { pos with y = pos.y - (bulletSpeed g) }
-  | Enemy pos ->
-      Enemy { pos with y = pos.y + (enemySpeed g) }
-  | Ship _ ->
-      let {x=sx; y=sy} = getSize obj in
-      Ship {x=min (max g.mouse.x sx) (g.cwidth-sx);
-            y=min (max g.mouse.y sy) (g.cheight-sy) }
-
-let drawObject g ctx obj =
-  match obj with
-  | Bullet pos -> 
-      ctx##fillStyle <- Js.string "rgb(255,255,0)";
-      ctx##fillRect (fint (pos.x - 4), fint (pos.y - 4), 8., 8.)
-  | Enemy pos ->
-      ctx##fillStyle <- Js.string "rgb(0,255,255)";
-      ctx##fillRect (fint (pos.x - 8), fint (pos.y - 8), 16., 16.)
-  | Ship pos ->
-      ctx##fillStyle <- 
-      if g.state <> GameOver then
-        Js.string "rgb(0,255,0)"
-      else
-        Js.string "rgb(255,128,0)";
-      ctx##fillRect (fint (pos.x - 16), fint (pos.y - 16), 32., 32.)
-
-let gcObject g =
-  let check = function
-    | Bullet pos -> pos.y > -4
-    | Enemy pos -> pos.y < (g.cheight + 16)
-    | _ -> true
-  in
-  let os' = List.filter check g.os in
-  { g with os = os' }
-
-let newBullet g =
-  let ship_pos = getPos (getShip g) in
-  Bullet {x=ship_pos.x; y=ship_pos.y}
-
-let newEnemy g =
-  Enemy {x=Random.int g.cwidth; y=(-16)}
-
-let hit src tgt =
-  let {x=aX; y=aY}, {x=bX; y=bY} = getPos src, getPos tgt in
-  let {x=aW; y=aH}, {x=bW; y=bH} = getSize src, getSize tgt in
-  abs (aX-bX) < aW+bW && abs (aY-bY) < aH+bH
-
-let collide g =
-  let score = ref g.score in
-  let gameover = ref false in
-  let affect src tgt =
-    match src, tgt with
-    | Bullet _, Enemy pos ->
-        score := !score + 1;
-        (* delete the enemy *)
-        Enemy {pos with y=g.cheight + 100}
-    | Enemy _, Bullet pos ->
-        (* delete the bullet *)
-        Bullet {pos with y=(-100)}
-    | Ship _, Enemy _
-    | Enemy _, Ship _ ->
-        gameover := true;
-        tgt
-    | _, _ -> tgt
-  in
-  let check obj =
-    let f tgt src = 
-      if hit src tgt then affect src tgt
-      else tgt
-    in
-    List.fold_left f obj g.os
-  in
-  let os' = List.map check g.os in
-  { g with os = os'; score = !score;
-           state = if !gameover then GameOver else g.state }
-
-let update g =
-  match g.state with
-  |GameInit -> 
-      (* move object *)
-      let g = {g with os = List.map (moveObject g) g.os} in
-      (* click to start *)
-      if g.mousePressed then
-        {g with state = GameMain; mousePressed = false }
-      else
-        g
-  |GameMain ->
-      (* shoot *)
-      let g = 
-        if g.mousePressed then 
-          {g with os = newBullet g :: g.os; mousePressed = false}
-        else
-          g
-      in
-      (* update enemies *)
-      let g = 
-        if (Random.int (30 / (enemySpeed g))) == 0 then 
-          {g with os = newEnemy g :: g.os}
-        else
-          g
-      in
-      (* move object *)
-      let g = {g with os = List.map (moveObject g) g.os} in
-      (* collision detection *)
-      let g = collide g in
-      (* delete unnecessary objects *)
-      gcObject g
-  |GameOver -> g
-
-let draw g =
-  let ctx = g.canvas##getContext (Dom_html._2d_) in
-  (* draw the background *)
-  (match g.state with
-   |GameInit |GameMain ->
-       ctx##fillStyle <- Js.string "#000000"
-   |GameOver ->
-       ctx##fillStyle <- Js.string "#FF0000" );
-  ctx##fillRect (0., 0., (fint g.cwidth), (fint g.cheight));
-  (* draw objects *)
-  List.iter (drawObject g ctx) g.os ;
-  (* draw text *)
-  ctx##font <- Js.string "20pt Arial";
-  ctx##fillStyle <- Js.string "#FFFFFF";
-  ctx##fillText (Js.string @@ string_of_int g.score, 10., 30.);
-  (* ctx##fillText (Js.string @@ string_of_int @@ List.length g.os, 10., 60.); *)
-  match g.state with
-  |GameInit ->
-      ctx##fillText (Js.string "Click to Start", 150., 200.)
-  |GameMain ->
-      ()
-  |GameOver ->
-      ctx##fillText (Js.string "Reload the page to restart", 100., 200.)
-
-let onMouseDown rg ev =
-  let pressed = (Dom_html.buttonPressed ev) = Dom_html.Left_button in
-  let gv = {!rg with mousePressed = pressed } in
-  rg := gv;
-  Js._false
-
-let onMouseMove rg ev =
-  let mx, my = Dom_html.eventAbsolutePosition ev in
-  let gv = {!rg with mouse = {x=mx; y=my}; } in
-  rg := gv;
-  Js._false
-
-let onInterval rgv _ =
-  let gv = update !rgv in
-  let gv = update gv in
-  draw gv;
-  rgv := gv
-
-let create_canvas () =
-  let d = Dom_html.window##document in
-  let c = Dom_html.createCanvas d in
-  c##width <- 480;
-  c##height <- 320;
-  c
-
-let initGameVariable () =
-  { canvas = create_canvas ();
-    os = [ Ship {x=0; y=0} ];
-    cleft = 0;
-    ctop = 0;
-    cwidth = 480;
-    cheight = 320;
-    score = 0;
-    mouse = {x=0; y=0};
-    mousePressed = false;
-    state = GameInit }
-
-let start _ =
-  let open Dom_html in
-  let window = window in
-  let document = window##document in
-  let body = document##body in
-  let gv = initGameVariable () in
-  let rgv = ref gv in
-  let interavl = 1000. /. 30. in (* 30fps *)
-  let id = window##setInterval (Js.wrap_callback (onInterval rgv), interavl) in
-  let target = (document :> eventTarget Js.t) in
-  addEventListener target Event.mousemove (handler @@ onMouseMove rgv) Js._false |> ignore;
-  addEventListener target Event.mousedown (handler @@ onMouseDown rgv) Js._false |> ignore;
-  Dom.appendChild body gv.canvas;
-  Js._false
-
-let () =
-  Dom_html.window##onload <- Dom_html.handler start

js_of_ocaml_game1/OMakefile

+FILES[] =
+	game1
+
+MyOCamlJSProgram(game1, $(FILES))

js_of_ocaml_game1/game1.html

+<html>
+  <head>
+  </head>
+  <body>
+    <script src='./testcase.js'></script>
+  </body>
+</html>

js_of_ocaml_game1/game1.js

+// This program was compiled from OCaml by js_of_ocaml 1.3
+function caml_raise_with_arg (tag, arg) { throw [0, tag, arg]; }
+function caml_raise_with_string (tag, msg) {
+  caml_raise_with_arg (tag, new MlWrappedString (msg));
+}
+function caml_invalid_argument (msg) {
+  caml_raise_with_string(caml_global_data[4], msg);
+}
+function caml_array_bound_error () {
+  caml_invalid_argument("index out of bounds");
+}
+function caml_str_repeat(n, s) {
+  if (!n) { return ""; }
+  if (n & 1) { return caml_str_repeat(n - 1, s) + s; }
+  var r = caml_str_repeat(n >> 1, s);
+  return r + r;
+}
+function MlString(param) {
+  if (param != null) {
+    this.bytes = this.fullBytes = param;
+    this.last = this.len = param.length;
+  }
+}
+MlString.prototype = {
+  string:null,
+  bytes:null,
+  fullBytes:null,
+  array:null,
+  len:null,
+  last:0,
+  toJsString:function() {
+    return this.string = decodeURIComponent (escape(this.getFullBytes()));
+  },
+  toBytes:function() {
+    if (this.string != null)
+      var b = unescape (encodeURIComponent (this.string));
+    else {
+      var b = "", a = this.array, l = a.length;
+      for (var i = 0; i < l; i ++) b += String.fromCharCode (a[i]);
+    }
+    this.bytes = this.fullBytes = b;
+    this.last = this.len = b.length;
+    return b;
+  },
+  getBytes:function() {
+    var b = this.bytes;
+    if (b == null) b = this.toBytes();
+    return b;
+  },
+  getFullBytes:function() {
+    var b = this.fullBytes;
+    if (b !== null) return b;
+    b = this.bytes;
+    if (b == null) b = this.toBytes ();
+    if (this.last < this.len) {
+      this.bytes = (b += caml_str_repeat(this.len - this.last, '\0'));
+      this.last = this.len;
+    }
+    this.fullBytes = b;
+    return b;
+  },
+  toArray:function() {
+    var b = this.bytes;
+    if (b == null) b = this.toBytes ();
+    var a = [], l = this.last;
+    for (var i = 0; i < l; i++) a[i] = b.charCodeAt(i);
+    for (l = this.len; i < l; i++) a[i] = 0;
+    this.string = this.bytes = this.fullBytes = null;
+    this.last = this.len;
+    this.array = a;
+    return a;
+  },
+  getArray:function() {
+    var a = this.array;
+    if (!a) a = this.toArray();
+    return a;
+  },
+  getLen:function() {
+    var len = this.len;
+    if (len !== null) return len;
+    this.toBytes();
+    return this.len;
+  },
+  toString:function() { var s = this.string; return s?s:this.toJsString(); },
+  valueOf:function() { var s = this.string; return s?s:this.toJsString(); },
+  blitToArray:function(i1, a2, i2, l) {
+    var a1 = this.array;
+    if (a1) {
+      if (i2 <= i1) {
+        for (var i = 0; i < l; i++) a2[i2 + i] = a1[i1 + i];
+      } else {
+        for (var i = l - 1; i >= 0; i--) a2[i2 + i] = a1[i1 + i];
+      }
+    } else {
+      var b = this.bytes;
+      if (b == null) b = this.toBytes();
+      var l1 = this.last - i1;
+      if (l <= l1)
+        for (var i = 0; i < l; i++) a2 [i2 + i] = b.charCodeAt(i1 + i);
+      else {
+        for (var i = 0; i < l1; i++) a2 [i2 + i] = b.charCodeAt(i1 + i);
+        for (; i < l; i++) a2 [i2 + i] = 0;
+      }
+    }
+  },
+  get:function (i) {
+    var a = this.array;
+    if (a) return a[i];
+    var b = this.bytes;
+    if (b == null) b = this.toBytes();
+    return (i<this.last)?b.charCodeAt(i):0;
+  },
+  safeGet:function (i) {
+    if (!this.len) this.toBytes();
+    if ((i < 0) || (i >= this.len)) caml_array_bound_error ();
+    return this.get(i);
+  },
+  set:function (i, c) {
+    var a = this.array;
+    if (!a) {
+      if (this.last == i) {
+        this.bytes += String.fromCharCode (c & 0xff);
+        this.last ++;
+        return 0;
+      }
+      a = this.toArray();
+    } else if (this.bytes != null) {
+      this.bytes = this.fullBytes = this.string = null;
+    }
+    a[i] = c & 0xff;
+    return 0;
+  },
+  safeSet:function (i, c) {
+    if (this.len == null) this.toBytes ();
+    if ((i < 0) || (i >= this.len)) caml_array_bound_error ();
+    this.set(i, c);
+  },
+  fill:function (ofs, len, c) {
+    if (ofs >= this.last && this.last && c == 0) return;
+    var a = this.array;
+    if (!a) a = this.toArray();
+    else if (this.bytes != null) {
+      this.bytes = this.fullBytes = this.string = null;
+    }
+    var l = ofs + len;
+    for (var i = ofs; i < l; i++) a[i] = c;
+  },
+  compare:function (s2) {
+    if (this.string != null && s2.string != null) {
+      if (this.string < s2.string) return -1;
+      if (this.string > s2.string) return 1;
+      return 0;
+    }
+    var b1 = this.getFullBytes ();
+    var b2 = s2.getFullBytes ();
+    if (b1 < b2) return -1;
+    if (b1 > b2) return 1;
+    return 0;
+  },
+  equal:function (s2) {
+    if (this.string != null && s2.string != null)
+      return this.string == s2.string;
+    return this.getFullBytes () == s2.getFullBytes ();
+  },
+  lessThan:function (s2) {
+    if (this.string != null && s2.string != null)
+      return this.string < s2.string;
+    return this.getFullBytes () < s2.getFullBytes ();
+  },
+  lessEqual:function (s2) {
+    if (this.string != null && s2.string != null)
+      return this.string <= s2.string;
+    return this.getFullBytes () <= s2.getFullBytes ();
+  }
+}
+function MlWrappedString (s) { this.string = s; }
+MlWrappedString.prototype = new MlString();
+function MlMakeString (l) { this.bytes = ""; this.len = l; }
+MlMakeString.prototype = new MlString ();
+function caml_array_get (array, index) {
+  if ((index < 0) || (index >= array.length - 1)) caml_array_bound_error();
+  return array[index+1];
+}
+function caml_array_set (array, index, newval) {
+  if ((index < 0) || (index >= array.length - 1)) caml_array_bound_error();
+  array[index+1]=newval; return 0;
+}
+function caml_call_gen(f, args) {
+  if(f.fun)
+    return caml_call_gen(f.fun, args);
+  var n = f.length;
+  var d = n - args.length;
+  if (d == 0)
+    return f.apply(null, args);
+  else if (d < 0)
+    return caml_call_gen(f.apply(null, args.slice(0,n)), args.slice(n));
+  else
+    return function (x){ return caml_call_gen(f, args.concat([x])); };
+}
+function caml_raise_constant (tag) { throw [0, tag]; }
+var caml_global_data = [0];
+function caml_raise_zero_divide () {
+  caml_raise_constant(caml_global_data[6]);
+}
+function caml_div(x,y) {
+  if (y == 0) caml_raise_zero_divide ();
+  return (x/y)|0;
+}
+function caml_parse_format (fmt) {
+  fmt = fmt.toString ();
+  var len = fmt.length;
+  if (len > 31) caml_invalid_argument("format_int: format too long");
+  var f =
+    { justify:'+', signstyle:'-', filler:' ', alternate:false,
+      base:0, signedconv:false, width:0, uppercase:false,
+      sign:1, prec:-1, conv:'f' };
+  for (var i = 0; i < len; i++) {
+    var c = fmt.charAt(i);
+    switch (c) {
+    case '-':
+      f.justify = '-'; break;
+    case '+': case ' ':
+      f.signstyle = c; break;
+    case '0':
+      f.filler = '0'; break;
+    case '#':
+      f.alternate = true; break;
+    case '1': case '2': case '3': case '4': case '5':
+    case '6': case '7': case '8': case '9':
+      f.width = 0;
+      while (c=fmt.charCodeAt(i) - 48, c >= 0 && c <= 9) {
+        f.width = f.width * 10 + c; i++
+      }
+      i--;
+     break;
+    case '.':
+      f.prec = 0;
+      i++;
+      while (c=fmt.charCodeAt(i) - 48, c >= 0 && c <= 9) {
+        f.prec = f.prec * 10 + c; i++
+      }
+      i--;
+    case 'd': case 'i':
+      f.signedconv = true; /* fallthrough */
+    case 'u':
+      f.base = 10; break;
+    case 'x':
+      f.base = 16; break;
+    case 'X':
+      f.base = 16; f.uppercase = true; break;
+    case 'o':
+      f.base = 8; break;
+    case 'e': case 'f': case 'g':
+      f.signedconv = true; f.conv = c; break;
+    case 'E': case 'F': case 'G':
+      f.signedconv = true; f.uppercase = true;
+      f.conv = c.toLowerCase (); break;
+    }
+  }
+  return f;
+}
+function caml_finish_formatting(f, rawbuffer) {
+  if (f.uppercase) rawbuffer = rawbuffer.toUpperCase();
+  var len = rawbuffer.length;
+  if (f.signedconv && (f.sign < 0 || f.signstyle != '-')) len++;
+  if (f.alternate) {
+    if (f.base == 8) len += 1;
+    if (f.base == 16) len += 2;
+  }
+  var buffer = "";
+  if (f.justify == '+' && f.filler == ' ')
+    for (var i = len; i < f.width; i++) buffer += ' ';
+  if (f.signedconv) {
+    if (f.sign < 0) buffer += '-';
+    else if (f.signstyle != '-') buffer += f.signstyle;
+  }
+  if (f.alternate && f.base == 8) buffer += '0';
+  if (f.alternate && f.base == 16) buffer += "0x";
+  if (f.justify == '+' && f.filler == '0')
+    for (var i = len; i < f.width; i++) buffer += '0';
+  buffer += rawbuffer;
+  if (f.justify == '-')
+    for (var i = len; i < f.width; i++) buffer += ' ';
+  return new MlWrappedString (buffer);
+}
+function caml_format_int(fmt, i) {
+  if (fmt.toString() == "%d") return new MlWrappedString(""+i);
+  var f = caml_parse_format(fmt);
+  if (i < 0) { if (f.signedconv) { f.sign = -1; i = -i; } else i >>>= 0; }
+  var s = i.toString(f.base);
+  if (f.prec >= 0) {
+    f.filler = ' ';
+    var n = f.prec - s.length;
+    if (n > 0) s = caml_str_repeat (n, '0') + s;
+  }
+  return caml_finish_formatting(f, s);
+}
+function caml_int64_compare(x,y) {
+  var x3 = x[3] << 16;
+  var y3 = y[3] << 16;
+  if (x3 > y3) return 1;
+  if (x3 < y3) return -1;
+  if (x[2] > y[2]) return 1;
+  if (x[2] < y[2]) return -1;
+  if (x[1] > y[1]) return 1;
+  if (x[1] < y[1]) return -1;
+  return 0;
+}
+function caml_int_compare (a, b) {
+  if (a < b) return (-1); if (a == b) return 0; return 1;
+}
+function caml_compare_val (a, b, total) {
+  var stack = [];
+  for(;;) {
+    if (!(total && a === b)) {
+      if (a instanceof MlString) {
+        if (b instanceof MlString) {
+            if (a != b) {
+		var x = a.compare(b);
+		if (x != 0) return x;
+	    }
+        } else
+          return 1;
+      } else if (a instanceof Array && a[0] === (a[0]|0)) {
+        var ta = a[0];
+        if (ta === 250) {
+          a = a[1];
+          continue;
+        } else if (b instanceof Array && b[0] === (b[0]|0)) {
+          var tb = b[0];
+          if (tb === 250) {
+            b = b[1];
+            continue;
+          } else if (ta != tb) {
+            return (ta < tb)?-1:1;
+          } else {
+            switch (ta) {
+            case 248: {
+		var x = caml_int_compare(a[2], b[2]);
+		if (x != 0) return x;
+		break;
+	    }
+            case 255: {
+		var x = caml_int64_compare(a, b);
+		if (x != 0) return x;
+		break;
+	    }
+            default:
+              if (a.length != b.length) return (a.length < b.length)?-1:1;
+              if (a.length > 1) stack.push(a, b, 1);
+            }
+          }
+        } else
+          return 1;
+      } else if (b instanceof MlString ||
+                 (b instanceof Array && b[0] === (b[0]|0))) {
+        return -1;
+      } else {
+        if (a < b) return -1;
+        if (a > b) return 1;
+        if (total && a != b) {
+          if (a == a) return 1;
+          if (b == b) return -1;
+        }
+      }
+    }
+    if (stack.length == 0) return 0;
+    var i = stack.pop();
+    b = stack.pop();
+    a = stack.pop();
+    if (i + 1 < a.length) stack.push(a, b, i + 1);
+    a = a[i];
+    b = b[i];
+  }
+}
+function caml_compare (a, b) { return caml_compare_val (a, b, true); }
+function caml_greaterequal (x, y) { return +(caml_compare(x,y,false) >= 0); }
+function caml_js_call(f, o, args) { return f.apply(o, args.slice(1)); }
+function caml_js_wrap_callback(f) {
+  var toArray = Array.prototype.slice;
+  return function () {
+    var args = (arguments.length > 0)?toArray.call (arguments):[undefined];
+    return caml_call_gen(f, args);
+  }
+}
+function caml_lessequal (x, y) { return +(caml_compare(x,y,false) <= 0); }
+function caml_ml_out_channels_list () { return 0; }
+function caml_mod(x,y) {
+  if (y == 0) caml_raise_zero_divide ();
+  return x%y;
+}
+function caml_register_global (n, v) { caml_global_data[n + 1] = v; }
+var caml_named_values = {};
+function caml_register_named_value(nm,v) {
+  caml_named_values[nm] = v; return 0;
+}
+function caml_sys_get_config () {
+  return [0, new MlWrappedString("Unix"), 32, 0];
+}
+(function(){function ce(dg,dh,di){return dg.length==2?dg(dh,di):caml_call_gen(dg,[dh,di]);}function Q(de,df){return de.length==1?de(df):caml_call_gen(de,[df]);}var a=[0,new MlString("Invalid_argument")],b=[0,new MlString("Not_found")];caml_register_global(6,b);caml_register_global(5,[0,new MlString("Division_by_zero")]);caml_register_global(3,a);caml_register_global(2,[0,new MlString("Failure")]);var G=new MlString("%d"),F=new MlString("Pervasives.do_at_exit"),E=new MlString("Random.int"),D=[0,2061652523,1569539636,364182224,414272206,318284740,2064149575,383018966,1344115143,840823159,1098301843,536292337,1586008329,189156120,1803991420,1217518152,51606627,1213908385,366354223,2077152089,1774305586,2055632494,913149062,526082594,2095166879,784300257,1741495174,1703886275,2023391636,1122288716,1489256317,258888527,511570777,1163725694,283659902,308386020,1316430539,1556012584,1938930020,2101405994,1280938813,193777847,1693450012,671350186,149669678,1330785842,1161400028,558145612,1257192637,1101874969,1975074006,710253903,1584387944,1726119734,409934019,801085050],C=new MlString("on"),B=new MlString("canvas"),A=new MlString("mousedown"),z=new MlString("mousemove"),y=new MlString("2d"),x=new MlString("Dom_html.Canvas_not_available"),w=[0,0,0],v=[0,[0,[0,0,0]],0],u=new MlString("#FF0000"),t=new MlString("#000000"),s=new MlString("20pt Arial"),r=new MlString("#FFFFFF"),q=new MlString("Click to Start"),p=new MlString("Reload the page to restart"),o=new MlString("rgb(0,255,0)"),n=new MlString("rgb(255,128,0)"),m=new MlString("rgb(255,255,0)"),l=new MlString("rgb(0,255,255)"),k=[0,16,16],j=[0,4,4],i=[0,8,8];function h(d,c){return caml_lessequal(d,c)?d:c;}function H(f,e){return caml_greaterequal(f,e)?f:e;}function I(g){return 0<=g?g:-g|0;}function N(M){var J=caml_ml_out_channels_list(0);for(;;){if(J){var K=J[2];try {}catch(L){}var J=K;continue;}return 0;}}caml_register_named_value(F,N);function S(P,O){if(O){var R=O[2],T=Q(P,O[1]);return [0,T,S(P,R)];}return 0;}function ae(_){return Q(function(U,W){var V=U,X=W;for(;;){if(X){var Y=X[2],Z=X[1];if(Q(_,Z)){var $=[0,Z,V],V=$,X=Y;continue;}var X=Y;continue;}var aa=V,ab=0;for(;;){if(aa){var ac=aa[2],ad=[0,aa[1],ab],aa=ac,ab=ad;continue;}return ab;}}},0);}var af=[0,0];32===caml_sys_get_config(0)[2];var ag=[0,D.slice(),0];function al(ah){if(!(1073741823<ah)&&0<ah)for(;;){ag[2]=(ag[2]+1|0)%55|0;var ai=caml_array_get(ag[1],ag[2]),aj=(caml_array_get(ag[1],(ag[2]+24|0)%55|0)+(ai^ai>>>25&31)|0)&1073741823;caml_array_set(ag[1],ag[2],aj);var ak=caml_mod(aj,ah);if(((1073741823-ah|0)+1|0)<(aj-ak|0))continue;return ak;}throw [0,a,E];}var am=undefined,ar=null;function aq(an,ao,ap){return an===am?Q(ao,0):Q(ap,an);}var as=false,au=Array;function av(at){return at instanceof au?0:[0,new MlWrappedString(at.toString())];}af[1]=[0,av,af[1]];function aP(ax){return caml_js_wrap_callback(function(aw){if(aw){var ay=Q(ax,aw);if(!(ay|0))aw.preventDefault();return ay;}var az=event,aA=Q(ax,az);az.returnValue=aA;return aA;});}function aQ(aB){return aB.toString();}function aR(aC,aD,aG,aN){if(aC.addEventListener===am){var aE=C.toString().concat(aD),aL=function(aF){var aK=[0,aG,aF,[0]];return Q(function(aJ,aI,aH){return caml_js_call(aJ,aI,aH);},aK);};aC.attachEvent(aE,aL);return function(aM){return aC.detachEvent(aE,aL);};}aC.addEventListener(aD,aG,aN);return function(aO){return aC.removeEventListener(aD,aG,aN);};}var aS=aQ(A),aT=aQ(z),aU=this,aV=aU.document,aX=y.toString(),aW=[0,x];this.HTMLElement===am;function a1(a0){var aY=aV.body,aZ=aV.documentElement;return [0,(a0.clientX+aY.scrollLeft|0)+aZ.scrollLeft|0,(a0.clientY+aY.scrollTop|0)+aZ.scrollTop|0];}function cT(a3,a2){return Q(a3,a2);}function c$(a4,a5){return Q(a5,a4);}function bo(a6){return a6;}function bb(a7){return 1+(a7[7]/5|0)|0;}function bC(a8){return a8[1];}function be(a9){switch(a9[0]){case 1:return j;case 2:return i;default:return k;}}function bK(bc,a_){switch(a_[0]){case 1:var a$=a_[1];return [1,[0,a$[1],a$[2]-5|0]];case 2:var ba=a_[1],bd=bb(bc);return [2,[0,ba[1],ba[2]+bd|0]];default:var bf=be(a_),bg=bf[2],bh=bf[1],bi=bc[6]-bg|0,bj=h(H(bc[8][2],bg),bi),bk=bc[5]-bh|0;return [0,[0,h(H(bc[8][1],bh),bk),bj]];}}function cK(bt,bn,bl){switch(bl[0]){case 1:var bm=bl[1];bn.fillStyle=m.toString();var bp=bo(bm[2]-4|0);return bn.fillRect(bo(bm[1]-4|0),bp,8,8);case 2:var bq=bl[1];bn.fillStyle=l.toString();var br=bo(bq[2]-8|0);return bn.fillRect(bo(bq[1]-8|0),br,16,16);default:var bs=bl[1],bu=2===bt[10]?n.toString():o.toString();bn.fillStyle=bu;var bv=bo(bs[2]-16|0);return bn.fillRect(bo(bs[1]-16|0),bv,32,32);}}function cG(bw){switch(bw[10]){case 1:if(bw[9]){var bx=bw.slice(),by=bw[2],bE=bw[2];for(;;){if(!by)throw [0,b];var bz=by[1],bB=by[2],bA=0===bz[0]?1:0;if(!bA){var by=bB;continue;}var bD=bC(bz);bx[2]=[0,[1,[0,bD[1],bD[2]]],bE];bx[9]=0;var bF=bx;break;}}else var bF=bw;if(0===al(caml_div(30,bb(bF)))){var bG=bF.slice(),bH=bF[2];bG[2]=[0,[2,[0,al(bF[5]),-16]],bH];var bI=bG;}else var bI=bF;var bJ=bI.slice(),bL=bI[2];bJ[2]=S(Q(bK,bI),bL);var bM=[0,bJ[7]],bN=[0,0],b_=function(bO){var bP=bO,bQ=bJ[2];for(;;){if(bQ){var bR=bQ[1],bT=bQ[2],bS=bC(bP),bU=bC(bR),bZ=bS[2],bY=bS[1],bX=bU[2],bW=bU[1],bV=be(bP),b0=be(bR),b3=bV[2],b2=b0[2],b1=b0[1]+bV[1]|0,b4=I(bW-bY|0)<b1?1:0,b5=b4?I(bX-bZ|0)<(b2+b3|0)?1:0:b4;if(b5){switch(bR[0]){case 1:if(2===bP[0]){var b6=bP[1];bM[1]=bM[1]+1|0;var b7=[2,[0,b6[1],bJ[6]+100|0]],b8=2;}else var b8=0;break;case 2:switch(bP[0]){case 2:var b8=0;break;case 0:var b8=1;break;default:var b7=[1,[0,bP[1][1],-100]],b8=2;}break;default:var b8=2===bP[0]?1:0;}switch(b8){case 1:bN[1]=1;var b7=bP;break;case 2:break;default:var b7=bP;}var b9=b7;}else var b9=bP;var bP=b9,bQ=bT;continue;}return bP;}},ca=S(b_,bJ[2]),b$=bJ.slice();b$[2]=ca;b$[7]=bM[1];var cb=bN[1]?2:bJ[10];b$[10]=cb;var cd=function(cc){switch(cc[0]){case 1:return -4<cc[1][2]?1:0;case 2:return cc[1][2]<(b$[6]+16|0)?1:0;default:return 1;}},cg=ce(ae,cd,b$[2]),cf=b$.slice();cf[2]=cg;return cf;case 2:return bw;default:var ch=bw.slice(),ci=bw[2];ch[2]=S(Q(bK,bw),ci);if(ch[9]){var cj=ch.slice();cj[9]=0;cj[10]=1;return cj;}return ch;}}function db(cq,cl){function co(ck){return ck;}function cp(cn){var cm=cl.button-1|0;if(!(cm<0||3<cm))switch(cm){case 1:return 3;case 2:break;case 3:return 2;default:return 1;}return 0;}var cr=1===aq(cl.which,cp,co)?1:0,cs=cq[1].slice();cs[9]=cr;cq[1]=cs;return as;}function c9(cD,cv){function cA(cu){function cx(ct){return [0,cu,ct];}function cy(cw){return a1(cv);}return aq(cv.pageY,cy,cx);}function cB(cz){return a1(cv);}var cC=aq(cv.pageX,cB,cA),cE=cD[1].slice();cE[8]=[0,cC[1],cC[2]];cD[1]=cE;return as;}function c7(cF,cU){var cH=cG(cG(cF[1])),cI=cH[1].getContext(aX);if(2<=cH[10])cI.fillStyle=u.toString();else cI.fillStyle=t.toString();var cJ=bo(cH[6]);cI.fillRect(0,0,bo(cH[5]),cJ);var cL=cH[2],cM=cL,cN=ce(cK,cH,cI);for(;;){if(cM){var cO=cM[2];Q(cN,cM[1]);var cM=cO;continue;}cI.font=s.toString();cI.fillStyle=r.toString();var cS=30,cR=10,cQ=caml_format_int(G,cH[7]);cI.fillText(cT(function(cP){return cP.toString();},cQ),cR,cS);switch(cH[10]){case 1:break;case 2:cI.fillText(p.toString(),100,200);break;default:cI.fillText(q.toString(),150,200);}cF[1]=cH;return 0;}}aU.onload=aP(function(dd){var cV=aU.document,cX=cV.body,cW=aU.document.createElement(B.toString()),cY=0,cZ=0,c0=0,c1=320,c2=480,c3=0,c4=0;if(1-(cW.getContext==ar?1:0)){cW.width=480;cW.height=320;var c5=[0,cW,v,c4,c3,c2,c1,c0,w,cZ,cY],c6=[0,c5];aU.setInterval(caml_js_wrap_callback(Q(c7,c6)),1000/30);var c_=function(c8){return 0;};c$(aR(cV,aT,cT(aP,Q(c9,c6)),as),c_);var dc=function(da){return 0;};c$(aR(cV,aS,cT(aP,Q(db,c6)),as),dc);cX.appendChild(c5[1]);return as;}throw [0,aW];});N(0);return;}());

js_of_ocaml_game1/game1.ml

+(* see alse, The original code is below.
+ * http://d.hatena.ne.jp/sunflat/20110305/p1 
+ * http://www2.sunflat.net/files/ocamljs_game1/game1.html *)
+
+(*
+ * The changes,
+ * - not use mutable.
+ * - change to js_of_ocaml from OCamlJS.
+ *)
+
+let debug f = Printf.ksprintf (fun s -> Firebug.console##log(Js.string s)) f
+let (@@) f x = f x
+let ($) g f = fun x -> g (f x)
+let id x = x
+let tee f x = ignore @@ f x; x
+let (|>) x f = f x
+
+let fint = float_of_int
+let sint = string_of_int
+
+type pos_t = {
+  x : int;
+  y : int;
+}
+
+type gameState = GameInit | GameMain | GameOver
+
+type gameObject =
+| Ship of pos_t
+| Bullet of pos_t
+| Enemy of pos_t
+
+type gameVariable = {
+  canvas : Dom_html.canvasElement Js.t;
+  os : gameObject list;
+  cleft: int;
+  ctop: int;
+  cwidth: int;
+  cheight: int;
+  score : int;
+  mouse : pos_t;
+  mousePressed : bool;
+  state : gameState;
+}
+
+let bulletSpeed g = 5
+
+let enemySpeed g = 1+(g.score / 5)
+
+let getPos = function
+  | Ship pos
+  | Bullet pos
+  | Enemy pos -> pos
+
+let getSize = function
+  | Ship _      -> {x=16; y=16}
+  | Bullet _    -> {x=4; y=4}
+  | Enemy _     -> {x=8; y=8}
+
+let getShip g =
+  let f = function
+    | Ship _ -> true
+    | _ -> false
+  in
+  List.find f g.os
+
+let moveObject g obj =
+  match obj with
+  | Bullet pos -> 
+      Bullet { pos with y = pos.y - (bulletSpeed g) }
+  | Enemy pos ->
+      Enemy { pos with y = pos.y + (enemySpeed g) }
+  | Ship _ ->
+      let {x=sx; y=sy} = getSize obj in
+      Ship {x=min (max g.mouse.x sx) (g.cwidth-sx);
+            y=min (max g.mouse.y sy) (g.cheight-sy) }
+
+let drawObject g ctx obj =
+  match obj with
+  | Bullet pos -> 
+      ctx##fillStyle <- Js.string "rgb(255,255,0)";
+      ctx##fillRect (fint (pos.x - 4), fint (pos.y - 4), 8., 8.)
+  | Enemy pos ->
+      ctx##fillStyle <- Js.string "rgb(0,255,255)";
+      ctx##fillRect (fint (pos.x - 8), fint (pos.y - 8), 16., 16.)
+  | Ship pos ->
+      ctx##fillStyle <- 
+      if g.state <> GameOver then
+        Js.string "rgb(0,255,0)"
+      else
+        Js.string "rgb(255,128,0)";
+      ctx##fillRect (fint (pos.x - 16), fint (pos.y - 16), 32., 32.)
+
+let gcObject g =
+  let check = function
+    | Bullet pos -> pos.y > -4
+    | Enemy pos -> pos.y < (g.cheight + 16)
+    | _ -> true
+  in
+  let os' = List.filter check g.os in
+  { g with os = os' }
+
+let newBullet g =
+  let ship_pos = getPos (getShip g) in
+  Bullet {x=ship_pos.x; y=ship_pos.y}
+
+let newEnemy g =
+  Enemy {x=Random.int g.cwidth; y=(-16)}
+
+let hit src tgt =
+  let {x=aX; y=aY}, {x=bX; y=bY} = getPos src, getPos tgt in
+  let {x=aW; y=aH}, {x=bW; y=bH} = getSize src, getSize tgt in
+  abs (aX-bX) < aW+bW && abs (aY-bY) < aH+bH
+
+let collide g =
+  let score = ref g.score in
+  let gameover = ref false in
+  let affect src tgt =
+    match src, tgt with
+    | Bullet _, Enemy pos ->
+        score := !score + 1;
+        (* delete the enemy *)
+        Enemy {pos with y=g.cheight + 100}
+    | Enemy _, Bullet pos ->
+        (* delete the bullet *)
+        Bullet {pos with y=(-100)}
+    | Ship _, Enemy _
+    | Enemy _, Ship _ ->
+        gameover := true;
+        tgt
+    | _, _ -> tgt
+  in
+  let check obj =
+    let f tgt src = 
+      if hit src tgt then affect src tgt
+      else tgt
+    in
+    List.fold_left f obj g.os
+  in
+  let os' = List.map check g.os in
+  { g with os = os'; score = !score;
+           state = if !gameover then GameOver else g.state }
+
+let update g =
+  match g.state with
+  |GameInit -> 
+      (* move object *)
+      let g = {g with os = List.map (moveObject g) g.os} in
+      (* click to start *)
+      if g.mousePressed then
+        {g with state = GameMain; mousePressed = false }
+      else
+        g
+  |GameMain ->
+      (* shoot *)
+      let g = 
+        if g.mousePressed then 
+          {g with os = newBullet g :: g.os; mousePressed = false}
+        else
+          g
+      in
+      (* update enemies *)
+      let g = 
+        if (Random.int (30 / (enemySpeed g))) == 0 then 
+          {g with os = newEnemy g :: g.os}
+        else
+          g
+      in
+      (* move object *)
+      let g = {g with os = List.map (moveObject g) g.os} in
+      (* collision detection *)
+      let g = collide g in
+      (* delete unnecessary objects *)
+      gcObject g
+  |GameOver -> g
+
+let draw g =
+  let ctx = g.canvas##getContext (Dom_html._2d_) in
+  (* draw the background *)
+  (match g.state with
+   |GameInit |GameMain ->
+       ctx##fillStyle <- Js.string "#000000"
+   |GameOver ->
+       ctx##fillStyle <- Js.string "#FF0000" );
+  ctx##fillRect (0., 0., (fint g.cwidth), (fint g.cheight));
+  (* draw objects *)
+  List.iter (drawObject g ctx) g.os ;
+  (* draw text *)
+  ctx##font <- Js.string "20pt Arial";
+  ctx##fillStyle <- Js.string "#FFFFFF";
+  ctx##fillText (Js.string @@ string_of_int g.score, 10., 30.);
+  (* ctx##fillText (Js.string @@ string_of_int @@ List.length g.os, 10., 60.); *)
+  match g.state with
+  |GameInit ->
+      ctx##fillText (Js.string "Click to Start", 150., 200.)
+  |GameMain ->
+      ()
+  |GameOver ->
+      ctx##fillText (Js.string "Reload the page to restart", 100., 200.)
+
+let onMouseDown rg ev =
+  let pressed = (Dom_html.buttonPressed ev) = Dom_html.Left_button in
+  let gv = {!rg with mousePressed = pressed } in
+  rg := gv;
+  Js._false
+
+let onMouseMove rg ev =
+  let mx, my = Dom_html.eventAbsolutePosition ev in
+  let gv = {!rg with mouse = {x=mx; y=my}; } in
+  rg := gv;
+  Js._false
+
+let onInterval rgv _ =
+  let gv = update !rgv in
+  let gv = update gv in
+  draw gv;
+  rgv := gv
+
+let create_canvas () =
+  let d = Dom_html.window##document in
+  let c = Dom_html.createCanvas d in
+  c##width <- 480;
+  c##height <- 320;
+  c
+
+let initGameVariable () =
+  { canvas = create_canvas ();
+    os = [ Ship {x=0; y=0} ];
+    cleft = 0;
+    ctop = 0;
+    cwidth = 480;
+    cheight = 320;
+    score = 0;
+    mouse = {x=0; y=0};
+    mousePressed = false;
+    state = GameInit }
+
+let start _ =
+  let open Dom_html in
+  let window = window in
+  let document = window##document in
+  let body = document##body in
+  let gv = initGameVariable () in
+  let rgv = ref gv in
+  let interavl = 1000. /. 30. in (* 30fps *)
+  let id = window##setInterval (Js.wrap_callback (onInterval rgv), interavl) in
+  let target = (document :> eventTarget Js.t) in
+  addEventListener target Event.mousemove (handler @@ onMouseMove rgv) Js._false |> ignore;
+  addEventListener target Event.mousedown (handler @@ onMouseDown rgv) Js._false |> ignore;
+  Dom.appendChild body gv.canvas;
+  Js._false
+
+let () =
+  Dom_html.window##onload <- Dom_html.handler start

testcase.html

-<html>
-  <head>
-  </head>
-  <body>
-    <script src='./testcase.js'></script>
-  </body>
-</html>

testcase.js

-// This program was compiled from OCaml by js_of_ocaml 1.3
-function caml_raise_with_arg (tag, arg) { throw [0, tag, arg]; }
-function caml_raise_with_string (tag, msg) {
-  caml_raise_with_arg (tag, new MlWrappedString (msg));
-}
-function caml_invalid_argument (msg) {
-  caml_raise_with_string(caml_global_data[4], msg);
-}
-function caml_array_bound_error () {
-  caml_invalid_argument("index out of bounds");
-}
-function caml_str_repeat(n, s) {
-  if (!n) { return ""; }
-  if (n & 1) { return caml_str_repeat(n - 1, s) + s; }
-  var r = caml_str_repeat(n >> 1, s);
-  return r + r;
-}
-function MlString(param) {
-  if (param != null) {
-    this.bytes = this.fullBytes = param;
-    this.last = this.len = param.length;
-  }
-}
-MlString.prototype = {
-  string:null,
-  bytes:null,
-  fullBytes:null,
-  array:null,
-  len:null,
-  last:0,
-  toJsString:function() {
-    return this.string = decodeURIComponent (escape(this.getFullBytes()));
-  },
-  toBytes:function() {
-    if (this.string != null)
-      var b = unescape (encodeURIComponent (this.string));
-    else {
-      var b = "", a = this.array, l = a.length;
-      for (var i = 0; i < l; i ++) b += String.fromCharCode (a[i]);
-    }
-    this.bytes = this.fullBytes = b;
-    this.last = this.len = b.length;
-    return b;
-  },
-  getBytes:function() {
-    var b = this.bytes;
-    if (b == null) b = this.toBytes();
-    return b;
-  },
-  getFullBytes:function() {
-    var b = this.fullBytes;
-    if (b !== null) return b;
-    b = this.bytes;
-    if (b == null) b = this.toBytes ();
-    if (this.last < this.len) {
-      this.bytes = (b += caml_str_repeat(this.len - this.last, '\0'));
-      this.last = this.len;
-    }
-    this.fullBytes = b;
-    return b;
-  },
-  toArray:function() {
-    var b = this.bytes;
-    if (b == null) b = this.toBytes ();
-    var a = [], l = this.last;
-    for (var i = 0; i < l; i++) a[i] = b.charCodeAt(i);
-    for (l = this.len; i < l; i++) a[i] = 0;
-    this.string = this.bytes = this.fullBytes = null;
-    this.last = this.len;
-    this.array = a;
-    return a;
-  },
-  getArray:function() {
-    var a = this.array;
-    if (!a) a = this.toArray();
-    return a;
-  },
-  getLen:function() {
-    var len = this.len;
-    if (len !== null) return len;
-    this.toBytes();
-    return this.len;
-  },
-  toString:function() { var s = this.string; return s?s:this.toJsString(); },
-  valueOf:function() { var s = this.string; return s?s:this.toJsString(); },
-  blitToArray:function(i1, a2, i2, l) {
-    var a1 = this.array;
-    if (a1) {
-      if (i2 <= i1) {
-        for (var i = 0; i < l; i++) a2[i2 + i] = a1[i1 + i];
-      } else {
-        for (var i = l - 1; i >= 0; i--) a2[i2 + i] = a1[i1 + i];
-      }
-    } else {
-      var b = this.bytes;
-      if (b == null) b = this.toBytes();
-      var l1 = this.last - i1;
-      if (l <= l1)
-        for (var i = 0; i < l; i++) a2 [i2 + i] = b.charCodeAt(i1 + i);
-      else {
-        for (var i = 0; i < l1; i++) a2 [i2 + i] = b.charCodeAt(i1 + i);
-        for (; i < l; i++) a2 [i2 + i] = 0;
-      }
-    }
-  },
-  get:function (i) {
-    var a = this.array;
-    if (a) return a[i];
-    var b = this.bytes;
-    if (b == null) b = this.toBytes();
-    return (i<this.last)?b.charCodeAt(i):0;
-  },
-  safeGet:function (i) {
-    if (!this.len) this.toBytes();
-    if ((i < 0) || (i >= this.len)) caml_array_bound_error ();
-    return this.get(i);
-  },
-  set:function (i, c) {
-    var a = this.array;
-    if (!a) {
-      if (this.last == i) {
-        this.bytes += String.fromCharCode (c & 0xff);
-        this.last ++;
-        return 0;
-      }
-      a = this.toArray();
-    } else if (this.bytes != null) {
-      this.bytes = this.fullBytes = this.string = null;
-    }
-    a[i] = c & 0xff;
-    return 0;
-  },
-  safeSet:function (i, c) {
-    if (this.len == null) this.toBytes ();
-    if ((i < 0) || (i >= this.len)) caml_array_bound_error ();
-    this.set(i, c);
-  },
-  fill:function (ofs, len, c) {
-    if (ofs >= this.last && this.last && c == 0) return;
-    var a = this.array;
-    if (!a) a = this.toArray();
-    else if (this.bytes != null) {
-      this.bytes = this.fullBytes = this.string = null;
-    }
-    var l = ofs + len;
-    for (var i = ofs; i < l; i++) a[i] = c;
-  },
-  compare:function (s2) {
-    if (this.string != null && s2.string != null) {
-      if (this.string < s2.string) return -1;
-      if (this.string > s2.string) return 1;
-      return 0;
-    }
-    var b1 = this.getFullBytes ();
-    var b2 = s2.getFullBytes ();
-    if (b1 < b2) return -1;
-    if (b1 > b2) return 1;
-    return 0;
-  },
-  equal:function (s2) {
-    if (this.string != null && s2.string != null)
-      return this.string == s2.string;
-    return this.getFullBytes () == s2.getFullBytes ();
-  },
-  lessThan:function (s2) {
-    if (this.string != null && s2.string != null)
-      return this.string < s2.string;
-    return this.getFullBytes () < s2.getFullBytes ();
-  },
-  lessEqual:function (s2) {
-    if (this.string != null && s2.string != null)
-      return this.string <= s2.string;
-    return this.getFullBytes () <= s2.getFullBytes ();
-  }
-}
-function MlWrappedString (s) { this.string = s; }
-MlWrappedString.prototype = new MlString();
-function MlMakeString (l) { this.bytes = ""; this.len = l; }
-MlMakeString.prototype = new MlString ();
-function caml_array_get (array, index) {
-  if ((index < 0) || (index >= array.length - 1)) caml_array_bound_error();
-  return array[index+1];
-}
-function caml_array_set (array, index, newval) {
-  if ((index < 0) || (index >= array.length - 1)) caml_array_bound_error();
-  array[index+1]=newval; return 0;
-}
-function caml_call_gen(f, args) {
-  if(f.fun)
-    return caml_call_gen(f.fun, args);
-  var n = f.length;
-  var d = n - args.length;
-  if (d == 0)
-    return f.apply(null, args);
-  else if (d < 0)
-    return caml_call_gen(f.apply(null, args.slice(0,n)), args.slice(n));
-  else
-    return function (x){ return caml_call_gen(f, args.concat([x])); };
-}
-function caml_raise_constant (tag) { throw [0, tag]; }
-var caml_global_data = [0];
-function caml_raise_zero_divide () {
-  caml_raise_constant(caml_global_data[6]);
-}
-function caml_div(x,y) {
-  if (y == 0) caml_raise_zero_divide ();
-  return (x/y)|0;
-}
-function caml_parse_format (fmt) {
-  fmt = fmt.toString ();
-  var len = fmt.length;
-  if (len > 31) caml_invalid_argument("format_int: format too long");
-  var f =
-    { justify:'+', signstyle:'-', filler:' ', alternate:false,
-      base:0, signedconv:false, width:0, uppercase:false,
-      sign:1, prec:-1, conv:'f' };
-  for (var i = 0; i < len; i++) {
-    var c = fmt.charAt(i);
-    switch (c) {
-    case '-':
-      f.justify = '-'; break;
-    case '+': case ' ':
-      f.signstyle = c; break;
-    case '0':
-      f.filler = '0'; break;
-    case '#':
-      f.alternate = true; break;
-    case '1': case '2': case '3': case '4': case '5':
-    case '6': case '7': case '8': case '9':
-      f.width = 0;
-      while (c=fmt.charCodeAt(i) - 48, c >= 0 && c <= 9) {
-        f.width = f.width * 10 + c; i++
-      }
-      i--;
-     break;
-    case '.':
-      f.prec = 0;
-      i++;
-      while (c=fmt.charCodeAt(i) - 48, c >= 0 && c <= 9) {
-        f.prec = f.prec * 10 + c; i++
-      }
-      i--;
-    case 'd': case 'i':
-      f.signedconv = true; /* fallthrough */
-    case 'u':
-      f.base = 10; break;
-    case 'x':
-      f.base = 16; break;
-    case 'X':
-      f.base = 16; f.uppercase = true; break;
-    case 'o':
-      f.base = 8; break;
-    case 'e': case 'f': case 'g':
-      f.signedconv = true; f.conv = c; break;
-    case 'E': case 'F': case 'G':
-      f.signedconv = true; f.uppercase = true;
-      f.conv = c.toLowerCase (); break;
-    }
-  }
-  return f;
-}
-function caml_finish_formatting(f, rawbuffer) {
-  if (f.uppercase) rawbuffer = rawbuffer.toUpperCase();
-  var len = rawbuffer.length;
-  if (f.signedconv && (f.sign < 0 || f.signstyle != '-')) len++;
-  if (f.alternate) {
-    if (f.base == 8) len += 1;
-    if (f.base == 16) len += 2;
-  }
-  var buffer = "";
-  if (f.justify == '+' && f.filler == ' ')
-    for (var i = len; i < f.width; i++) buffer += ' ';
-  if (f.signedconv) {
-    if (f.sign < 0) buffer += '-';
-    else if (f.signstyle != '-') buffer += f.signstyle;
-  }
-  if (f.alternate && f.base == 8) buffer += '0';
-  if (f.alternate && f.base == 16) buffer += "0x";
-  if (f.justify == '+' && f.filler == '0')
-    for (var i = len; i < f.width; i++) buffer += '0';
-  buffer += rawbuffer;
-  if (f.justify == '-')
-    for (var i = len; i < f.width; i++) buffer += ' ';
-  return new MlWrappedString (buffer);
-}
-function caml_format_int(fmt, i) {
-  if (fmt.toString() == "%d") return new MlWrappedString(""+i);
-  var f = caml_parse_format(fmt);
-  if (i < 0) { if (f.signedconv) { f.sign = -1; i = -i; } else i >>>= 0; }
-  var s = i.toString(f.base);
-  if (f.prec >= 0) {
-    f.filler = ' ';
-    var n = f.prec - s.length;
-    if (n > 0) s = caml_str_repeat (n, '0') + s;
-  }
-  return caml_finish_formatting(f, s);
-}
-function caml_int64_compare(x,y) {
-  var x3 = x[3] << 16;
-  var y3 = y[3] << 16;
-  if (x3 > y3) return 1;
-  if (x3 < y3) return -1;
-  if (x[2] > y[2]) return 1;
-  if (x[2] < y[2]) return -1;
-  if (x[1] > y[1]) return 1;
-  if (x[1] < y[1]) return -1;
-  return 0;
-}
-function caml_int_compare (a, b) {
-  if (a < b) return (-1); if (a == b) return 0; return 1;
-}
-function caml_compare_val (a, b, total) {
-  var stack = [];
-  for(;;) {
-    if (!(total && a === b)) {
-      if (a instanceof MlString) {
-        if (b instanceof MlString) {
-            if (a != b) {
-		var x = a.compare(b);
-		if (x != 0) return x;
-	    }
-        } else
-          return 1;
-      } else if (a instanceof Array && a[0] === (a[0]|0)) {
-        var ta = a[0];
-        if (ta === 250) {
-          a = a[1];
-          continue;
-        } else if (b instanceof Array && b[0] === (b[0]|0)) {
-          var tb = b[0];
-          if (tb === 250) {
-            b = b[1];
-            continue;
-          } else if (ta != tb) {
-            return (ta < tb)?-1:1;
-          } else {
-            switch (ta) {
-            case 248: {
-		var x = caml_int_compare(a[2], b[2]);
-		if (x != 0) return x;
-		break;
-	    }
-            case 255: {
-		var x = caml_int64_compare(a, b);
-		if (x != 0) return x;
-		break;
-	    }
-            default:
-              if (a.length != b.length) return (a.length < b.length)?-1:1;
-              if (a.length > 1) stack.push(a, b, 1);
-            }
-          }
-        } else
-          return 1;
-      } else if (b instanceof MlString ||
-                 (b instanceof Array && b[0] === (b[0]|0))) {
-        return -1;
-      } else {
-        if (a < b) return -1;
-        if (a > b) return 1;
-        if (total && a != b) {
-          if (a == a) return 1;
-          if (b == b) return -1;
-        }
-      }
-    }
-    if (stack.length == 0) return 0;
-    var i = stack.pop();
-    b = stack.pop();
-    a = stack.pop();
-    if (i + 1 < a.length) stack.push(a, b, i + 1);
-    a = a[i];
-    b = b[i];
-  }
-}
-function caml_compare (a, b) { return caml_compare_val (a, b, true); }
-function caml_greaterequal (x, y) { return +(caml_compare(x,y,false) >= 0); }
-function caml_js_call(f, o, args) { return f.apply(o, args.slice(1)); }
-function caml_js_wrap_callback(f) {
-  var toArray = Array.prototype.slice;
-  return function () {
-    var args = (arguments.length > 0)?toArray.call (arguments):[undefined];
-    return caml_call_gen(f, args);
-  }
-}
-function caml_lessequal (x, y) { return +(caml_compare(x,y,false) <= 0); }
-function caml_ml_out_channels_list () { return 0; }
-function caml_mod(x,y) {
-  if (y == 0) caml_raise_zero_divide ();
-  return x%y;
-}
-function caml_register_global (n, v) { caml_global_data[n + 1] = v; }
-var caml_named_values = {};
-function caml_register_named_value(nm,v) {
-  caml_named_values[nm] = v; return 0;
-}
-function caml_sys_get_config () {
-  return [0, new MlWrappedString("Unix"), 32, 0];
-}
-(function(){function ce(dg,dh,di){return dg.length==2?dg(dh,di):caml_call_gen(dg,[dh,di]);}function Q(de,df){return de.length==1?de(df):caml_call_gen(de,[df]);}var a=[0,new MlString("Invalid_argument")],b=[0,new MlString("Not_found")];caml_register_global(6,b);caml_register_global(5,[0,new MlString("Division_by_zero")]);caml_register_global(3,a);caml_register_global(2,[0,new MlString("Failure")]);var G=new MlString("%d"),F=new MlString("Pervasives.do_at_exit"),E=new MlString("Random.int"),D=[0,2061652523,1569539636,364182224,414272206,318284740,2064149575,383018966,1344115143,840823159,1098301843,536292337,1586008329,189156120,1803991420,1217518152,51606627,1213908385,366354223,2077152089,1774305586,2055632494,913149062,526082594,2095166879,784300257,1741495174,1703886275,2023391636,1122288716,1489256317,258888527,511570777,1163725694,283659902,308386020,1316430539,1556012584,1938930020,2101405994,1280938813,193777847,1693450012,671350186,149669678,1330785842,1161400028,558145612,1257192637,1101874969,1975074006,710253903,1584387944,1726119734,409934019,801085050],C=new MlString("on"),B=new MlString("canvas"),A=new MlString("mousedown"),z=new MlString("mousemove"),y=new MlString("2d"),x=new MlString("Dom_html.Canvas_not_available"),w=[0,0,0],v=[0,[0,[0,0,0]],0],u=new MlString("#FF0000"),t=new MlString("#000000"),s=new MlString("20pt Arial"),r=new MlString("#FFFFFF"),q=new MlString("Click to Start"),p=new MlString("Reload the page to restart"),o=new MlString("rgb(0,255,0)"),n=new MlString("rgb(255,128,0)"),m=new MlString("rgb(255,255,0)"),l=new MlString("rgb(0,255,255)"),k=[0,16,16],j=[0,4,4],i=[0,8,8];function h(d,c){return caml_lessequal(d,c)?d:c;}function H(f,e){return caml_greaterequal(f,e)?f:e;}function I(g){return 0<=g?g:-g|0;}function N(M){var J=caml_ml_out_channels_list(0);for(;;){if(J){var K=J[2];try {}catch(L){}var J=K;continue;}return 0;}}caml_register_named_value(F,N);function S(P,O){if(O){var R=O[2],T=Q(P,O[1]);return [0,T,S(P,R)];}return 0;}function ae(_){return Q(function(U,W){var V=U,X=W;for(;;){if(X){var Y=X[2],Z=X[1];if(Q(_,Z)){var $=[0,Z,V],V=$,X=Y;continue;}var X=Y;continue;}var aa=V,ab=0;for(;;){if(aa){var ac=aa[2],ad=[0,aa[1],ab],aa=ac,ab=ad;continue;}return ab;}}},0);}var af=[0,0];32===caml_sys_get_config(0)[2];var ag=[0,D.slice(),0];function al(ah){if(!(1073741823<ah)&&0<ah)for(;;){ag[2]=(ag[2]+1|0)%55|0;var ai=caml_array_get(ag[1],ag[2]),aj=(caml_array_get(ag[1],(ag[2]+24|0)%55|0)+(ai^ai>>>25&31)|0)&1073741823;caml_array_set(ag[1],ag[2],aj);var ak=caml_mod(aj,ah);if(((1073741823-ah|0)+1|0)<(aj-ak|0))continue;return ak;}throw [0,a,E];}var am=undefined,ar=null;function aq(an,ao,ap){return an===am?Q(ao,0):Q(ap,an);}var as=false,au=Array;function av(at){return at instanceof au?0:[0,new MlWrappedString(at.toString())];}af[1]=[0,av,af[1]];function aP(ax){return caml_js_wrap_callback(function(aw){if(aw){var ay=Q(ax,aw);if(!(ay|0))aw.preventDefault();return ay;}var az=event,aA=Q(ax,az);az.returnValue=aA;return aA;});}function aQ(aB){return aB.toString();}function aR(aC,aD,aG,aN){if(aC.addEventListener===am){var aE=C.toString().concat(aD),aL=function(aF){var aK=[0,aG,aF,[0]];return Q(function(aJ,aI,aH){return caml_js_call(aJ,aI,aH);},aK);};aC.attachEvent(aE,aL);return function(aM){return aC.detachEvent(aE,aL);};}aC.addEventListener(aD,aG,aN);return function(aO){return aC.removeEventListener(aD,aG,aN);};}var aS=aQ(A),aT=aQ(z),aU=this,aV=aU.document,aX=y.toString(),aW=[0,x];this.HTMLElement===am;function a1(a0){var aY=aV.body,aZ=aV.documentElement;return [0,(a0.clientX+aY.scrollLeft|0)+aZ.scrollLeft|0,(a0.clientY+aY.scrollTop|0)+aZ.scrollTop|0];}function cT(a3,a2){return Q(a3,a2);}function c$(a4,a5){return Q(a5,a4);}function bo(a6){return a6;}function bb(a7){return 1+(a7[7]/5|0)|0;}function bC(a8){return a8[1];}function be(a9){switch(a9[0]){case 1:return j;case 2:return i;default:return k;}}function bK(bc,a_){switch(a_[0]){case 1:var a$=a_[1];return [1,[0,a$[1],a$[2]-5|0]];case 2:var ba=a_[1],bd=bb(bc);return [2,[0,ba[1],ba[2]+bd|0]];default:var bf=be(a_),bg=bf[2],bh=bf[1],bi=bc[6]-bg|0,bj=h(H(bc[8][2],bg),bi),bk=bc[5]-bh|0;return [0,[0,h(H(bc[8][1],bh),bk),bj]];}}function cK(bt,bn,bl){switch(bl[0]){case 1:var bm=bl[1];bn.fillStyle=m.toString();var bp=bo(bm[2]-4|0);return bn.fillRect(bo(bm[1]-4|0),bp,8,8);case 2:var bq=bl[1];bn.fillStyle=l.toString();var br=bo(bq[2]-8|0);return bn.fillRect(bo(bq[1]-8|0),br,16,16);default:var bs=bl[1],bu=2===bt[10]?n.toString():o.toString();bn.fillStyle=bu;var bv=bo(bs[2]-16|0);return bn.fillRect(bo(bs[1]-16|0),bv,32,32);}}function cG(bw){switch(bw[10]){case 1:if(bw[9]){var bx=bw.slice(),by=bw[2],bE=bw[2];for(;;){if(!by)throw [0,b];var bz=by[1],bB=by[2],bA=0===bz[0]?1:0;if(!bA){var by=bB;continue;}var bD=bC(bz);bx[2]=[0,[1,[0,bD[1],bD[2]]],bE];bx[9]=0;var bF=bx;break;}}else var bF=bw;if(0===al(caml_div(30,bb(bF)))){var bG=bF.slice(),bH=bF[2];bG[2]=[0,[2,[0,al(bF[5]),-16]],bH];var bI=bG;}else var bI=bF;var bJ=bI.slice(),bL=bI[2];bJ[2]=S(Q(bK,bI),bL);var bM=[0,bJ[7]],bN=[0,0],b_=function(bO){var bP=bO,bQ=bJ[2];for(;;){if(bQ){var bR=bQ[1],bT=bQ[2],bS=bC(bP),bU=bC(bR),bZ=bS[2],bY=bS[1],bX=bU[2],bW=bU[1],bV=be(bP),b0=be(bR),b3=bV[2],b2=b0[2],b1=b0[1]+bV[1]|0,b4=I(bW-bY|0)<b1?1:0,b5=b4?I(bX-bZ|0)<(b2+b3|0)?1:0:b4;if(b5){switch(bR[0]){case 1:if(2===bP[0]){var b6=bP[1];bM[1]=bM[1]+1|0;var b7=[2,[0,b6[1],bJ[6]+100|0]],b8=2;}else var b8=0;break;case 2:switch(bP[0]){case 2:var b8=0;break;case 0:var b8=1;break;default:var b7=[1,[0,bP[1][1],-100]],b8=2;}break;default:var b8=2===bP[0]?1:0;}switch(b8){case 1:bN[1]=1;var b7=bP;break;case 2:break;default:var b7=bP;}var b9=b7;}else var b9=bP;var bP=b9,bQ=bT;continue;}return bP;}},ca=S(b_,bJ[2]),b$=bJ.slice();b$[2]=ca;b$[7]=bM[1];var cb=bN[1]?2:bJ[10];b$[10]=cb;var cd=function(cc){switch(cc[0]){case 1:return -4<cc[1][2]?1:0;case 2:return cc[1][2]<(b$[6]+16|0)?1:0;default:return 1;}},cg=ce(ae,cd,b$[2]),cf=b$.slice();cf[2]=cg;return cf;case 2:return bw;default:var ch=bw.slice(),ci=bw[2];ch[2]=S(Q(bK,bw),ci);if(ch[9]){var cj=ch.slice();cj[9]=0;cj[10]=1;return cj;}return ch;}}function db(cq,cl){function co(ck){return ck;}function cp(cn){var cm=cl.button-1|0;if(!(cm<0||3<cm))switch(cm){case 1:return 3;case 2:break;case 3:return 2;default:return 1;}return 0;}var cr=1===aq(cl.which,cp,co)?1:0,cs=cq[1].slice();cs[9]=cr;cq[1]=cs;return as;}function c9(cD,cv){function cA(cu){function cx(ct){return [0,cu,ct];}function cy(cw){return a1(cv);}return aq(cv.pageY,cy,cx);}function cB(cz){return a1(cv);}var cC=aq(cv.pageX,cB,cA),cE=cD[1].slice();cE[8]=[0,cC[1],cC[2]];cD[1]=cE;return as;}function c7(cF,cU){var cH=cG(cG(cF[1])),cI=cH[1].getContext(aX);if(2<=cH[10])cI.fillStyle=u.toString();else cI.fillStyle=t.toString();var cJ=bo(cH[6]);cI.fillRect(0,0,bo(cH[5]),cJ);var cL=cH[2],cM=cL,cN=ce(cK,cH,cI);for(;;){if(cM){var cO=cM[2];Q(cN,cM[1]);var cM=cO;continue;}cI.font=s.toString();cI.fillStyle=r.toString();var cS=30,cR=10,cQ=caml_format_int(G,cH[7]);cI.fillText(cT(function(cP){return cP.toString();},cQ),cR,cS);switch(cH[10]){case 1:break;case 2:cI.fillText(p.toString(),100,200);break;default:cI.fillText(q.toString(),150,200);}cF[1]=cH;return 0;}}aU.onload=aP(function(dd){var cV=aU.document,cX=cV.body,cW=aU.document.createElement(B.toString()),cY=0,cZ=0,c0=0,c1=320,c2=480,c3=0,c4=0;if(1-(cW.getContext==ar?1:0)){cW.width=480;cW.height=320;var c5=[0,cW,v,c4,c3,c2,c1,c0,w,cZ,cY],c6=[0,c5];aU.setInterval(caml_js_wrap_callback(Q(c7,c6)),1000/30);var c_=function(c8){return 0;};c$(aR(cV,aT,cT(aP,Q(c9,c6)),as),c_);var dc=function(da){return 0;};c$(aR(cV,aS,cT(aP,Q(db,c6)),as),dc);cX.appendChild(c5[1]);return as;}throw [0,aW];});N(0);return;}());
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.