emacs-evil / evil

The extensible vi layer for Emacs.
GNU General Public License v3.0
3.38k stars 281 forks source link

evil-mode macro doesn't match with vim/gvim. #1001

Open chenpoyang opened 6 years ago

chenpoyang commented 6 years ago

Emacs version: GNU Emacs 25.3.1 (x86_64-apple-darwin13.4.0, NS appkit-1265.21 Version 10.9.5 (Build 13F1911)) of 2017-09-13 Operating System: Darwin macbook.local 17.3.0 Darwin Kernel Version 17.3.0: Thu Nov 9 18:09:22 PST 2017; root:xnu-4570.31.3~1/RELEASE_X86_64 x86_64 Evil version: Evil version 1.2.13 Evil installation type: MELPA Graphical

Reproduction steps

i have evil-mode install in my emacs. and i have several code to align:

jasdfkjalsdjf = asdlfjasdf 
asdf = asdfa
asdf = asdfa
hello world         = abc
abc = 4

so i use macro to align in vim/gvim:

normal mode:
qa
0f=20i<Space><Esc>020lvf=hxjq

and then:

normal mode:
20@a

then in vim/gvim, they automatic align:

jasdfkjalsdjf       = asdlfjasdf
asdf                = asdfa
asdf                = asdfa
hello world         = abc
abc                 = 4

when i do the same thing in evil-mode using emacs, they are not align.

Expected behavior

jasdfkjalsdjf       = asdlfjasdf
asdf                = asdfa
asdf                = asdfa
hello world         = abc
abc                 = 4

Actual behavior

jasdfkjalsdjf       = asdlfjasdf 
asdf                     = asdfa
asdf                     = asdfa
hello world                             = abc
abc                     = 4

it alway add more chars before '='

TheBB commented 6 years ago

Is something wrong with your macro?

0f=20i020lvf=hxjq

I suppose you didn't mean to insert 020lvf=hxjq twenty times, which is what I see happening in vim.

chenpoyang commented 6 years ago

@TheBB

020lvf=hxjq
: 20chars width, and delete char until '='. you can test it in vim or gvim. oh, a mistake in html > and < :
0f=20i<Space><Esc>020lvf=hxjq

wasamasa commented 6 years ago

There's this fascinating thing known as Markdown that allows you to wrap code in triple backquotes instead of HTML tags.

As for the bug, I can reproduce this and noticed that the keyboard macro is prematurely aborted and never fully executed. So, if anyone knows how to debug that, any help is welcome.

justbur commented 6 years ago

This works as expected for me 0f=20i<Space><Esc>020lvf=hxjq

chenpoyang commented 6 years ago

debug:

0f=20i<Space><Esc>020lvf=hxjq

the macro editor show:

0           ;; evil-digit-argument-or-evil-beginning-of-line
f           ;; evil-find-char
=           ;; evil-indent **this is not right**
2           ;; digit-argument
0           ;; evil-digit-argument-or-evil-beginning-of-line
i           ;; evil-insert
SPC         ;; evil-forward-char **not right too**
<escape>        ;; evil-force-normal-state
19*SPC          ;; evil-forward-char **not right too**
0           ;; evil-digit-argument-or-evil-beginning-of-line
2           ;; digit-argument
0           ;; evil-digit-argument-or-evil-beginning-of-line
l           ;; evil-forward-char
v           ;; evil-visual-char
f           ;; evil-find-char
=           ;; evil-indent **not right too**
h           ;; evil-backward-char
x           ;; evil-delete-char
j           ;; evil-next-line
0           ;; evil-digit-argument-or-evil-beginning-of-line

when i change '=' to ';', the macro editor show:

0           ;; evil-digit-argument-or-evil-beginning-of-line
f           ;; evil-find-char
;           ;; evil-repeat-find-char **not right too**
2           ;; digit-argument
0           ;; evil-digit-argument-or-evil-beginning-of-line
i           ;; evil-insert
SPC         ;; evil-forward-char **not right too**
<escape>        ;; evil-force-normal-state
19*SPC          ;; evil-forward-char **not right too**
0           ;; evil-digit-argument-or-evil-beginning-of-line
2           ;; digit-argument
0           ;; evil-digit-argument-or-evil-beginning-of-line
l           ;; evil-forward-char
v           ;; evil-visual-char
f           ;; evil-find-char
;           ;; evil-repeat-find-char **not right too**
h           ;; evil-backward-char
x           ;; evil-delete-char
j           ;; evil-next-line
0           ;; evil-digit-argument-or-evil-beginning-of-line

in the end , i change space to zero and '=' to number 8, it ident normally, the macro editor show:

0           ;; evil-digit-argument-or-evil-beginning-of-line
f           ;; evil-find-char
8           ;; digit-argument
2           ;; digit-argument
0           ;; evil-digit-argument-or-evil-beginning-of-line
i           ;; evil-insert
0           ;; evil-digit-argument-or-evil-beginning-of-line
<escape>        ;; evil-force-normal-state
20*0            ;; evil-digit-argument-or-evil-beginning-of-line
2           ;; digit-argument
0           ;; evil-digit-argument-or-evil-beginning-of-line
l           ;; evil-forward-char
v           ;; evil-visual-char
f           ;; evil-find-char
8           ;; digit-argument
h           ;; evil-backward-char
x           ;; evil-delete-char
j           ;; evil-next-line
0           ;; evil-digit-argument-or-evil-beginning-of-line

the text indent like these:

jasdfkjalsdjf000000080asdlfjasdf
asdf000000000000000080asdfa
asdf000000000000000080asdfa
hello0world00000000080abc
abc00000000000000000804
justbur commented 6 years ago

The original macro still works fine for me. That macro editor lists the wrong commands for me too, but that is likely because it is looking up all of the commands in normal state (it isn't aware of evil-mode in other words).

Try executing this function after recording the original macro. Also, you should be doing all of this with an uncustomized emacs setup using emacs -Q

(defun print-macro ()
  (interactive)
  (message "%s"
           (mapconcat
            (lambda (c)
              (if (symbolp c)
                  (format "<%s>" (symbol-name c))
                (char-to-string c)))
            (evil-get-register evil-last-register t)
            "")))

This function prints the correct macro for me in the messages buffer.