     visible: (x,y)->
         # returns the square
         #   [ i_a -> i_b ]  x  [ j_a, j_b ]
-        j = binary_search @columnOffset, x
-        i = (y / @rowHeight | 0)
-        i = Math.max(0, i)
-        i = Math.min(i, @nbRows - @nbRowsVisible)
-        j = Math.max(0, j)
-        j = Math.min(j, @nbCols - @nbColsVisible)
+        i = bound (y / @rowHeight | 0), 0, (@nbRows - @nbRowsVisible)
+        j = bound binary_search(@columnOffset, x), 0, (@nbCols - @nbColsVisible)
         [i, j]
 
     setup: ->

        for j in [@firstVisibleColumn ... @firstVisibleColumn + @nbColsVisible] by 1
            columnHeader = @columns[j]
            do (columnHeader)=>
                @data.getHeader j, (data)=>
                    @painter.fillColumnHeader columnHeader, data
            for i in [@firstVisibleRow ... @firstVisibleRow + @nbRowsVisible] by 1
                k = i+ ","+j
                cell = @cells[k]
                do (cell)=>
                    @data.getCell i,j,(data)=>
                        cell.pending = false
                        @painter.fillCell cell,data

    goTo: (i,j)->
        @headerContainer.style.display = "none"

document.addEventListener "DOMContentLoaded", =>
    document.removeEventListener "DOMContentLoaded", arguments.callee


bound = (x, m, M)->
    if (x < m) then m else if (x > M) then M else x

class Promise

