aboutsummaryrefslogtreecommitdiff
path: root/atom/packages/vim-mode/lib/operators/replace-operator.coffee
blob: 9cf44b3e7391116bb8ad45a5d95cd5c40d2b2a8e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
_ = require 'underscore-plus'
{OperatorWithInput} = require './general-operators'
{ViewModel} = require '../view-models/view-model'
{Range} = require 'atom'

module.exports =
class Replace extends OperatorWithInput
  constructor: (@editor, @vimState) ->
    super(@editor, @vimState)
    @viewModel = new ViewModel(this, class: 'replace', hidden: true, singleChar: true, defaultText: '\n')

  execute: (count=1) ->
    if @input.characters is ""
      # replace canceled

      if @vimState.mode is "visual"
        @vimState.resetVisualMode()
      else
        @vimState.activateNormalMode()

      return

    @editor.transact =>
      if @motion?
        if _.contains(@motion.select(), true)
          @editor.replaceSelectedText null, (text) =>
            text.replace(/./g, @input.characters)
          for selection in @editor.getSelections()
            point = selection.getBufferRange().start
            selection.setBufferRange(Range.fromPointWithDelta(point, 0, 0))
      else
        for cursor in @editor.getCursors()
          pos = cursor.getBufferPosition()
          currentRowLength = @editor.lineTextForBufferRow(pos.row).length
          continue unless currentRowLength - pos.column >= count

          _.times count, =>
            point = cursor.getBufferPosition()
            @editor.setTextInBufferRange(Range.fromPointWithDelta(point, 0, 1), @input.characters)
            cursor.moveRight()
          cursor.setBufferPosition(pos)

        # Special case: when replaced with a newline move to the start of the
        # next row.
        if @input.characters is "\n"
          _.times count, =>
            @editor.moveDown()
          @editor.moveToFirstCharacterOfLine()

    @vimState.activateNormalMode()