From 7ac0cdcbf5ec5e06779ea6e51ab704d525984443 Mon Sep 17 00:00:00 2001 From: Antonio Scandurra Date: Fri, 12 Jun 2015 13:12:50 +0200 Subject: [PATCH] Start porting `TextEditorComponent` spec --- spec/text-editor-component-spec.coffee | 123 ++++++++++++++++-------- src/gutter-container-component.coffee | 5 +- src/line-number-gutter-component.coffee | 9 +- src/line-numbers-tile-component.coffee | 12 ++- src/text-editor-component.coffee | 2 +- 5 files changed, 102 insertions(+), 49 deletions(-) diff --git a/spec/text-editor-component-spec.coffee b/spec/text-editor-component-spec.coffee index 6749e7803..808eb527e 100644 --- a/spec/text-editor-component-spec.coffee +++ b/spec/text-editor-component-spec.coffee @@ -5,9 +5,9 @@ TextEditorView = require '../src/text-editor-view' TextEditorComponent = require '../src/text-editor-component' nbsp = String.fromCharCode(160) -describe "TextEditorComponent", -> +fdescribe "TextEditorComponent", -> [contentNode, editor, wrapperView, wrapperNode, component, componentNode, verticalScrollbarNode, horizontalScrollbarNode] = [] - [lineHeightInPixels, charWidth, nextAnimationFrame, noAnimationFrame, tileSize] = [] + [lineHeightInPixels, charWidth, nextAnimationFrame, noAnimationFrame, tileSize, tileHeightInPixels] = [] beforeEach -> tileSize = 3 @@ -45,6 +45,7 @@ describe "TextEditorComponent", -> component.setFontSize(20) lineHeightInPixels = editor.getLineHeightInPixels() + tileHeightInPixels = tileSize * lineHeightInPixels charWidth = editor.getDefaultCharWidth() componentNode = component.getDomNode() verticalScrollbarNode = componentNode.querySelector('.vertical-scrollbar') @@ -80,11 +81,10 @@ describe "TextEditorComponent", -> it "renders the currently-visible lines in a tiled fashion", -> wrapperNode.style.height = 6.5 * lineHeightInPixels + 'px' - tileHeight = tileSize * lineHeightInPixels component.measureDimensions() nextAnimationFrame() - tilesNodes = componentNode.querySelectorAll(".tile") + tilesNodes = componentNode.querySelector(".lines").querySelectorAll(".tile") expect(tilesNodes.length).toBe(3) @@ -94,13 +94,13 @@ describe "TextEditorComponent", -> expectTileContainsRow(tilesNodes[0], 1, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 2, top: 2 * lineHeightInPixels) - expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeight}px, 0px)" + expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeightInPixels}px, 0px)" expect(tilesNodes[1].querySelectorAll(".line").length).toBe(tileSize) expectTileContainsRow(tilesNodes[1], 3, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 4, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 5, top: 2 * lineHeightInPixels) - expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeight}px, 0px)" + expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeightInPixels}px, 0px)" expect(tilesNodes[2].querySelectorAll(".line").length).toBe(tileSize) expectTileContainsRow(tilesNodes[2], 6, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[2], 7, top: 1 * lineHeightInPixels) @@ -112,24 +112,24 @@ describe "TextEditorComponent", -> verticalScrollbarNode.dispatchEvent(new UIEvent('scroll')) nextAnimationFrame() - tilesNodes = componentNode.querySelectorAll(".tile") + tilesNodes = componentNode.querySelector(".lines").querySelectorAll(".tile") expect(component.lineNodeForScreenRow(2)).toBeUndefined() expect(tilesNodes.length).toBe(3) - expect(tilesNodes[0].style['-webkit-transform']).toBe "translate3d(0px, -5px, 0px)" + expect(tilesNodes[0].style['-webkit-transform']).toBe "translate3d(0px, #{0 * tileHeightInPixels - 5}px, 0px)" expect(tilesNodes[0].querySelectorAll(".line").length).toBe(tileSize) expectTileContainsRow(tilesNodes[0], 3, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 4, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 5, top: 2 * lineHeightInPixels) - expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeight - 5}px, 0px)" + expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeightInPixels - 5}px, 0px)" expect(tilesNodes[1].querySelectorAll(".line").length).toBe(tileSize) expectTileContainsRow(tilesNodes[1], 6, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 7, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 8, top: 2 * lineHeightInPixels) - expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeight - 5}px, 0px)" + expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeightInPixels - 5}px, 0px)" expect(tilesNodes[2].querySelectorAll(".line").length).toBe(tileSize) expectTileContainsRow(tilesNodes[2], 9, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[2], 10, top: 1 * lineHeightInPixels) @@ -137,19 +137,18 @@ describe "TextEditorComponent", -> it "updates the top position of subsequent tiles when lines are inserted or removed", -> wrapperNode.style.height = 6.5 * lineHeightInPixels + 'px' - tileHeight = tileSize * lineHeightInPixels component.measureDimensions() editor.getBuffer().deleteRows(0, 1) nextAnimationFrame() - tilesNodes = componentNode.querySelectorAll(".tile") + tilesNodes = componentNode.querySelector(".lines").querySelectorAll(".tile") expect(tilesNodes[0].style['-webkit-transform']).toBe "translate3d(0px, 0px, 0px)" expectTileContainsRow(tilesNodes[0], 0, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 1, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 2, top: 2 * lineHeightInPixels) - expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeight}px, 0px)" + expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeightInPixels}px, 0px)" expectTileContainsRow(tilesNodes[1], 3, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 4, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 5, top: 2 * lineHeightInPixels) @@ -157,19 +156,19 @@ describe "TextEditorComponent", -> editor.getBuffer().insert([0, 0], '\n\n') nextAnimationFrame() - tilesNodes = componentNode.querySelectorAll(".tile") + tilesNodes = componentNode.querySelector(".lines").querySelectorAll(".tile") expect(tilesNodes[0].style['-webkit-transform']).toBe "translate3d(0px, 0px, 0px)" expectTileContainsRow(tilesNodes[0], 0, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 1, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[0], 2, top: 2 * lineHeightInPixels) - expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeight}px, 0px)" + expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeightInPixels}px, 0px)" expectTileContainsRow(tilesNodes[1], 3, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 4, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[1], 5, top: 2 * lineHeightInPixels) - expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeight}px, 0px)" + expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeightInPixels}px, 0px)" expectTileContainsRow(tilesNodes[2], 6, top: 0 * lineHeightInPixels) expectTileContainsRow(tilesNodes[2], 7, top: 1 * lineHeightInPixels) expectTileContainsRow(tilesNodes[2], 8, top: 2 * lineHeightInPixels) @@ -543,47 +542,90 @@ describe "TextEditorComponent", -> expect(foldedLineNode.querySelector('.fold-marker')).toBeFalsy() describe "gutter rendering", -> - it "renders the currently-visible line numbers", -> + expectTileContainsRow = (tileNode, screenRow, {top, text}) -> + lineNode = tileNode.querySelector("[data-screen-row='#{screenRow}']") + + expect(lineNode.offsetTop).toBe(top) + expect(lineNode.textContent).toBe(text) + + it "renders the currently-visible line numbers in a tiled fashion", -> wrapperNode.style.height = 4.5 * lineHeightInPixels + 'px' component.measureDimensions() nextAnimationFrame() - expect(componentNode.querySelectorAll('.line-number').length).toBe 6 + 1 # visible line-numbers + dummy line number - expect(component.lineNumberNodeForScreenRow(0).textContent).toBe "#{nbsp}1" - expect(component.lineNumberNodeForScreenRow(5).textContent).toBe "#{nbsp}6" + tilesNodes = componentNode.querySelector(".line-numbers").querySelectorAll(".tile") - verticalScrollbarNode.scrollTop = 2.5 * lineHeightInPixels + expect(tilesNodes.length).toBe(3) + expect(tilesNodes[0].style['-webkit-transform']).toBe "translate3d(0px, 0px, 0px)" + + expect(tilesNodes[0].querySelectorAll('.line-number').length).toBe 3 + expectTileContainsRow(tilesNodes[0], 0, top: lineHeightInPixels * 0, text: "#{nbsp}1") + expectTileContainsRow(tilesNodes[0], 1, top: lineHeightInPixels * 1, text: "#{nbsp}2") + expectTileContainsRow(tilesNodes[0], 2, top: lineHeightInPixels * 2, text: "#{nbsp}3") + + expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeightInPixels}px, 0px)" + expect(tilesNodes[1].querySelectorAll('.line-number').length).toBe 3 + expectTileContainsRow(tilesNodes[1], 3, top: lineHeightInPixels * 0, text: "#{nbsp}4") + expectTileContainsRow(tilesNodes[1], 4, top: lineHeightInPixels * 1, text: "#{nbsp}5") + expectTileContainsRow(tilesNodes[1], 5, top: lineHeightInPixels * 2, text: "#{nbsp}6") + + expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeightInPixels}px, 0px)" + expect(tilesNodes[2].querySelectorAll('.line-number').length).toBe 3 + expectTileContainsRow(tilesNodes[2], 6, top: lineHeightInPixels * 0, text: "#{nbsp}7") + expectTileContainsRow(tilesNodes[2], 7, top: lineHeightInPixels * 1, text: "#{nbsp}8") + expectTileContainsRow(tilesNodes[2], 8, top: lineHeightInPixels * 2, text: "#{nbsp}9") + + verticalScrollbarNode.scrollTop = tileSize * lineHeightInPixels + 5 verticalScrollbarNode.dispatchEvent(new UIEvent('scroll')) nextAnimationFrame() - expect(componentNode.querySelectorAll('.line-number').length).toBe 6 + 1 # visible line-numbers + dummy line number + tilesNodes = componentNode.querySelector(".line-numbers").querySelectorAll(".tile") - expect(component.lineNumberNodeForScreenRow(2).textContent).toBe "#{nbsp}3" - expect(component.lineNumberNodeForScreenRow(2).offsetTop).toBe 2 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(7).textContent).toBe "#{nbsp}8" - expect(component.lineNumberNodeForScreenRow(7).offsetTop).toBe 7 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(2)).toBeUndefined() + expect(tilesNodes.length).toBe(3) + + expect(tilesNodes[0].style['-webkit-transform']).toBe "translate3d(0px, #{0 * tileHeightInPixels - 5}px, 0px)" + expect(tilesNodes[0].querySelectorAll(".line-number").length).toBe(tileSize) + expectTileContainsRow(tilesNodes[0], 3, top: lineHeightInPixels * 0, text: "#{nbsp}4") + expectTileContainsRow(tilesNodes[0], 4, top: lineHeightInPixels * 1, text: "#{nbsp}5") + expectTileContainsRow(tilesNodes[0], 5, top: lineHeightInPixels * 2, text: "#{nbsp}6") + + expect(tilesNodes[1].style['-webkit-transform']).toBe "translate3d(0px, #{1 * tileHeightInPixels - 5}px, 0px)" + expect(tilesNodes[1].querySelectorAll(".line-number").length).toBe(tileSize) + expectTileContainsRow(tilesNodes[1], 6, top: 0 * lineHeightInPixels, text: "#{nbsp}7") + expectTileContainsRow(tilesNodes[1], 7, top: 1 * lineHeightInPixels, text: "#{nbsp}8") + expectTileContainsRow(tilesNodes[1], 8, top: 2 * lineHeightInPixels, text: "#{nbsp}9") + + expect(tilesNodes[2].style['-webkit-transform']).toBe "translate3d(0px, #{2 * tileHeightInPixels - 5}px, 0px)" + expect(tilesNodes[2].querySelectorAll(".line-number").length).toBe(tileSize) + expectTileContainsRow(tilesNodes[2], 9, top: 0 * lineHeightInPixels, text: "10") + expectTileContainsRow(tilesNodes[2], 10, top: 1 * lineHeightInPixels, text: "11") + expectTileContainsRow(tilesNodes[2], 11, top: 2 * lineHeightInPixels, text: "12") it "updates the translation of subsequent line numbers when lines are inserted or removed", -> editor.getBuffer().insert([0, 0], '\n\n') nextAnimationFrame() lineNumberNodes = componentNode.querySelectorAll('.line-number') - expect(component.lineNumberNodeForScreenRow(0).offsetTop).toBe 0 + expect(component.lineNumberNodeForScreenRow(0).offsetTop).toBe 0 * lineHeightInPixels expect(component.lineNumberNodeForScreenRow(1).offsetTop).toBe 1 * lineHeightInPixels expect(component.lineNumberNodeForScreenRow(2).offsetTop).toBe 2 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(3).offsetTop).toBe 3 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(4).offsetTop).toBe 4 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(3).offsetTop).toBe 0 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(4).offsetTop).toBe 1 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(5).offsetTop).toBe 2 * lineHeightInPixels editor.getBuffer().insert([0, 0], '\n\n') nextAnimationFrame() - expect(component.lineNumberNodeForScreenRow(0).offsetTop).toBe 0 + expect(component.lineNumberNodeForScreenRow(0).offsetTop).toBe 0 * lineHeightInPixels expect(component.lineNumberNodeForScreenRow(1).offsetTop).toBe 1 * lineHeightInPixels expect(component.lineNumberNodeForScreenRow(2).offsetTop).toBe 2 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(3).offsetTop).toBe 3 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(4).offsetTop).toBe 4 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(5).offsetTop).toBe 5 * lineHeightInPixels - expect(component.lineNumberNodeForScreenRow(6).offsetTop).toBe 6 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(3).offsetTop).toBe 0 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(4).offsetTop).toBe 1 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(5).offsetTop).toBe 2 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(6).offsetTop).toBe 0 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(7).offsetTop).toBe 1 * lineHeightInPixels + expect(component.lineNumberNodeForScreenRow(8).offsetTop).toBe 2 * lineHeightInPixels it "renders • characters for soft-wrapped lines", -> editor.setSoftWrapped(true) @@ -592,13 +634,16 @@ describe "TextEditorComponent", -> component.measureDimensions() nextAnimationFrame() - expect(componentNode.querySelectorAll('.line-number').length).toBe 6 + 1 # 1 dummy line + expect(componentNode.querySelectorAll('.line-number').length).toBe 9 + 1 # 3 line-numbers tiles + 1 dummy line expect(component.lineNumberNodeForScreenRow(0).textContent).toBe "#{nbsp}1" expect(component.lineNumberNodeForScreenRow(1).textContent).toBe "#{nbsp}•" expect(component.lineNumberNodeForScreenRow(2).textContent).toBe "#{nbsp}2" expect(component.lineNumberNodeForScreenRow(3).textContent).toBe "#{nbsp}•" expect(component.lineNumberNodeForScreenRow(4).textContent).toBe "#{nbsp}3" expect(component.lineNumberNodeForScreenRow(5).textContent).toBe "#{nbsp}•" + expect(component.lineNumberNodeForScreenRow(6).textContent).toBe "#{nbsp}4" + expect(component.lineNumberNodeForScreenRow(7).textContent).toBe "#{nbsp}•" + expect(component.lineNumberNodeForScreenRow(8).textContent).toBe "#{nbsp}•" it "pads line numbers to be right-justified based on the maximum number of line number digits", -> editor.getBuffer().setText([1..10].join('\n')) @@ -959,7 +1004,7 @@ describe "TextEditorComponent", -> it "renders 2 regions for 2-line selections", -> editor.setSelectedScreenRange([[1, 6], [2, 10]]) nextAnimationFrame() - tileNode = componentNode.querySelectorAll(".tile")[0] + tileNode = componentNode.querySelector(".lines").querySelectorAll(".tile")[0] regions = tileNode.querySelectorAll('.selection .region') expect(regions.length).toBe 2 @@ -980,7 +1025,7 @@ describe "TextEditorComponent", -> nextAnimationFrame() # Tile 0 - tileNode = componentNode.querySelectorAll(".tile")[0] + tileNode = componentNode.querySelector(".lines").querySelectorAll(".tile")[0] regions = tileNode.querySelectorAll('.selection .region') expect(regions.length).toBe(3) @@ -1003,7 +1048,7 @@ describe "TextEditorComponent", -> expect(region3Rect.right).toBe tileNode.getBoundingClientRect().right # Tile 3 - tileNode = componentNode.querySelectorAll(".tile")[1] + tileNode = componentNode.querySelector(".lines").querySelectorAll(".tile")[1] regions = tileNode.querySelectorAll('.selection .region') expect(regions.length).toBe(3) @@ -2015,7 +2060,7 @@ describe "TextEditorComponent", -> component.measureDimensions() nextAnimationFrame() - tilesNodes = componentNode.querySelectorAll(".tile") + tilesNodes = componentNode.querySelector(".lines").querySelectorAll(".tile") top = 0 for tileNode in tilesNodes diff --git a/src/gutter-container-component.coffee b/src/gutter-container-component.coffee index 5fa2f85f4..9e0be4d8d 100644 --- a/src/gutter-container-component.coffee +++ b/src/gutter-container-component.coffee @@ -7,8 +7,7 @@ LineNumberGutterComponent = require './line-number-gutter-component' module.exports = class GutterContainerComponent - - constructor: ({@onLineNumberGutterMouseDown, @editor}) -> + constructor: ({@onLineNumberGutterMouseDown, @editor, @presenter}) -> # An array of objects of the form: {name: {String}, component: {Object}} @gutterComponents = [] @gutterComponentsByGutterName = {} @@ -35,7 +34,7 @@ class GutterContainerComponent gutterComponent = @gutterComponentsByGutterName[gutter.name] if not gutterComponent if gutter.name is 'line-number' - gutterComponent = new LineNumberGutterComponent({onMouseDown: @onLineNumberGutterMouseDown, @editor, gutter}) + gutterComponent = new LineNumberGutterComponent({onMouseDown: @onLineNumberGutterMouseDown, @presenter, @editor, gutter}) @lineNumberGutterComponent = gutterComponent else gutterComponent = new CustomGutterComponent({gutter}) diff --git a/src/line-number-gutter-component.coffee b/src/line-number-gutter-component.coffee index a848e600c..602558fc5 100644 --- a/src/line-number-gutter-component.coffee +++ b/src/line-number-gutter-component.coffee @@ -9,7 +9,7 @@ module.exports = class LineNumberGutterComponent extends TiledComponent dummyLineNumberNode: null - constructor: ({@onMouseDown, @editor, @gutter}) -> + constructor: ({@onMouseDown, @editor, @presenter, @gutter}) -> @lineNumberNodesById = {} @visible = true @@ -74,10 +74,9 @@ class LineNumberGutterComponent extends TiledComponent @dummyLineNumberNode.innerHTML = DummyLineNumberComponent.buildLineNumberInnerHTML(0, false) lineNumberNodeForScreenRow: (screenRow) -> - for id, lineNumberState of @oldState.lineNumbers - if lineNumberState.screenRow is screenRow - return @lineNumberNodesById[id] - null + tile = @presenter.tileForRow(screenRow) + + @componentsByTileId[tile]?.lineNumberNodeForScreenRow(screenRow) onMouseDown: (event) => {target} = event diff --git a/src/line-numbers-tile-component.coffee b/src/line-numbers-tile-component.coffee index a0ae8d49a..a36ed4330 100644 --- a/src/line-numbers-tile-component.coffee +++ b/src/line-numbers-tile-component.coffee @@ -30,12 +30,16 @@ class LineNumbersTileComponent @domNode.style.display = @newTileState.display @oldTileState.display = @newTileState.display + if @newState.backgroundColor isnt @oldState.backgroundColor + @domNode.style.backgroundColor = @newState.backgroundColor + @oldState.backgroundColor = @newState.backgroundColor + if @newTileState.height isnt @oldTileState.height @domNode.style.height = @newTileState.height + 'px' @oldTileState.height = @newTileState.height if @newTileState.top isnt @oldTileState.top - @domNode.style['-webkit-transform'] = "translate3d(#{@newTileState.left}px, #{@newTileState.top}px, 0px)" + @domNode.style['-webkit-transform'] = "translate3d(0, #{@newTileState.top}px, 0px)" @oldTileState.top = @newTileState.top @oldTileState.left = @newTileState.left @@ -127,3 +131,9 @@ class LineNumbersTileComponent className += " " + decorationClasses.join(' ') if decorationClasses? className += " foldable" if foldable and not softWrapped className + + lineNumberNodeForScreenRow: (screenRow) -> + for id, lineNumberState of @oldTileState.lineNumbers + if lineNumberState.screenRow is screenRow + return @lineNumberNodesById[id] + null diff --git a/src/text-editor-component.coffee b/src/text-editor-component.coffee index ac71da748..8802d8022 100644 --- a/src/text-editor-component.coffee +++ b/src/text-editor-component.coffee @@ -165,7 +165,7 @@ class TextEditorComponent @overlayManager?.measureOverlays() mountGutterContainerComponent: -> - @gutterContainerComponent = new GutterContainerComponent({@editor, @onLineNumberGutterMouseDown}) + @gutterContainerComponent = new GutterContainerComponent({@editor, @onLineNumberGutterMouseDown, @presenter}) @domNode.insertBefore(@gutterContainerComponent.getDomNode(), @domNode.firstChild) becameVisible: ->