Add ~/.atom/dev/packages to load paths

Add ~/.atom/dev/packages to load paths

--- src/browser/atom-protocol-handler.coffee
+++ src/browser/atom-protocol-handler.coffee
@@ -13,6 +13,7 @@
     @loadPaths = [
       path.join(@resourcePath, 'node_modules')
       path.join(app.getHomeDir(), '.atom', 'packages')
+      path.join(app.getHomeDir(), '.atom', 'dev', 'packages')
     ]

     @registerAtomProtocol()


[api] Switch back to using callback ( for now )

--- lib/api.coffee
+++ lib/api.coffee
@@ -138,6 +138,4 @@
           # Send the message
           # engineIOServer.clients[message.sid].send(JSON.stringify(message, true))

-      return Q.fcall =>
-        return wss;
-
+      callback null, wss


Organise action requires close to their use in app.coffee

--- lib/app.coffee
+++ lib/app.coffee
@@ -3,12 +3,11 @@
 data = require('./data/data')
 config = require('./config')

-auth = require('./actions/auth')
-app = require('./actions/app')
-
 program.version(packageJSON.version)

 # ---------- Auth Module ----------
+
+auth = require('./actions/auth')

 program
 	.command('login <username:password>')
@@ -22,6 +21,8 @@

 # ---------- App Module ----------

+app = require('./actions/app')
+
 program
 	.command('apps')
 	.description('Show a list of your apps')


Fix issue cannor read property 'match' of undefined

Fixed issue #27 where some tabs would cause the package to error when the
`.getURI()` method of a editor exists, but returns `undefined`. This is a
fix for the case where a new (untitled) tab causes the issue (see third
comment). However, the original problem (see first comment) may be fixed,
but it can possibly cause the Settings tab to no longer be pinnable on
some machines...

--- lib/pinned-tabs.coffee
+++ lib/pinned-tabs.coffee
@@ -171,7 +171,7 @@
     return pane.itemAtIndex tabIndex

   getItemID: (item) ->
-    if item.getURI
+    if item.getURI && item.getURI()
       uri = item.getURI()
       uri = 'markdown-preview://' + item.editorForId(item.editorId).getFileName() if uri.match(/markdown-preview:\/\//)
       return uri


Code cleanups

Code cleanups

--- src/coffee/jsEngine/Engine/Engine.coffee
+++ src/coffee/jsEngine/Engine/Engine.coffee
@@ -229,7 +229,6 @@
     @loader.loadThemes @options.themes
     return

-
   ###
   Starts the engine

@@ -305,7 +304,6 @@
     console.log "jsEngine started" #dev
     return

-
   ###
   Creates and prepares the game canvas for being used
   ###
@@ -326,7 +324,6 @@
     else
       @renderer = new Renderer.Canvas(@canvas)
     return
-

   ###
   Enables or disables canvas autoresize.
@@ -352,7 +349,6 @@
       @canvas.style.width = @canvasResX + "px"
       @canvas.style.height = @canvasResY + "px"
     return
-

   ###
   Function for resizing the canvas. Not used if engine option "autoResizeCanvas" is false.
@@ -388,7 +384,6 @@
     @canvas.style.width = w + "px"
     return

-
   ###
   Function for converting between speed units

@@ -447,7 +442,6 @@

     oldRoom

-
   ###
   Adds a room to the room list. This function is automatically called by the Room class' constructor.

@@ -462,7 +456,6 @@
     @roomList.push room
     return

-
   ###
   Removes a room from the room list.

@@ -488,7 +481,6 @@
     @roomList.splice i, 1
     return

-
   ###
   Toggles if all sound effects should be muted.

@@ -506,7 +498,6 @@
     @soundsMuted = muted
     return

-
   ###
   Toggles if all music should be muted.

@@ -523,7 +514,6 @@

     @musicMuted = muted
     return
-

   ###
   Sets the default theme for the engine objects
@@ -539,7 +529,6 @@
     @currentRoom.setTheme undefined, enforce
     return

-
   ###
   Starts the engine's main loop
   ###
@@ -554,7 +543,6 @@
     engine.mainLoop()
     return

-
   ###
   Stops the engine's main loop
   ###
@@ -562,7 +550,6 @@
     return  unless @running
     @running = false
     return
-

   ###
   The engine's main loop function (should not be called manually)
@@ -593,7 +580,7 @@
     # Draw game objects
     @drawCalls = 0 #dev
     drawTime = new Date().getTime() #dev
-    @redraw()
+    @renderer.render @cameras
     drawTime = new Date().getTime() - drawTime #dev

     # Count frames per second and calculate mean redraw time
@@ -601,14 +588,12 @@
       @fpsCounter++ #dev
       @drawTimeCounter += drawTime #dev
       @fpsMsCounter += @timeIncrease #dev
-    #dev
     else #dev
       @fps = @fpsCounter #dev
       @drawTime = @drawTimeCounter / @fpsCounter #dev
       @fpsCounter = 0 #dev
       @drawTimeCounter = 0 #dev
       @fpsMsCounter = 0 #dev
-    #dev

     # Schedule the loop to run again
     requestAnimationFrame (time) ->
@@ -617,7 +602,6 @@

     return

-
   ###
   Sets the horizontal resolution of the main canvas

@@ -629,7 +613,6 @@
     @autoResizeCanvas()  if @autoResize
     return

-
   ###
   Sets the vertical resolution of the main canvas

@@ -640,7 +623,6 @@
     @canvasResY = res
     @autoResizeCanvas()  if @autoResize
     return
-

   ###
   Registers an object to the engine. This will give the object an id which can be used for accessing it at a later time.
@@ -667,7 +649,6 @@
     req.open "GET", filePath, false
     req.send()
     req.responseText
-

   ###
   Loads and executes one or multiple JavaScript file synchronously
@@ -695,7 +676,6 @@
     window.loadedFiles = window.loadedFiles.concat(filePaths)
     return

-
   ###
   Uses an http request to fetch the data from a file and runs a callback function with the file data as first parameter

@@ -725,13 +705,10 @@
     req.send params
     unless async
       if req.readyState is 4 and req.status is 200 #dev
-        callback.call caller, req.responseText
-      #dev
+        callback.call caller, req.responseText #dev
       else #dev
         throw new Error("XMLHttpRequest failed: " + url) #dev
     return
-
-  #dev

   ###
   Removes an object from all engine loops, views, and from the object index
@@ -772,17 +749,6 @@

     return

-
-  ###
-  Redraws the canvas by redrawing all cameras
-  ###
-  redraw: ->
-
-    # Send cameras to the renderer
-    @renderer.render @cameras
-    return
-
-
   ###
   Downloads a screen dump of the main canvas. Very usable for creating game screenshots directly from browser consoles.
   ###


fix(cli): remove useless node-watch require

--- lib/cli.coffee
+++ lib/cli.coffee
@@ -11,7 +11,6 @@
 directory = require '../lib/directory'
 parser = require '../lib/parser'
 render = require '../lib/render.coffee'
-watch = require 'node-watch'

 colors.setTheme({
   silly: 'rainbow'


expose suite and runner as globals on CLI

--- lib/cli.coffee
+++ lib/cli.coffee
@@ -37,11 +37,11 @@

 files = _.map program.args, (path) -> Path.resolve(path)

-suite = new Suite()
+suite = global.BarrierSuite = new Suite()
+runner = global.BarrierRunner = new Runner(suite)
+runner.reporter(program.reporter or "dot")
+
 suite.withDSL -> require(file) for file in files
-
-runner = new Runner(suite)
-runner.reporter(program.reporter or "dot")

 runner.run().then(
   -> process.exit(runner.stats.failures)


make sure to not reading the trailing newline char

--- lib/remote-atom.coffee
+++ lib/remote-atom.coffee
@@ -46,6 +46,8 @@
                 @open_in_atom()
             else if @readbytes < @datasize
                 @readbytes += Buffer.byteLength(line)
+                if @readbytes > @datasize and line.slice(-1) is "\n"
+                    line = line.slice(0, -1)
                 fs.writeSync(@fd, line)
         else
             m = line.match /([a-z\-]+?)\s*:\s*(.*?)\s*$/


helpers: refactored and fixed comments

helpers: refactored and fixed comments

--- helpers.coffee
+++ helpers.coffee
@@ -4,64 +4,57 @@

 helpers = exports.helpers = {}

-# Cross-browser indexOf, so that IE can join the party.
-helpers.indexOf = indexOf = (array, item, from) ->
-  return array.indexOf item, from if array.indexOf
-  for other, index in array
-    if other is item and (not from or (from <= index))
-      return index
-  -1
+# Cross-engine indexOf, so that JScript can join the party.
+indexOf = helpers.indexOf = Array.indexOf or
+  if Array::indexOf
+    (array, item, from) -> array.indexOf item, from
+  else
+    (array, item, from) ->
+      for other, index in array
+        if other is item and (not from or from <= index)
+          return index
+      -1

 # Does a list include a value?
-helpers.include = include = (list, value) ->
-  indexOf(list, value) >= 0
+helpers.include = (list, value) -> 0 <= indexOf list, value

 # Peek at the beginning of a given string to see if it matches a sequence.
-helpers.starts = starts = (string, literal, start) ->
-  string.substring(start, (start or 0) + literal.length) is literal
+helpers.starts = (string, literal, start) ->
+  literal is string.substr start, literal.length

 # Peek at the end of a given string to see if it matches a sequence.
-helpers.ends = ends = (string, literal, back) ->
-  start = string.length - literal.length - (back ? 0)
-  string.substring(start, start + literal.length) is literal
+helpers.ends = (string, literal, back) ->
+  ll = literal.length
+  literal is string.substr string.length - ll - (back or 0), ll

 # Trim out all falsy values from an array.
-helpers.compact = compact = (array) -> item for item in array when item
+helpers.compact = (array) -> item for item in array when item

 # Count the number of occurences of a character in a string.
-helpers.count = count = (string, letter) ->
-  num = 0
-  pos = indexOf string, letter
-  while pos isnt -1
-    num += 1
-    pos = indexOf string, letter, pos + 1
+helpers.count = (string, letter) ->
+  num = pos = 0
+  num++ while 0 < pos = 1 + string.indexOf letter, pos
   num

 # Merge objects, returning a fresh copy with attributes from both sides.
 # Used every time `BaseNode#compile` is called, to allow properties in the
 # options hash to propagate down the tree without polluting other branches.
-helpers.merge = merge = (options, overrides) ->
-  fresh = {}
-  (fresh[key] = val) for all key, val of options
-  (fresh[key] = val) for all key, val of overrides if overrides
-  fresh
+helpers.merge = (options, overrides) ->
+  extend (extend {}, options), overrides

 # Extend a source object with the properties of another object (shallow copy).
 # We use this to simulate Node's deprecated `process.mixin`
-helpers.extend = extend = (object, properties) ->
+extend = helpers.extend = (object, properties) ->
   (object[key] = val) for all key, val of properties
+  object

-# Return a completely flattened version of an array. Handy for getting a
-# list of `children` from the nodes.
-helpers.flatten = flatten = (array) ->
-  memo = []
-  for item in array
-    if item instanceof Array then memo = memo.concat(item) else memo.push(item)
-  memo
+# Return a flattened version of an array (nonrecursive).
+# Handy for getting a list of `children` from the nodes.
+helpers.flatten = (array) -> array.concat.apply [], array

 # Delete a key from an object, returning the value. Useful when a node is
 # looking for a particular method in an options hash.
-helpers.del = del = (obj, key) ->
-  val = obj[key]
+helpers.del = (obj, key) ->
+  val =  obj[key]
   delete obj[key]
   val


Remove logging

Remove logging

--- lib/select-next.coffee
+++ lib/select-next.coffee
@@ -24,7 +24,6 @@
   selectAllOccurrences: ->
     range = [[0, 0], @editor.getEofBufferPosition()]
     @scanForNextOcurrence range, ({range, stop}) =>
-      console.log range.toString()
       @addSelection(range)

   selectNextOccurrence: ->


Delete unused import

Delete unused import

--- lib/status-view.coffee
+++ lib/status-view.coffee
@@ -1,5 +1,3 @@
-{View} = require 'atom'
-
 module.exports = class StatusView
   constructor: ->
     @element = document.createElement('div')


:fire: unused

:fire: unused

--- lib/text-object.coffee
+++ lib/text-object.coffee
@@ -11,8 +11,6 @@
   sortRanges
   getLineTextToPoint
 } = require './utils'
-
-

 class TextObject extends Base
   @extend(false)


:art: refactoring TexObject

:art: refactoring TexObject

--- lib/text-object.coffee
+++ lib/text-object.coffee
@@ -8,8 +8,8 @@
   @extend()
   complete: true

-  isWholeLine: ({start, end}) ->
-    (start.column is 0) and (end.column is 0) and start < end
+  isLinewiseRange: (range) ->
+    (range.start.column is 0) and (range.end.column is 0) and (not range.isEmpty())

   rangeToBeginningOfFile: (point) ->
     new Range(Point.ZERO, point)
@@ -18,16 +18,25 @@
     new Range(point, Point.INFINITY)

   isLinewise: ->
-    for s in @editor.getSelections() when not @isWholeLine s.getBufferRange()
-      return false
-    true
+    @editor.getSelections().every (s) =>
+      @isLinewiseRange s.getBufferRange()

   eachSelection: (callback) ->
-    for selection in @editor.getSelections()
-      callback selection
-    if @isLinewise() and @vimState.isMode('visual', ['characterwise', 'blockwise'])
+    for s in @editor.getSelections()
+      callback s
+    if @isLinewise() and not @vimState.isMode('visual', 'linewise')
       @vimState.activate('visual', 'linewise')
+    @isIncludeNonEmptySelection()
+
+  isIncludeNonEmptySelection: ->
     @editor.getSelections().some((s) -> not s.isEmpty())
+
+  sortRanges: (ranges) ->
+    ranges.sort((a, b) -> a.compare(b))
+
+  setBufferRangeSafely: (selection, range) ->
+    if range
+      selection.setBufferRange(range)

 # Word
 # -------------------------
@@ -40,9 +49,8 @@
       @selectExclusive(selection, wordRegex)
       @selectInclusive(selection) if @inclusive

-  selectExclusive: (selection, wordRegex) ->
-    range = selection.cursor.getCurrentWordBufferRange({wordRegex})
-    selection.setBufferRange(range)
+  selectExclusive: (s, wordRegex) ->
+    @setBufferRangeSafely s, s.cursor.getCurrentWordBufferRange({wordRegex})

   selectInclusive: (selection) ->
     scanRange = selection.cursor.getCurrentLineBufferRange()
@@ -122,22 +130,22 @@
     range

   select: ->
-    @eachSelection (selection) =>
-      if range = @getRange(selection, @pair)
-        selection.setBufferRange(range)
+    @eachSelection (s) =>
+      @setBufferRangeSafely s, @getRange(s, @pair)

 class AnyPair extends Pair
   @extend()
   pairs: ['""', "''", "``", "{}", "<>", "><", "[]", "()"]

-  select: ->
-    @eachSelection (selection) =>
-      ranges = []
-      for pair in @pairs when (range = @getRange(selection, pair))
-        ranges.push range
-      unless _.isEmpty(ranges)
-        ranges = ranges.sort (a, b) -> a.compare(b)
-        selection.setBufferRange(_.last(ranges))
+  getNearestRange: (selection, pairs) ->
+    ranges = []
+    for pair in pairs when (range = @getRange(selection, pair))
+      ranges.push range
+    _.last(@sortRanges(ranges)) unless _.isEmpty(ranges)
+
+  select: ->
+    @eachSelection (s) =>
+      @setBufferRangeSafely s, @getNearestRange(s, @pairs)

 class DoubleQuote extends Pair
   @extend()
@@ -198,8 +206,7 @@
   selectParagraph: (selection) ->
     [startRow, endRow] = selection.getBufferRowRange()
     if startRow is endRow
-      if range = @getRange(startRow)
-        selection.setBufferRange(range)
+      @setBufferRangeSafely selection, @getRange(startRow)
     else # have direction
       if selection.isReversed()
         if range = @getRange(startRow-1)
@@ -320,7 +327,7 @@
   @extend()
   select: ->
     @editor.selectAll()
-    @editor.getLastSelection().isEmpty()
+    @isIncludeNonEmptySelection()

 module.exports = {
   Word, WholeWord,


fix #99

fix #99

--- lib/text-object.coffee
+++ lib/text-object.coffee
@@ -361,7 +361,8 @@
       swrap(selection).setBufferRangeSafely @getRange(startRow)
     else
       point = if selection.isReversed()
-        @getRange(startRow - 1)?.start
+        startRow = Math.max(0, startRow - 1)
+        @getRange(startRow)?.start
       else
         @getRange(endRow + 1)?.end
       selection.selectToBufferPosition point if point?


Checkout origin/head in review function

Checkout origin/head in review function

Should have changed this when I changed the checkout function

--- lib/git.coffee
+++ lib/git.coffee
@@ -127,7 +127,7 @@
     .then (pr) ->
       opts.pr = pr
       opts.head = pr?.head?.ref
-      checkout opts.repo, opts.head ? 'source'
+      checkout opts.repo, "origin/#{opts.head}" ? 'source'
     .then (ref) ->
       new Promise (resolve, reject) ->
         action args..., (err) ->


JS: fix broken filter.unParseFilter test

--- tests_javascript/test_filter.coffee
+++ tests_javascript/test_filter.coffee
@@ -78,21 +78,21 @@
             _.defaults {pilot: ['Paxswill', 'DurrHurrDurr']}, defaults

     test 'Should unparse a filters object into a filter string', () ->
-        assert.strictEqual (filter._unParseFilters {}), ''
-        assert.strictEqual (filter._unParseFilters {pilot: ['Paxswill']}),
+        assert.strictEqual (filter.unParseFilters {}), ''
+        assert.strictEqual (filter.unParseFilters {pilot: ['Paxswill']}),
             'pilot/Paxswill'
-        assert.strictEqual (filter._unParseFilters \
+        assert.strictEqual (filter.unParseFilters \
             {pilot: ['Paxswill', 'DurrHurrDurr']}),
             'pilot/DurrHurrDurr,Paxswill'
-        assert.strictEqual (filter._unParseFilters \
+        assert.strictEqual (filter.unParseFilters \
             {system: [], pilot: ['Paxswill', 'DurrHurrDurr']}),
             'pilot/DurrHurrDurr,Paxswill'
-        assert.strictEqual (filter._unParseFilters \
+        assert.strictEqual (filter.unParseFilters \
             {page: 42, system: [], pilot: ['Paxswill', 'DurrHurrDurr']}),
             'page/42/pilot/DurrHurrDurr,Paxswill'
-        assert.strictEqual (filter._unParseFilters {details: ['Foo Bar']}),
+        assert.strictEqual (filter.unParseFilters {details: ['Foo Bar']}),
             'details/Foo Bar'
-        assert.strictEqual (filter._unParseFilters \
+        assert.strictEqual (filter.unParseFilters \
             {details: ['Foo Bar', 'Baz Qux']}),
             'details/Foo Bar/details/Baz Qux'


try to lazily load as much as possible

try to lazily load as much as possible

--- lib/ink.coffee
+++ lib/ink.coffee
@@ -1,65 +1,65 @@
 {CompositeDisposable} = require 'atom'
 etch = require 'etch'
+{once} = require 'underscore-plus'

+# these need to be loaded first so deserialization works fine
 PaneItem = require './util/pane-item'
-Loading = require './util/loading'
-progress = require './util/progress'
-Tooltip = require './util/tooltip'
-block = require './editor/block'
-highlights = require './editor/highlights'
-Result = require './editor/result'
-Docs = require './editor/docs'
 Console = require './console/console'
-Stepper = require './debugger/stepper'
-breakpoints = require './debugger/breakpoints'
 PlotPane = require './plots/pane'
 DocPane = require('./docs/docpane')
 InkTerminal = require('./console2/console')
-{Pannable} = require './plots/canopy'
-katex = require('./util/katexify')
-profiler = require './plots/profiler'
 Workspace = require './workspace/workspace'
 Linter  = require './linter/linter'
-tree = require './tree'
-goto = require './util/gotodef'
+
+exportables =
+  PaneItem: => PaneItem
+  Console: => Console
+  PlotPane: => PlotPane
+  DocPane: => DocPane
+  InkTerminal: => InkTerminal
+  Workspace: => Workspace
+  Linter : => Linter
+  Loading: once(=> require './util/loading')
+  progress: once(=> require './util/progress')
+  Tooltip: once(=> require './util/tooltip')
+  block: once(=> require './editor/block')
+  highlights: once(=> require './editor/highlights')
+  Result: once(=> require './editor/result')
+  InlineDoc: once(=> require './editor/docs')
+  Stepper: once(=> require './debugger/stepper')
+  breakpoints: once(=> require './debugger/breakpoints')
+  Pannable: once(=> require('./plots/canopy').Pannable)
+  KaTeX: once(=> require('./util/katexify'))
+  profiler: once(=> require './plots/profiler')
+  tree: once(=> require './tree')
+  goto: once(=> require './util/gotodef')
+  Opener: once(=> require('./util/opener'))
+  matchHighlighter: once(=> require './util/matchHighlighter')
+  ansiToHTML: once(=> require './util/ansitohtml')

 module.exports = Ink =
   activate: ->
     etch.setScheduler(atom.views)
-    mod.activate() for mod in [PaneItem, Result, Docs, Console, PlotPane, InkTerminal, Linter]
+    mod.activate() for mod in [exportables.PaneItem(), exportables.Result(), exportables.InlineDoc(), exportables.Console(), exportables.PlotPane(), exportables.InkTerminal(), exportables.Linter()]

   deactivate: ->
     # pkg = atom.packages.getActivePackage 'ink'
-    # localStorage.setItem pkg.getCanDeferMainModuleRequireStorageKey(), false
-    mod.deactivate() for mod in [PaneItem, Result, Docs, Console, PlotPane, InkTerminal, Linter]
+    # localStorage.setItem pkg.getCanDeferMainModuleRequireStorageKey(), exportables.false()
+    mod.deactivate() for mod in [exportables.PaneItem(), exportables.Result(), exportables.InlineDoc(), exportables.Console(), exportables.PlotPane(), exportables.InkTerminal(), exportables.Linter()]

   consumeStatusBar: (bar) ->
-    progress.consumeStatusBar bar
+    exportables.progress().consumeStatusBar bar

   provide: ->
-    util:
-      focusEditorPane: () -> PaneItem.focusEditorPane()
-    highlight: (ed, start, end, clas) =>
-      block.highlight ed, start, end, clas
-    Loading: Loading
-    progress: progress
-    Result: Result
-    Console: Console
-    Stepper: Stepper
-    breakpoints: breakpoints
-    Workspace: Workspace
-    PlotPane: PlotPane
-    DocPane: DocPane
-    Pannable: Pannable
-    highlights: highlights
-    tree: tree
-    InlineDoc: Docs
-    goto: goto
-    Tooltip: Tooltip
-    Profiler: profiler
-    Opener: require('./util/opener')
-    KaTeX: katex
-    InkTerminal: InkTerminal
-    Linter: Linter
-    matchHighlighter: require './util/matchHighlighter'
-    ansiToHTML: require './util/ansitohtml'
+    obj =
+      util:
+        focusEditorPane: () -> exportables.PaneItem().focusEditorPane()
+      highlight: (ed, start, end, clas) =>
+        exportables.block().highlight ed, start, end, clas
+
+    for key, val of exportables
+      do (val) ->
+        Object.defineProperty(obj, key, {
+          get: -> val()
+        })
+    obj


added WEEK, MONT and YEAR constants

added WEEK, MONT and YEAR constants


normalize file path key to make it work on windows

--- lib/nap.coffee
+++ lib/nap.coffee
@@ -469,7 +469,7 @@
         dirs = glob.sync path.resolve("#{@appDir}/#{pattern}").replace(/\\/g, "\/")
         matches = matches.concat(dirs)
       matches = _.uniq _.flatten matches
-      matches = (file.replace(@appDir, '').replace(/^\//, '') for file in matches)
+      matches = (path.normalize(file).replace(@appDir, '').replace(/^\//, '').replace(/\\/g, '\/') for file in matches)
       assets[key][pkg] = matches
   @assets = assets

@@ -477,4 +477,4 @@

 clearAssetsDir = =>
   rimraf.sync(@_outputDir)
-  fs.mkdirSync(@_outputDir, '0755')+  fs.mkdirSync(@_outputDir, '0755')


fuuu ui bug

fuuu ui bug

--- src/atomicity.coffee
+++ src/atomicity.coffee
@@ -18,10 +18,10 @@
 editor.getSession().setMode new JavaScriptMode
 editor.getSession().setUseSoftTabs true
 editor.getSession().setTabSize 2
-editor.focus()

 # fuuuuu, ui bug
 setTimeout ->
+  editor.focus()
   editor.resize()
 , 50


Modified in browser at pixie.strd6.com

Modified in browser at pixie.strd6.com

--- src/clampable.coffee
+++ src/clampable.coffee
@@ -1,5 +1,5 @@
 ###*
-The `Clampable` module provides helper methods to clamp object properties. This mod
+The `Clampable` module provides helper methods to clamp object properties. This module is included

     player = GameObject
       x: 40


Handle cross-domian requests

Handle cross-domian requests

--- lib/zen.coffee
+++ lib/zen.coffee
@@ -67,6 +67,15 @@
     createServer: ->
       @server = __server()
       @server.on "request", (request, response) =>
+
+        if request.method.toUpperCase() is "OPTIONS"
+          headers = {}
+          for key, value of ZEN.headers
+            headers[key] = if Array.isArray(value) then value.join(", ") else value
+          headers["Access-Control-Allow-Origin"] = request.headers.origin or "*"
+          response.writeHead "204", "No Content", headers
+          response.end()
+
         response.request = url: request.url, method: request.method, at: new Date()
         response[method] = callback for method, callback of zenresponse
         response.setTimeout ZEN.timeout, -> response.requestTimeout()


Revert 0fe459c, since hoverIntent may not be the only set of custom events in the extension.

--- src/js/jquery.extension.hlf.event.coffee
+++ src/js/jquery.extension.hlf.event.coffee
@@ -37,96 +37,95 @@
         current: 0
         previous: 0

-  hoverIntent = hlf.hoverIntent
-  mouse = hlf.mouse
+  do (hoverIntent = hlf.hoverIntent, mouse = hlf.mouse) ->

-  attr = (name='') -> "#{hoverIntent.toString 'attr'}#{name}"
+    attr = (name='') -> "#{hoverIntent.toString 'attr'}#{name}"

-  debugLog = if hoverIntent.debug is off then $.noop else
-    -> hlf.debugLog hoverIntent.toString('log'), arguments...
+    debugLog = if hoverIntent.debug is off then $.noop else
+      -> hlf.debugLog hoverIntent.toString('log'), arguments...

-  defaultState =
-    intentional: yes
-    timer: { cleared: no, timeout: null }
-    sensitivity: hoverIntent.sensitivity
-    interval: hoverIntent.interval
+    defaultState =
+      intentional: yes
+      timer: { cleared: no, timeout: null }
+      sensitivity: hoverIntent.sensitivity
+      interval: hoverIntent.interval

-  getComputedState = ($trigger) ->
-    state = {}
-    for key, value of defaultState
-      if $.isPlainObject value then value = _.clone value
-      state[key] = $trigger.data(attr(key)) or value
-    state
+    getComputedState = ($trigger) ->
+      state = {}
+      for key, value of defaultState
+        if $.isPlainObject value then value = _.clone value
+        state[key] = $trigger.data(attr(key)) or value
+      state

-  check = (event) ->
-    $trigger = $ @
-    state = getComputedState $trigger
-    debugLog state
-    didTeardown = teardownCheckIfNeeded event, $trigger, state
-    if didTeardown is no then setupCheckIfNeeded event, $trigger, state
+    check = (event) ->
+      $trigger = $ @
+      state = getComputedState $trigger
+      debugLog state
+      didTeardown = teardownCheckIfNeeded event, $trigger, state
+      if didTeardown is no then setupCheckIfNeeded event, $trigger, state

-  setupCheckIfNeeded = (event, $trigger, state) ->
-    return no if state.timer.cleared is no and state.timer.timeout?
-    debugLog 'setup'
-    state.timer.timeout = setTimeout ->
-      debugLog 'check and update'
-      performCheck event, $trigger, state
-    , state.interval
-    state.timer.cleared = no
-    $trigger.data attr('timer'), state.timer
-    return yes
+    setupCheckIfNeeded = (event, $trigger, state) ->
+      return no if state.timer.cleared is no and state.timer.timeout?
+      debugLog 'setup'
+      state.timer.timeout = setTimeout ->
+        debugLog 'check and update'
+        performCheck event, $trigger, state
+      , state.interval
+      state.timer.cleared = no
+      $trigger.data attr('timer'), state.timer
+      return yes

-  teardownCheckIfNeeded = (event, $trigger, state) ->
-    return no if event.type isnt 'mouseleave'
-    debugLog 'teardown'
-    if state.timer.cleared is no
-      clearTimeout state.timer.timeout
-      $trigger
-        .removeData attr('timer')
-        .removeData attr('intentional')
-    triggerEvent 'truemouseleave', $trigger
-    return yes
+    teardownCheckIfNeeded = (event, $trigger, state) ->
+      return no if event.type isnt 'mouseleave'
+      debugLog 'teardown'
+      if state.timer.cleared is no
+        clearTimeout state.timer.timeout
+        $trigger
+          .removeData attr('timer')
+          .removeData attr('intentional')
+      triggerEvent 'truemouseleave', $trigger
+      return yes

-  performCheck = (event, $trigger, state) ->
-    state.intentional =
-      (Math.abs(mouse.x.previous - mouse.x.current) +
-       Math.abs(mouse.y.previous - mouse.y.current)) >
-      state.sensitivity
-    mouse.x.previous = event.pageX
-    mouse.y.previous = event.pageY
-    if state.intentional is yes and event.type is 'mouseover'
-      triggerEvent 'truemouseenter', $trigger
-    state.timer.cleared = yes
-    $trigger.data attr('intentional'), state.intentional
-    $trigger.data attr('timer'), state.timer
+    performCheck = (event, $trigger, state) ->
+      state.intentional =
+        (Math.abs(mouse.x.previous - mouse.x.current) +
+         Math.abs(mouse.y.previous - mouse.y.current)) >
+        state.sensitivity
+      mouse.x.previous = event.pageX
+      mouse.y.previous = event.pageY
+      if state.intentional is yes and event.type is 'mouseover'
+        triggerEvent 'truemouseenter', $trigger
+      state.timer.cleared = yes
+      $trigger.data attr('intentional'), state.intentional
+      $trigger.data attr('timer'), state.timer

-  trackMouse = _.throttle (event) ->
-    mouse.x.current = event.pageX
-    mouse.y.current = event.pageY
-  , 16
+    trackMouse = _.throttle (event) ->
+      mouse.x.current = event.pageX
+      mouse.y.current = event.pageY
+    , 16

-  triggerEvent = (name, $trigger) ->
-    switch name
-      when 'truemouseenter' then event =
-        new $.Event name, { pageX: mouse.x.current, pageY: mouse.y.current }
-      when 'truemouseleave' then event = name
-      else event = null
-    if event?
-      debugLog name
-      $trigger.trigger event
-    else return no
+    triggerEvent = (name, $trigger) ->
+      switch name
+        when 'truemouseenter' then event =
+          new $.Event name, { pageX: mouse.x.current, pageY: mouse.y.current }
+        when 'truemouseleave' then event = name
+        else event = null
+      if event?
+        debugLog name
+        $trigger.trigger event
+      else return no

-  $.event.special.truemouseenter =
-    setup: (data, namespaces) ->
-      $(@).on   { mouseover: check, mousemove: trackMouse }
-    teardown: (data, namespaces) ->
-      $(@).off  { mouseover: check, mousemove: trackMouse }
+    $.event.special.truemouseenter =
+      setup: (data, namespaces) ->
+        $(@).on   { mouseover: check, mousemove: trackMouse }
+      teardown: (data, namespaces) ->
+        $(@).off  { mouseover: check, mousemove: trackMouse }

-  $.event.special.truemouseleave =
-    setup: (data, namespaces) ->
-      $(@).on   { mouseleave: check }
-    teardown: (data, namespaces) ->
-      $(@).off  { mouseleave: check }
+    $.event.special.truemouseleave =
+      setup: (data, namespaces) ->
+        $(@).on   { mouseleave: check }
+      teardown: (data, namespaces) ->
+        $(@).off  { mouseleave: check }

 # Export. Prefer AMD.
 if define? and define.amd?


Modified in browser at pixie.strd6.com

Modified in browser at pixie.strd6.com

--- src/expirable.coffee
+++ src/expirable.coffee
@@ -2,6 +2,7 @@
   Object.reverseMerge I,
     duration: -1
     alpha: 1
+    fadeOut: false

   startingAlpha = I.alpha


"arguments"

"arguments"

--- js/main.coffee
+++ js/main.coffee
@@ -1,4 +1,6 @@
 do ->
-  func = (x,y) -> ( x + y )
+  func = (args...) ->
+     console.log args

-  console.log(func 2, 3)
+
+  func 2, 3


Remove comma after a single argument

Remove comma after a single argument

--- js/tran.coffee
+++ js/tran.coffee
@@ -90,7 +90,7 @@
   successtHandler: (translated) ->
       chrome.tabs.getSelected(null, (tab) ->
         chrome.tabs.sendMessage(tab.id, {
-          action: tran.messageType translated,
+          action: tran.messageType translated
           data: translated.outerHTML,
           success: !translated.classList.contains('failTranslate')
         })


Fix number of mine

Fix number of mine

--- src/game.coffee
+++ src/game.coffee
@@ -114,7 +114,7 @@
   constructor: (id) ->
     @state = States.Empty
     @entities = Mine: 1
-    @nbMines = 2
+    @nbMines = 50
     @flags = 0
     @safe = 0
     @data = []


Game debugging control toggle should init properly.


Don't bubble key events

Don't bubble key events

--- src/game.coffee
+++ src/game.coffee
@@ -36,11 +36,13 @@
     action = keyMapping[event.which]
     if action?
       @actions[action] = true
+      false

   onKeyUp: (event) ->
     action = keyMapping[event.which]
     if action?
       @actions[action] = false
+      false

   run: ->
     webglmc.resmgr.wait =>


Added nice coffeescript modulo operator to geom.next

--- src/geom.coffee
+++ src/geom.coffee
@@ -18,7 +18,7 @@
   ###
   Returns the ith cyclic ordered number after start in the range [0..n].
   ###
-  (start + i) % n
+  (start + i) %% n

 geom.rangesDisjoint = ([a1, a2], [b1, b2]) ->
   ## Returns whether the scalar interval [a1, a2] is disjoint from the scalar


Publicizes version number

Publicizes version number

--- src/hull.coffee
+++ src/hull.coffee
@@ -54,7 +54,8 @@
           widget: window.Hull.widget,
           templates: window.Hull.templates,
           emit: window.Hull.emit,
-          on: window.Hull.on
+          on: window.Hull.on,
+          version: window.Hull.version
         }
         if _.isArray(config.expose)
           _.map config.expose, (i) ->


Add multi-language object ({en: "hoge"}) support

--- src/i18n.coffee
+++ src/i18n.coffee
@@ -1,9 +1,20 @@
-I18n = (id, args...) ->
-  m = chrome.i18n.getMessage(id, [args...])
-  return escapeHtml(m) if m != ""
-  m = id.replace(/(.)([A-Z][a-z])/g, (m, p1, p2) -> "#{p1} #{p2.toLowerCase()}")
-  m = m.replace(/_/g, ' ')
-  escapeHtml(m)
+I18n = (id_or_object, args...) ->
+  switch typeof id_or_object
+    when "string"
+      m = chrome.i18n.getMessage(id_or_object, [args...])
+      return escapeHtml(m) if m != ""
+      m = id_or_object.replace(
+        /(.)([A-Z][a-z])/g,
+        (m, p1, p2) -> "#{p1} #{p2.toLowerCase()}"
+      )
+      m = m.replace(/_/g, ' ')
+      escapeHtml(m)
+    when "object"
+      m = id_or_object[chrome.i18n.getUILanguage()]
+      return m if m
+      id_or_object["en"]
+    else
+      undefined

 $(->
   pat = /__MSG_([A-Za-z0-9]+)__/


invalid condition - not setting locale when adding resources

--- src/l10n.coffee
+++ src/l10n.coffee
@@ -1,4 +1,5 @@
-angular.module('l10n', []).provider('l10n',
+angular.module('l10n', [])
+.provider('l10n',
 	db: {}
 	localeMessages: {}
 	locale: null
@@ -11,7 +12,7 @@

 		@localeMessages[locale] = {} if typeof @localeMessages[locale] == 'undefined'
 		angular.extend @localeMessages[locale], values
-		@setLocale(locale) unless locale
+		@setLocale(locale) if locale

 	setLocale: (locale) ->
 		# clean up DB first


Fix typo, gague -> gauge

Fix typo, gague -> gauge

--- metrics.coffee
+++ metrics.coffee
@@ -112,13 +112,13 @@

 	gauge : (key, value, sampleRate = 1, opts)->
 		key = Metrics.buildPromKey(key)
-		prom.metric('gague', key).set({app: appname, host: hostname, status: opts?.status}, this.sanitizeValue(value))
+		prom.metric('gauge', key).set({app: appname, host: hostname, status: opts?.status}, this.sanitizeValue(value))
 		if process.env['DEBUG_METRICS']
 			console.log("doing gauge", key, opts)

 	globalGauge: (key, value, sampleRate = 1, opts)->
 		key = Metrics.buildPromKey(key)
-		prom.metric('gague', key).set({app: appname, status: opts?.status},this.sanitizeValue(value))
+		prom.metric('gauge', key).set({app: appname, status: opts?.status},this.sanitizeValue(value))

 	mongodb: require "./mongodb"
 	http: require "./http"


fixed catch

fixed catch

--- API/src/scraper.coffee
+++ API/src/scraper.coffee
@@ -67,7 +67,7 @@
                 .then (values) ->
                     cache.set('tiere', values, 60*60*24)
                     f values
-                .catch err ->
+                .catch (err) ->
                     r err
         else
             f values