From 8c36d2673b1e80d84ecf5884f0a6c07723ff6511 Mon Sep 17 00:00:00 2001 From: Ivan Zuzak Date: Sat, 30 Aug 2014 20:20:09 +0200 Subject: [PATCH 01/10] Select row when clicking the gutter --- spec/editor-component-spec.coffee | 4 ++-- src/editor-component.coffee | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/spec/editor-component-spec.coffee b/spec/editor-component-spec.coffee index d80396d23..5b30bdbdf 100644 --- a/spec/editor-component-spec.coffee +++ b/spec/editor-component-spec.coffee @@ -1331,9 +1331,9 @@ describe "EditorComponent", -> gutterNode = componentNode.querySelector('.gutter') describe "when the gutter is clicked", -> - it "moves the cursor to the beginning of the clicked row", -> + it "selects the clicked row", -> gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(4))) - expect(editor.getCursorScreenPosition()).toEqual [4, 0] + expect(editor.getSelectedScreenRange()).toEqual [[4, 0], [5, 0]] describe "when the gutter is shift-clicked", -> beforeEach -> diff --git a/src/editor-component.coffee b/src/editor-component.coffee index b14a169b8..17c0f831c 100644 --- a/src/editor-component.coffee +++ b/src/editor-component.coffee @@ -649,7 +649,7 @@ EditorComponent = React.createClass {editor} = @props clickedRow = @screenPositionForMouseEvent(event).row - editor.setCursorScreenPosition([clickedRow, 0]) + editor.setSelectedScreenRange([[clickedRow, 0], [clickedRow + 1, 0]]) @handleDragUntilMouseUp event, (screenPosition) -> dragRow = screenPosition.row From 7f14965ca829323c8bdd9a3d31b0ecd4b0199497 Mon Sep 17 00:00:00 2001 From: Ivan Zuzak Date: Sun, 31 Aug 2014 21:39:16 +0200 Subject: [PATCH 02/10] Support selecting multiple rows with meta-click --- spec/editor-component-spec.coffee | 44 +++++++++++++++++++++++++++++++ src/editor-component.coffee | 31 +++++++++++++++++++++- 2 files changed, 74 insertions(+), 1 deletion(-) diff --git a/spec/editor-component-spec.coffee b/spec/editor-component-spec.coffee index 5b30bdbdf..411b39241 100644 --- a/spec/editor-component-spec.coffee +++ b/spec/editor-component-spec.coffee @@ -1335,6 +1335,16 @@ describe "EditorComponent", -> gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(4))) expect(editor.getSelectedScreenRange()).toEqual [[4, 0], [5, 0]] + describe "when the gutter is meta-clicked", -> + it "creates a new selection for the clicked row", -> + editor.setSelectedScreenRange([[3, 0], [3, 2]]) + + gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(4), metaKey: true)) + expect(editor.getSelectedScreenRanges()).toEqual [[[3, 0], [3, 2]], [[4, 0], [5, 0]]] + + gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + expect(editor.getSelectedScreenRanges()).toEqual [[[3, 0], [3, 2]], [[4, 0], [5, 0]], [[6, 0], [7, 0]]] + describe "when the gutter is shift-clicked", -> beforeEach -> editor.setSelectedScreenRange([[3, 4], [4, 5]]) @@ -1366,6 +1376,40 @@ describe "EditorComponent", -> gutterNode.dispatchEvent(buildMouseEvent('mouseup', clientCoordinatesForScreenRowInGutter(2))) expect(editor.getSelectedScreenRange()).toEqual [[2, 0], [7, 0]] + describe "when the gutter is meta-clicked and dragged", -> + beforeEach -> + editor.setSelectedScreenRange([[3, 0], [3, 2]]) + + describe "when dragging downward", -> + it "selects the rows between the start and end of the drag", -> + gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(4), metaKey: true)) + gutterNode.dispatchEvent(buildMouseEvent('mousemove', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + nextAnimationFrame() + gutterNode.dispatchEvent(buildMouseEvent('mouseup', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + expect(editor.getSelectedScreenRanges()).toEqual [[[3, 0], [3, 2]], [[4, 0], [7, 0]]] + + it "merges overlapping selections", -> + gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(2), metaKey: true)) + gutterNode.dispatchEvent(buildMouseEvent('mousemove', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + nextAnimationFrame() + gutterNode.dispatchEvent(buildMouseEvent('mouseup', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + expect(editor.getSelectedScreenRanges()).toEqual [[[2, 0], [7, 0]]] + + describe "when dragging upward", -> + it "selects the rows between the start and end of the drag", -> + gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + gutterNode.dispatchEvent(buildMouseEvent('mousemove', clientCoordinatesForScreenRowInGutter(4), metaKey: true)) + nextAnimationFrame() + gutterNode.dispatchEvent(buildMouseEvent('mouseup', clientCoordinatesForScreenRowInGutter(4), metaKey: true)) + expect(editor.getSelectedScreenRanges()).toEqual [[[3, 0], [3, 2]], [[4, 0], [7, 0]]] + + it "merges overlapping selections", -> + gutterNode.dispatchEvent(buildMouseEvent('mousedown', clientCoordinatesForScreenRowInGutter(6), metaKey: true)) + gutterNode.dispatchEvent(buildMouseEvent('mousemove', clientCoordinatesForScreenRowInGutter(2), metaKey: true)) + nextAnimationFrame() + gutterNode.dispatchEvent(buildMouseEvent('mouseup', clientCoordinatesForScreenRowInGutter(2), metaKey: true)) + expect(editor.getSelectedScreenRanges()).toEqual [[[2, 0], [7, 0]]] + describe "when the gutter is shift-clicked and dragged", -> describe "when the shift-click is below the existing selection's tail", -> describe "when dragging downward", -> diff --git a/src/editor-component.coffee b/src/editor-component.coffee index 17c0f831c..003e9b703 100644 --- a/src/editor-component.coffee +++ b/src/editor-component.coffee @@ -1,3 +1,4 @@ +_ = require 'underscore-plus' React = require 'react-atom-fork' {div, span} = require 'reactionary-atom-fork' {debounce, defaults, isEqualForProperties} = require 'underscore-plus' @@ -640,8 +641,12 @@ EditorComponent = React.createClass onGutterMouseDown: (event) -> return unless event.button is 0 # only handle the left mouse button - if event.shiftKey + {shiftKey, metaKey, ctrlKey} = event + + if shiftKey @onGutterShiftClick(event) + else if metaKey or (ctrlKey and process.platform isnt 'darwin') + @onGutterMetaClick(event) else @onGutterClick(event) @@ -658,6 +663,30 @@ EditorComponent = React.createClass else editor.setSelectedScreenRange([[clickedRow, 0], [dragRow + 1, 0]]) + onGutterMetaClick: (event) -> + {editor} = @props + clickedRow = @screenPositionForMouseEvent(event).row + + bufferRange = editor.bufferRangeForScreenRange([[clickedRow, 0], [clickedRow + 1, 0]]) + rowSelection = editor.addSelectionForBufferRange(bufferRange) + + @handleDragUntilMouseUp event, (screenPosition) -> + dragRow = screenPosition.row + + if dragRow < clickedRow # dragging up + rowSelection.setScreenRange([[dragRow, 0], [clickedRow + 1, 0]]) + else + rowSelection.setScreenRange([[clickedRow, 0], [dragRow + 1, 0]]) + + # After updating the selected screen range, merge overlapping selections + editor.mergeIntersectingSelections() + + # The merge process will possibly destroy the current selection because + # it will be merged into another one. Therefore, we need to obtain a + # reference to the new selection that contains the originally selected row + rowSelection = _.find editor.getSelections(), (selection) -> + selection.intersectsBufferRange(bufferRange) + onGutterShiftClick: (event) -> {editor} = @props clickedRow = @screenPositionForMouseEvent(event).row From 65cae0f68d4e6c5c69c28b71eed6647c27f75722 Mon Sep 17 00:00:00 2001 From: Ivan Zuzak Date: Mon, 1 Sep 2014 18:24:04 +0200 Subject: [PATCH 03/10] Fix indentation to make coffeelint happy --- src/editor-component.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/editor-component.coffee b/src/editor-component.coffee index 003e9b703..52ca61bc6 100644 --- a/src/editor-component.coffee +++ b/src/editor-component.coffee @@ -685,7 +685,7 @@ EditorComponent = React.createClass # it will be merged into another one. Therefore, we need to obtain a # reference to the new selection that contains the originally selected row rowSelection = _.find editor.getSelections(), (selection) -> - selection.intersectsBufferRange(bufferRange) + selection.intersectsBufferRange(bufferRange) onGutterShiftClick: (event) -> {editor} = @props From 29ad748aa4fbd9365050a16b2998c5140f19f3cd Mon Sep 17 00:00:00 2001 From: Ivan Zuzak Date: Wed, 3 Sep 2014 18:52:50 +0200 Subject: [PATCH 04/10] Dont propagate fold icon clicks to editor component --- src/gutter-component.coffee | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/gutter-component.coffee b/src/gutter-component.coffee index e9eeddaf9..c6cf62490 100644 --- a/src/gutter-component.coffee +++ b/src/gutter-component.coffee @@ -21,7 +21,7 @@ GutterComponent = React.createClass if gutterBackgroundColor isnt 'rbga(0, 0, 0, 0)' backgroundColor = gutterBackgroundColor - div className: 'gutter', onClick: @onClick, onMouseDown: onMouseDown, + div className: 'gutter', onClick: @onClick, onMouseDown: @onMouseDown, div className: 'line-numbers', ref: 'lineNumbers', style: height: Math.max(scrollHeight, scrollViewHeight) WebkitTransform: @getTransform() @@ -215,6 +215,14 @@ GutterComponent = React.createClass lineNumberNodeForScreenRow: (screenRow) -> @lineNumberNodesById[@lineNumberIdsByScreenRow[screenRow]] + onMouseDown: (event) -> + {editor} = @props + {target} = event + lineNumber = target.parentNode + + unless target.classList.contains('icon-right') and lineNumber.classList.contains('foldable') + @props.onMouseDown(event) + onClick: (event) -> {editor} = @props {target} = event From ebbfaa23ce9267528f6bed802920517ee2c9b42d Mon Sep 17 00:00:00 2001 From: Ivan Zuzak Date: Wed, 3 Sep 2014 18:54:46 +0200 Subject: [PATCH 05/10] Preserve folds when selecting rows by clicking the gutter --- src/editor-component.coffee | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/src/editor-component.coffee b/src/editor-component.coffee index 52ca61bc6..cc248c69a 100644 --- a/src/editor-component.coffee +++ b/src/editor-component.coffee @@ -654,32 +654,32 @@ EditorComponent = React.createClass {editor} = @props clickedRow = @screenPositionForMouseEvent(event).row - editor.setSelectedScreenRange([[clickedRow, 0], [clickedRow + 1, 0]]) + editor.setSelectedScreenRange([[clickedRow, 0], [clickedRow + 1, 0]], preserveFolds: true) @handleDragUntilMouseUp event, (screenPosition) -> dragRow = screenPosition.row if dragRow < clickedRow # dragging up - editor.setSelectedScreenRange([[dragRow, 0], [clickedRow + 1, 0]]) + editor.setSelectedScreenRange([[dragRow, 0], [clickedRow + 1, 0]], preserveFolds: true) else - editor.setSelectedScreenRange([[clickedRow, 0], [dragRow + 1, 0]]) + editor.setSelectedScreenRange([[clickedRow, 0], [dragRow + 1, 0]], preserveFolds: true) onGutterMetaClick: (event) -> {editor} = @props clickedRow = @screenPositionForMouseEvent(event).row bufferRange = editor.bufferRangeForScreenRange([[clickedRow, 0], [clickedRow + 1, 0]]) - rowSelection = editor.addSelectionForBufferRange(bufferRange) + rowSelection = editor.addSelectionForBufferRange(bufferRange, preserveFolds: true) @handleDragUntilMouseUp event, (screenPosition) -> dragRow = screenPosition.row if dragRow < clickedRow # dragging up - rowSelection.setScreenRange([[dragRow, 0], [clickedRow + 1, 0]]) + rowSelection.setScreenRange([[dragRow, 0], [clickedRow + 1, 0]], preserveFolds: true) else - rowSelection.setScreenRange([[clickedRow, 0], [dragRow + 1, 0]]) + rowSelection.setScreenRange([[clickedRow, 0], [dragRow + 1, 0]], preserveFolds: true) # After updating the selected screen range, merge overlapping selections - editor.mergeIntersectingSelections() + editor.mergeIntersectingSelections(preserveFolds: true) # The merge process will possibly destroy the current selection because # it will be merged into another one. Therefore, we need to obtain a @@ -700,9 +700,9 @@ EditorComponent = React.createClass @handleDragUntilMouseUp event, (screenPosition) -> dragRow = screenPosition.row if dragRow < tailPosition.row # dragging up - editor.setSelectedScreenRange([[dragRow, 0], tailPosition]) + editor.setSelectedScreenRange([[dragRow, 0], tailPosition], preserveFolds: true) else - editor.setSelectedScreenRange([tailPosition, [dragRow + 1, 0]]) + editor.setSelectedScreenRange([tailPosition, [dragRow + 1, 0]], preserveFolds: true) onStylesheetsChanged: (stylesheet) -> return unless @performedInitialMeasurement From 8a6e72f21f18a85745dfbe1503e5984049216417 Mon Sep 17 00:00:00 2001 From: Ivan Zuzak Date: Thu, 4 Sep 2014 13:57:41 +0200 Subject: [PATCH 06/10] Respect preserveFolds attribute when creating selections from markers --- src/editor.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/editor.coffee b/src/editor.coffee index 9753ad409..629955d3f 100644 --- a/src/editor.coffee +++ b/src/editor.coffee @@ -1722,7 +1722,7 @@ class Editor extends Model selection = new Selection(_.extend({editor: this, marker, cursor}, options)) @selections.push(selection) selectionBufferRange = selection.getBufferRange() - @mergeIntersectingSelections() + @mergeIntersectingSelections(preserveFolds: marker.getAttributes().preserveFolds) if selection.destroyed for selection in @getSelections() if selection.intersectsBufferRange(selectionBufferRange) From 55913626ccb264b8bc9d94641061172d6dc53e32 Mon Sep 17 00:00:00 2001 From: Kevin Sawicki Date: Wed, 3 Sep 2014 09:45:45 -0700 Subject: [PATCH 07/10] Upgrade to fuzzaldrin 2.1 --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 6dc56fa54..96851f421 100644 --- a/package.json +++ b/package.json @@ -31,7 +31,7 @@ "first-mate": "^2.0.5", "fs-plus": "^2.2.6", "fstream": "0.1.24", - "fuzzaldrin": "^1.1", + "fuzzaldrin": "^2.1", "git-utils": "^2.1.4", "grim": "0.12.0", "guid": "0.0.10", From 641698330f5a142156409dd66b0b4d7247f5fd0b Mon Sep 17 00:00:00 2001 From: Kevin Sawicki Date: Wed, 3 Sep 2014 09:53:38 -0700 Subject: [PATCH 08/10] Upgrade to fuzzy-finder@0.58 --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 96851f421..c180d81d0 100644 --- a/package.json +++ b/package.json @@ -84,7 +84,7 @@ "exception-reporting": "0.20.0", "feedback": "0.33.0", "find-and-replace": "0.132.0", - "fuzzy-finder": "0.57.0", + "fuzzy-finder": "0.58.0", "git-diff": "0.39.0", "go-to-line": "0.25.0", "grammar-selector": "0.29.0", From b5676adf8adfe8ab8b42f3e3d7b5e718e26973cc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ivan=20=C5=BDu=C5=BEak?= Date: Thu, 4 Sep 2014 21:52:00 +0200 Subject: [PATCH 09/10] Remove check for deprecated function calls --- spec/spec-helper.coffee | 1 - 1 file changed, 1 deletion(-) diff --git a/spec/spec-helper.coffee b/spec/spec-helper.coffee index 6fdbed35b..46d43ed7d 100644 --- a/spec/spec-helper.coffee +++ b/spec/spec-helper.coffee @@ -138,7 +138,6 @@ afterEach -> jasmine.unspy(atom, 'saveSync') ensureNoPathSubscriptions() atom.syntax.off() - ensureNoDeprecatedFunctionsCalled() if isCoreSpec waits(0) # yield to ui thread to make screen update more frequently ensureNoPathSubscriptions = -> From eb9d4ba8166c61ee8ed481dbb73f16c6685bf0ec Mon Sep 17 00:00:00 2001 From: Kevin Sawicki Date: Thu, 4 Sep 2014 13:39:49 -0700 Subject: [PATCH 10/10] :memo: Use ### for example sections --- src/git.coffee | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/git.coffee b/src/git.coffee index 7cf4014a9..08a24d23b 100644 --- a/src/git.coffee +++ b/src/git.coffee @@ -27,12 +27,14 @@ Task = require './task' # # ## Examples # +# ### Logging the URL of the origin remote +# # ```coffee # git = atom.project.getRepo() # console.log git.getOriginUrl() # ``` # -# ## Requiring in packages +# ### Requiring in packages # # ```coffee # {Git} = require 'atom'