microsoft / vscode

Visual Studio Code
https://code.visualstudio.com
MIT License
162.95k stars 28.77k forks source link

Autoindent inserts extra undo item, requires double undo after paste #30406

Open atombender opened 7 years ago

atombender commented 7 years ago

Here's an example of pasting something, then hitting cmd-Z to undo. As you can see, it first undoes one indentation, then undoes the paste. That's not right, since my paste was a single command, so a single undo should undo it.

vsc

Steps to Reproduce:

  1. Copy something.
  2. Go into a block that has a deeper indentation level.
  3. Hit cmd-V.
  4. Hit cmd-Z.
  5. The paste remains, but one indent level is subtracted.

Reproduces without extensions: Yes

rebornix commented 3 years ago

I put this under "under-discussion" as it ocurred to me that when the auto indent went wrong, a undo/redo point in between can help users go back to the normal paste. Not sure what's the right behavior here.

LeaVerou commented 2 years ago

I put this under "under-discussion" as it ocurred to me that when the auto indent went wrong, a undo/redo point in between can help users go back to the normal paste. Not sure what's the right behavior here.

It all depends on what the common case is. If 99% of the time you want to undo the paste and 1% of the time you want to fix the indentation, the cost of fixing the indentation manually is trivial compared to the cost of double undo (and the jarring UX this causes, when undoing doesn't undo your actual last action, which is perceived to be the paste). I don't know if it's actually 99 to 1, but I would be very surprised if it's less than 90 to 10, which still doesn't justify the double undo.

poke commented 2 years ago

For what it's worth, to add a voice against this suggestion:

When I undo after pasting, it is almost always to undo the auto formatting that happened after pasting. It's very rare that I want to undo the pasting altogether, but it is very common that I might paste something where I want to keep the original formatting as is, without the editor changing it after the fact.

So the combination of paste & undo is very common for me to paste something while keeping the original formatting.

This behavior is also in sync with some other programs, e.g. in MS Office when pasting a URL. The URL will be automatically formatted as a clickable link and undoing once will only remove that formatting.

LeaVerou commented 2 years ago

@poke formatting != matching indentation. It's the latter we are talking about, and I'd still wager that people rarely want to undo indentation matching, because that's usually desirable. The automatic formatting on paste is indeed often undesirable, which is why there's a setting to disable it.

LeaVerou commented 2 years ago

While consistency is not a goal in itself, when unsure between two options of similar (perceived) usability, consistency is a good point to consider that might tip the scales.

What do other editors do?

Any other editors to try?

myfonj commented 2 years ago

What do other editors do?

But do those editors the indent step though? I've just tried current stable Sublime 4113 and Atom 1.58.0 with default settings on Windows and they either did not the auto indent step at all (Sublime) or consistently (Atom *), so naturally there was no extra step after paste to undo.

Steps taken:

var check = "Cut this declaration";// not this comment
function x () {
    var pivot = "Something indented.";
/* Select this comment and paste. */
};

VSC outcome:

// not this comment
function x () {
    var pivot = "Something indented.";
    var check = "Cut this declaration";
};
  1. undo: un-indented pasted declaration;
  2. undo: (selected) comment back;
  3. undo: (selected) declaration back;

Atom and Sublime outcomes:

// not this comment
function x () {
    var pivot = "Something indented.";
var check = "Cut this declaration";
};
  1. undo: (selected) declaration back;

(*) Atom auto-indented pasted line only when it contained line break, i.e. when cut line from the test case included the // not this comment[\n] slug.

LeaVerou commented 2 years ago

I used a fairly large chunk of HTML, cut a highly indented multi-line block of markup and pasted it in an area of the markup with only 1 level indentation and then the opposite. I don't remember if I had default settings, but I confirmed that in both cases, the snippet I pasted actually got its indentation changed to match. That's why I didn't mention CodeMirror among my examples, because that seemed to not do any indentation matching.

And yes, if the thing you're pasting doesn't contain line breaks, no indentation matching is needed and it should just be pasted where your cursor is, not sure what you expected to happen with a single line paste?

myfonj commented 2 years ago

the cost of fixing the indentation manually is trivial compared to the cost of double undo.

The cost of double undo is single extra key stroke on key user happens to have finger already, i.e. the smallest possible "distance of keystrokes" if there is such a thing. Besides no keystroke at all I cannot imagine anything "cheaper".

The cost of fixing the indentation manually means: 1: selecting the pasted block (what could be pretty daunting cursor etude if pasted block does not constitute easily selectable syntactic unit); 2: adjusting the indent = different key stroke(s). I see this as quite "expensive", especially for the use-case when user needs to get the "original" indentation they have in the clipboard.

myfonj commented 2 years ago

not sure what you expected to happen with a single line paste

well, consistency. While with current understanding of Atom's behaviour that makes difference between clipboard containing line breaks and clipboard not containing line breaks it makes quite sense (and I admit I've encountered similar behaviour in other text editors before), I don't see it as very consistent and more importantly observable from users' perspective. I'd really expect pasted text\n and text to behave the same way and I see it more consistent to be treated equally.

LeaVerou commented 2 years ago

the cost of fixing the indentation manually is trivial compared to the cost of double undo.

The cost of double undo is single extra key stroke on key user happens to have finger already, i.e. the smallest possible "distance of keystrokes" if there is such a thing. Besides no keystroke at all I cannot imagine anything "cheaper".

The cost of fixing the indentation manually means: 1: selecting the pasted block (what could be pretty daunting cursor etude if pasted block does not constitute easily selectable syntactic unit); 2: adjusting the indent = different key stroke(s). I see this as quite "expensive", especially for the use-case when user needs to get the "original" indentation they have in the clipboard.

It is clearly more expensive to fix indentation manually. That does not always mean we should go with the other option. The frequency each outcome is needed matters too. If on 100 paste+undo actions, the user intended to undo the paste in 99 of them, and fix the indentation in 1, then the additional cost of fixing the indentation manually in the one case is outweighed by the 99 keystrokes saved. If the ratio is 50-50, obviously that points towards a different decision.

Consistency is also a factor. The current Code behavior is very externally inconsistent, since (to my knowledge) no other code editor behaves that way. This is very jarring for users coming to Code from other editors. External consistency is not a goal in itself, and there are sometimes valid reasons to break it. However, when it's unclear which of two options is better usability-wise, it's useful to take consistency into account as a factor.

not sure what you expected to happen with a single line paste

well, consistency. While with current understanding of Atom's behaviour that makes difference between clipboard containing line breaks and clipboard not containing line breaks it makes quite sense (and I admit I've encountered similar behaviour in other text editors before), I don't see it as very consistent and more importantly observable from users' perspective. I'd really expect pasted text\n and text to behave the same way and I see it more consistent to be treated equally.

If you paste multiple lines, the first line doesn't change indentation anyway, so it is consistent. I'm not sure what inconsistency you're seeing, as you say all editors follow similar algorithms for matching indentation, so if anything, the behavior you seem to be expecting (it is still unclear to me what that is) would be externally inconsistent.

jespertheend commented 2 years ago

I was looking for an existing feature request for pasting code without auto indentation. Came here and realised ctrl Z would do what I wanted. Please don't remove this without adding a way to paste code without formatting.