aboutsummaryrefslogtreecommitdiff
path: root/atom/packages/vim-mode/lib/operators
diff options
context:
space:
mode:
authorBen Beltran <ben@nsovocal.com>2015-09-28 12:39:59 -0500
committerBen Beltran <ben@nsovocal.com>2015-09-28 12:39:59 -0500
commit455f099b504ec07dd492ab31987ae05a6f6774c7 (patch)
tree22b0c7fd8e492733b97e661750a2d79c46da451d /atom/packages/vim-mode/lib/operators
parent24c7594d62d8d7fbbcdb64b11ce4adc5d8e6991a (diff)
Adds atom packages
Diffstat (limited to 'atom/packages/vim-mode/lib/operators')
-rw-r--r--atom/packages/vim-mode/lib/operators/general-operators.coffee77
-rw-r--r--atom/packages/vim-mode/lib/operators/indent-operators.coffee21
-rw-r--r--atom/packages/vim-mode/lib/operators/input.coffee104
-rw-r--r--atom/packages/vim-mode/lib/operators/put-operator.coffee4
-rw-r--r--atom/packages/vim-mode/lib/operators/replace-operator.coffee6
5 files changed, 103 insertions, 109 deletions
diff --git a/atom/packages/vim-mode/lib/operators/general-operators.coffee b/atom/packages/vim-mode/lib/operators/general-operators.coffee
index dd99256..9547941 100644
--- a/atom/packages/vim-mode/lib/operators/general-operators.coffee
+++ b/atom/packages/vim-mode/lib/operators/general-operators.coffee
@@ -12,11 +12,8 @@ class Operator
vimState: null
motion: null
complete: null
- selectOptions: null
- # selectOptions - The options object to pass through to the motion when
- # selecting.
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
@complete = false
# Public: Determines when the command can be executed.
@@ -76,14 +73,9 @@ class OperatorWithInput extends Operator
#
class Delete extends Operator
register: null
- allowEOL: null
- # allowEOL - Determines whether the cursor should be allowed to rest on the
- # end of line character or not.
- constructor: (@editor, @vimState, {@allowEOL, @selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
@complete = false
- @selectOptions ?= {}
- @selectOptions.requireEOL ?= true
@register = settings.defaultRegister()
# Public: Deletes the text selected by the given motion.
@@ -92,27 +84,28 @@ class Delete extends Operator
#
# Returns nothing.
execute: (count) ->
- if _.contains(@motion.select(count, @selectOptions), true)
+ if _.contains(@motion.select(count), true)
@setTextRegister(@register, @editor.getSelectedText())
- for selection in @editor.getSelections()
- selection.deleteSelectedText()
+ @editor.transact =>
+ for selection in @editor.getSelections()
+ selection.deleteSelectedText()
for cursor in @editor.getCursors()
if @motion.isLinewise?()
cursor.skipLeadingWhitespace()
else
cursor.moveLeft() if cursor.isAtEndOfLine() and not cursor.isAtBeginningOfLine()
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
#
# It toggles the case of everything selected by the following motion
#
class ToggleCase extends Operator
- constructor: (@editor, @vimState, {@complete, @selectOptions}={}) ->
+ constructor: (@editor, @vimState, {@complete}={}) ->
- execute: (count=1) ->
+ execute: (count) ->
if @motion?
- if _.contains(@motion.select(count, @selectOptions), true)
+ if _.contains(@motion.select(count), true)
@editor.replaceSelectedText {}, (text) ->
text.split('').map((char) ->
lower = char.toLowerCase()
@@ -126,7 +119,7 @@ class ToggleCase extends Operator
for cursor in @editor.getCursors()
point = cursor.getBufferPosition()
lineLength = @editor.lineTextForBufferRow(point.row).length
- cursorCount = Math.min(count, lineLength - point.column)
+ cursorCount = Math.min(count ? 1, lineLength - point.column)
_.times cursorCount, =>
point = cursor.getBufferPosition()
@@ -140,35 +133,35 @@ class ToggleCase extends Operator
cursor.moveRight() unless point.column >= lineLength - 1
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
#
# In visual mode or after `g` with a motion, it makes the selection uppercase
#
class UpperCase extends Operator
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
@complete = false
- execute: (count=1) ->
- if _.contains(@motion.select(count, @selectOptions), true)
+ execute: (count) ->
+ if _.contains(@motion.select(count), true)
@editor.replaceSelectedText {}, (text) ->
text.toUpperCase()
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
#
# In visual mode or after `g` with a motion, it makes the selection lowercase
#
class LowerCase extends Operator
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
@complete = false
- execute: (count=1) ->
- if _.contains(@motion.select(count, @selectOptions), true)
+ execute: (count) ->
+ if _.contains(@motion.select(count), true)
@editor.replaceSelectedText {}, (text) ->
text.toLowerCase()
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
#
# It copies everything selected by the following motion.
@@ -176,7 +169,7 @@ class LowerCase extends Operator
class Yank extends Operator
register: null
- constructor: (@editor, @vimState, {@allowEOL, @selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
@register = settings.defaultRegister()
# Public: Copies the text selected by the given motion.
@@ -185,13 +178,20 @@ class Yank extends Operator
#
# Returns nothing.
execute: (count) ->
+ oldTop = @editor.getScrollTop()
+ oldLeft = @editor.getScrollLeft()
+ oldLastCursorPosition = @editor.getCursorBufferPosition()
+
originalPositions = @editor.getCursorBufferPositions()
if _.contains(@motion.select(count), true)
text = @editor.getSelectedText()
startPositions = _.pluck(@editor.getSelectedBufferRanges(), "start")
newPositions = for originalPosition, i in originalPositions
- if startPositions[i] and (@vimState.mode is 'visual' or not @motion.isLinewise?())
- Point.min(startPositions[i], originalPositions[i])
+ if startPositions[i]
+ position = Point.min(startPositions[i], originalPositions[i])
+ if @vimState.mode isnt 'visual' and @motion.isLinewise?()
+ position = new Point(position.row, originalPositions[i].column)
+ position
else
originalPosition
else
@@ -201,13 +201,18 @@ class Yank extends Operator
@setTextRegister(@register, text)
@editor.setSelectedBufferRanges(newPositions.map (p) -> new Range(p, p))
- @vimState.activateCommandMode()
+
+ if oldLastCursorPosition.isEqual(@editor.getCursorBufferPosition())
+ @editor.setScrollLeft(oldLeft)
+ @editor.setScrollTop(oldTop)
+
+ @vimState.activateNormalMode()
#
# It combines the current line with the following line.
#
class Join extends Operator
- constructor: (@editor, @vimState, {@selectOptions}={}) -> @complete = true
+ constructor: (@editor, @vimState) -> @complete = true
# Public: Combines the current with the following lines
#
@@ -218,13 +223,13 @@ class Join extends Operator
@editor.transact =>
_.times count, =>
@editor.joinLines()
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
#
# Repeat the last operation
#
class Repeat extends Operator
- constructor: (@editor, @vimState, {@selectOptions}={}) -> @complete = true
+ constructor: (@editor, @vimState) -> @complete = true
isRecordable: -> false
@@ -237,7 +242,7 @@ class Repeat extends Operator
# It creates a mark at the current cursor position
#
class Mark extends OperatorWithInput
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
super(@editor, @vimState)
@viewModel = new ViewModel(this, class: 'mark', singleChar: true, hidden: true)
@@ -247,7 +252,7 @@ class Mark extends OperatorWithInput
# Returns nothing.
execute: ->
@vimState.setMark(@input.characters, @editor.getCursorBufferPosition())
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
module.exports = {
Operator, OperatorWithInput, OperatorError, Delete, ToggleCase,
diff --git a/atom/packages/vim-mode/lib/operators/indent-operators.coffee b/atom/packages/vim-mode/lib/operators/indent-operators.coffee
index 0ad37e0..ba3c155 100644
--- a/atom/packages/vim-mode/lib/operators/indent-operators.coffee
+++ b/atom/packages/vim-mode/lib/operators/indent-operators.coffee
@@ -1,17 +1,24 @@
+_ = require 'underscore-plus'
{Operator} = require './general-operators'
class AdjustIndentation extends Operator
- execute: (count=1) ->
+ execute: (count) ->
mode = @vimState.mode
@motion.select(count)
- {start} = @editor.getSelectedBufferRange()
+ originalRanges = @editor.getSelectedBufferRanges()
- @indent()
+ if mode is 'visual'
+ @editor.transact =>
+ _.times(count ? 1, => @indent())
+ else
+ @indent()
- if mode isnt 'visual'
- @editor.setCursorBufferPosition([start.row, 0])
- @editor.moveToFirstCharacterOfLine()
- @vimState.activateCommandMode()
+ @editor.clearSelections()
+ @editor.getLastCursor().setBufferPosition([originalRanges.shift().start.row, 0])
+ for range in originalRanges
+ @editor.addCursorAtBufferPosition([range.start.row, 0])
+ @editor.moveToFirstCharacterOfLine()
+ @vimState.activateNormalMode()
class Indent extends AdjustIndentation
indent: ->
diff --git a/atom/packages/vim-mode/lib/operators/input.coffee b/atom/packages/vim-mode/lib/operators/input.coffee
index 3821045..0fee121 100644
--- a/atom/packages/vim-mode/lib/operators/input.coffee
+++ b/atom/packages/vim-mode/lib/operators/input.coffee
@@ -1,3 +1,4 @@
+Motions = require '../motions/index'
{Operator, Delete} = require './general-operators'
_ = require 'underscore-plus'
settings = require '../settings'
@@ -18,7 +19,7 @@ class Insert extends Operator
execute: ->
if @typingCompleted
return unless @typedText? and @typedText.length > 0
- @editor.insertText(@typedText, normalizeLineEndings: true)
+ @editor.insertText(@typedText, normalizeLineEndings: true, autoIndent: true)
for cursor in @editor.getCursors()
cursor.moveLeft() unless cursor.isAtBeginningOfLine()
else
@@ -28,6 +29,26 @@ class Insert extends Operator
inputOperator: -> true
+class ReplaceMode extends Insert
+
+ execute: ->
+ if @typingCompleted
+ return unless @typedText? and @typedText.length > 0
+ @editor.transact =>
+ @editor.insertText(@typedText, normalizeLineEndings: true)
+ toDelete = @typedText.length - @countChars('\n', @typedText)
+ for selection in @editor.getSelections()
+ count = toDelete
+ selection.delete() while count-- and not selection.cursor.isAtEndOfLine()
+ for cursor in @editor.getCursors()
+ cursor.moveLeft() unless cursor.isAtBeginningOfLine()
+ else
+ @vimState.activateReplaceMode()
+ @typingCompleted = true
+
+ countChars: (char, string) ->
+ string.split(char).length - 1
+
class InsertAfter extends Insert
execute: ->
@editor.moveRight() unless @editor.getLastCursor().isAtEndOfLine()
@@ -45,7 +66,7 @@ class InsertAtBeginningOfLine extends Insert
super
class InsertAboveWithNewline extends Insert
- execute: (count=1) ->
+ execute: ->
@vimState.setInsertionCheckpoint() unless @typingCompleted
@editor.insertNewlineAbove()
@editor.getLastCursor().skipLeadingWhitespace()
@@ -60,7 +81,7 @@ class InsertAboveWithNewline extends Insert
@typingCompleted = true
class InsertBelowWithNewline extends Insert
- execute: (count=1) ->
+ execute: ->
@vimState.setInsertionCheckpoint() unless @typingCompleted
@editor.insertNewlineBelow()
@editor.getLastCursor().skipLeadingWhitespace()
@@ -81,7 +102,7 @@ class Change extends Insert
standalone: false
register: null
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
@register = settings.defaultRegister()
# Public: Changes the text selected by the given motion.
@@ -90,67 +111,29 @@ class Change extends Insert
#
# Returns nothing.
execute: (count) ->
- # If we've typed, we're being repeated. If we're being repeated,
- # undo transactions are already handled.
- @vimState.setInsertionCheckpoint() unless @typingCompleted
-
if _.contains(@motion.select(count, excludeWhitespace: true), true)
+ # If we've typed, we're being repeated. If we're being repeated,
+ # undo transactions are already handled.
+ @vimState.setInsertionCheckpoint() unless @typingCompleted
+
@setTextRegister(@register, @editor.getSelectedText())
- if @motion.isLinewise?()
- @editor.insertNewline()
- @editor.moveLeft()
+ if @motion.isLinewise?() and not @typingCompleted
+ for selection in @editor.getSelections()
+ if selection.getBufferRange().end.row is 0
+ selection.deleteSelectedText()
+ else
+ selection.insertText("\n", autoIndent: true)
+ selection.cursor.moveLeft()
else
for selection in @editor.getSelections()
selection.deleteSelectedText()
- return super if @typingCompleted
-
- @vimState.activateInsertMode()
- @typingCompleted = true
-
-class Substitute extends Insert
- register: null
-
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
- @register = settings.defaultRegister()
+ return super if @typingCompleted
- execute: (count=1) ->
- @vimState.setInsertionCheckpoint() unless @typingCompleted
- _.times count, =>
- @editor.selectRight()
- @setTextRegister(@register, @editor.getSelectedText())
- @editor.delete()
-
- if @typingCompleted
- @typedText = @typedText.trimLeft()
- return super
-
- @vimState.activateInsertMode()
- @typingCompleted = true
-
-class SubstituteLine extends Insert
- register: null
-
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
- @register = settings.defaultRegister()
-
- execute: (count=1) ->
- @vimState.setInsertionCheckpoint() unless @typingCompleted
- @editor.moveToBeginningOfLine()
- _.times count, =>
- @editor.selectToEndOfLine()
- @editor.selectRight()
- @setTextRegister(@register, @editor.getSelectedText())
- @editor.delete()
- @editor.insertNewlineAbove()
- @editor.getLastCursor().skipLeadingWhitespace()
-
- if @typingCompleted
- @typedText = @typedText.trimLeft()
- return super
-
- @vimState.activateInsertMode()
- @typingCompleted = true
+ @vimState.activateInsertMode()
+ @typingCompleted = true
+ else
+ @vimState.activateNormalMode()
# Takes a transaction and turns it into a string of what was typed.
# This class is an implementation detail of Insert
@@ -225,7 +208,6 @@ module.exports = {
InsertAtBeginningOfLine,
InsertAboveWithNewline,
InsertBelowWithNewline,
- Change,
- Substitute,
- SubstituteLine
+ ReplaceMode,
+ Change
}
diff --git a/atom/packages/vim-mode/lib/operators/put-operator.coffee b/atom/packages/vim-mode/lib/operators/put-operator.coffee
index 63151f1..611d6fa 100644
--- a/atom/packages/vim-mode/lib/operators/put-operator.coffee
+++ b/atom/packages/vim-mode/lib/operators/put-operator.coffee
@@ -9,7 +9,7 @@ module.exports =
class Put extends Operator
register: null
- constructor: (@editor, @vimState, {@location, @selectOptions}={}) ->
+ constructor: (@editor, @vimState, {@location}={}) ->
@location ?= 'after'
@complete = true
@register = settings.defaultRegister()
@@ -58,9 +58,9 @@ class Put extends Operator
@editor.setCursorScreenPosition(originalPosition)
@editor.moveToFirstCharacterOfLine()
- @vimState.activateCommandMode()
if type isnt 'linewise'
@editor.moveLeft()
+ @vimState.activateNormalMode()
# Private: Helper to determine if the editor is currently on the last row.
#
diff --git a/atom/packages/vim-mode/lib/operators/replace-operator.coffee b/atom/packages/vim-mode/lib/operators/replace-operator.coffee
index 52157d0..9cf44b3 100644
--- a/atom/packages/vim-mode/lib/operators/replace-operator.coffee
+++ b/atom/packages/vim-mode/lib/operators/replace-operator.coffee
@@ -5,7 +5,7 @@ _ = require 'underscore-plus'
module.exports =
class Replace extends OperatorWithInput
- constructor: (@editor, @vimState, {@selectOptions}={}) ->
+ constructor: (@editor, @vimState) ->
super(@editor, @vimState)
@viewModel = new ViewModel(this, class: 'replace', hidden: true, singleChar: true, defaultText: '\n')
@@ -16,7 +16,7 @@ class Replace extends OperatorWithInput
if @vimState.mode is "visual"
@vimState.resetVisualMode()
else
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()
return
@@ -47,4 +47,4 @@ class Replace extends OperatorWithInput
@editor.moveDown()
@editor.moveToFirstCharacterOfLine()
- @vimState.activateCommandMode()
+ @vimState.activateNormalMode()