1
0
mirror of https://github.com/chylex/IntelliJ-IdeaVim.git synced 2025-05-14 15:34:06 +02:00

[New Typing Handler]: Support d

This commit is contained in:
Alex Plate 2022-09-06 13:13:31 +03:00
parent 43a79dbad4
commit c32c62eacc
No known key found for this signature in database
GPG Key ID: 0B97153C8FFEC09F
10 changed files with 64 additions and 26 deletions

View File

@ -25,10 +25,12 @@ import com.intellij.openapi.fileTypes.FileType
import com.intellij.openapi.project.Project
import com.intellij.psi.PsiFile
import com.maddyhome.idea.vim.api.VimEditor
import com.maddyhome.idea.vim.command.VimStateMachine
import com.maddyhome.idea.vim.helper.EditorDataContext
import com.maddyhome.idea.vim.helper.inInsertMode
import com.maddyhome.idea.vim.helper.inNormalMode
import com.maddyhome.idea.vim.helper.isIdeaVimDisabledHere
import com.maddyhome.idea.vim.helper.mode
import com.maddyhome.idea.vim.newapi.vim
import javax.swing.KeyStroke
@ -92,8 +94,8 @@ class VimTypedDelegateHandler : TypedHandlerDelegate() {
}
}
internal val charsByDelegate = setOf('j')
internal val charsByDelegate = setOf('j', 'd')
internal fun useNewHandler(editor: VimEditor, c: Char): Boolean {
return c in charsByDelegate && editor.inNormalMode
return c in charsByDelegate && (editor.inNormalMode || editor.mode == VimStateMachine.Mode.OP_PENDING)
}

View File

@ -27,10 +27,7 @@ import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.command.CommandProcessor;
import com.intellij.openapi.command.UndoConfirmationPolicy;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.editor.Caret;
import com.intellij.openapi.editor.Document;
import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.editor.LogicalPosition;
import com.intellij.openapi.editor.*;
import com.intellij.openapi.editor.event.EditorMouseEvent;
import com.intellij.openapi.editor.event.EditorMouseListener;
import com.intellij.openapi.editor.impl.TextRangeInterval;
@ -176,6 +173,15 @@ public class ChangeGroup extends VimChangeGroupBase {
MotionGroup.scrollCaretIntoView(editor);
}
@Override
public void typeDirectly(@NotNull VimEditor vimEditor, @NotNull ExecutionContext context, char key) {
Editor editor = ((IjVimEditor)vimEditor).getEditor();
final Document doc = ((IjVimEditor)vimEditor).getEditor().getDocument();
CommandProcessor.getInstance().executeCommand(editor.getProject(), () -> ApplicationManager.getApplication()
.runWriteAction(() -> EditorModificationUtilEx.insertStringAtCaret(editor, Character.toString(key))), "", doc,
UndoConfirmationPolicy.DEFAULT, doc);
MotionGroup.scrollCaretIntoView(editor);
}
@Override

View File

@ -73,7 +73,7 @@ public class MacroGroup extends VimMacroBase {
final Runnable run = () -> {
// Handle one keystroke then queue up the next key
if (keyStack.hasStroke()) {
KeyHandler.getInstance().handleKey(editor, keyStack.feedStroke(), context, true, false, true);
KeyHandler.getInstance().handleKey(editor, keyStack.feedStroke(), context, true, false, true, false);
}
if (keyStack.hasStroke()) {
playbackKeys(editor, context, cnt, total);
@ -105,7 +105,7 @@ public class MacroGroup extends VimMacroBase {
return;
}
ProgressManager.getInstance().executeNonCancelableSection(() -> {
KeyHandler.getInstance().handleKey(editor, key, context, true, false, true);
KeyHandler.getInstance().handleKey(editor, key, context, true, false, true, false);
});
}
keyStack.resetFirst();

View File

@ -32,6 +32,12 @@ class IjExecutionContext(override val context: DataContext) : ExecutionContext {
override fun isNewDelegate(): Boolean {
return context.getData(NEW_DELEGATE) ?: false
}
override fun withOldDelegate(editor: VimEditor): ExecutionContext {
val context1 = EditorDataContext((editor as IjVimEditor).editor, context)
context1.newTypingDelegate = false
return IjExecutionContext(context1)
}
}
val DataContext.vim

View File

@ -111,6 +111,7 @@ class KeyHandler {
allowKeyMappings: Boolean,
mappingCompleted: Boolean,
execute: Boolean = true,
directTyping: Boolean = false
): StateUpdateResult {
LOG.trace {
"""
@ -186,7 +187,7 @@ class KeyHandler {
// If we are in insert/replace mode send this key in for processing
if (editorState.mode == VimStateMachine.Mode.INSERT || editorState.mode == VimStateMachine.Mode.REPLACE) {
LOG.trace("Process insert or replace")
shouldRecord = injector.changeGroup.processKey(editor, context, key) && shouldRecord
shouldRecord = injector.changeGroup.processKey(editor, context, key, directTyping) && shouldRecord
} else if (editorState.mode == VimStateMachine.Mode.SELECT) {
LOG.trace("Process select")
shouldRecord = injector.changeGroup.processKeyInSelectMode(editor, context, key) && shouldRecord

View File

@ -28,6 +28,7 @@ interface ExecutionContext {
// TODO: 10.02.2022 Not sure about this method
fun updateEditor(editor: VimEditor): ExecutionContext
fun isNewDelegate(): Boolean
fun withOldDelegate(editor: VimEditor): ExecutionContext
}
interface ExecutionContextManager {

View File

@ -79,7 +79,7 @@ interface VimChangeGroup {
operatorArguments: OperatorArguments
): Boolean
fun processKey(editor: VimEditor, context: ExecutionContext, key: KeyStroke): Boolean
fun processKey(editor: VimEditor, context: ExecutionContext, key: KeyStroke, directTyping: Boolean): Boolean
fun processKeyInSelectMode(editor: VimEditor, context: ExecutionContext, key: KeyStroke): Boolean
@ -199,5 +199,6 @@ interface VimChangeGroup {
)
fun type(vimEditor: VimEditor, context: ExecutionContext, key: Char)
fun typeDirectly(vimEditor: VimEditor, context: ExecutionContext, key: Char)
fun replaceText(editor: VimEditor, start: Int, end: Int, str: String)
}

View File

@ -699,16 +699,25 @@ abstract class VimChangeGroupBase : VimChangeGroup {
editor: VimEditor,
context: ExecutionContext,
key: KeyStroke,
directTyping: Boolean,
): Boolean {
logger.debug { "processKey($key)" }
if (key.keyChar != KeyEvent.CHAR_UNDEFINED) {
type(editor, context, key.keyChar)
if (directTyping) {
typeDirectly(editor, context, key.keyChar)
} else {
type(editor, context, key.keyChar)
}
return true
}
// Shift-space
if (key.keyCode == 32 && key.modifiers and KeyEvent.SHIFT_DOWN_MASK != 0) {
type(editor, context, ' ')
if (directTyping) {
typeDirectly(editor, context, ' ')
} else {
type(editor, context, ' ')
}
return true
}
return false
@ -721,7 +730,7 @@ abstract class VimChangeGroupBase : VimChangeGroup {
): Boolean {
var res: Boolean
SelectionVimListenerSuppressor.lock().use {
res = processKey(editor, context, key)
res = processKey(editor, context, key, false)
editor.exitSelectModeNative(false)
KeyHandler.getInstance().reset(editor)
if (isPrintableChar(key.keyChar) || activeTemplateWithLeftRightMotion(editor, key)) {

View File

@ -87,18 +87,28 @@ sealed class ChangeEditorActionHandler : EditorActionHandlerBase(false) {
try {
when (this) {
is ForEachCaret -> {
editor.forEachNativeCaret(
{ current ->
if (!current.isValid) return@forEachNativeCaret
if (!execute(editor, current, context, cmd.argument, operatorArguments)) {
worked[0] = false
}
},
true
)
if (!context.isNewDelegate()) {
editor.forEachNativeCaret(
{ current ->
if (!current.isValid) return@forEachNativeCaret
if (!execute(editor, current, context, cmd.argument, operatorArguments)) {
worked[0] = false
}
},
true
)
} else {
worked[0] = execute(editor, caret, context, cmd.argument, operatorArguments)
}
}
is SingleExecution -> {
worked[0] = execute(editor, context, cmd.argument, operatorArguments)
if (!context.isNewDelegate()) {
worked[0] = execute(editor, context, cmd.argument, operatorArguments)
} else {
if (caret == editor.primaryCaret()) {
worked[0] = execute(editor, context, cmd.argument, operatorArguments)
}
}
}
}
} catch (e: java.lang.Exception) {
@ -114,7 +124,9 @@ sealed class ChangeEditorActionHandler : EditorActionHandlerBase(false) {
if (worked[0]) {
VimRepeater.saveLastChange(cmd)
VimRepeater.repeatHandler = false
editor.forEachNativeCaret({ it.vimLastColumn = it.getVisualPosition().column })
editor.carets().forEach {
it.vimLastColumn = it.getVisualPosition().column
}
}
val toSwitch = editor.vimChangeActionSwitchMode

View File

@ -96,7 +96,7 @@ class ToKeysMappingInfo(
override fun execute(editor: VimEditor, context: ExecutionContext) {
LOG.debug("Executing 'ToKeys' mapping info...")
val editorDataContext = injector.executionContextManager.onEditor(editor, context)
val editorDataContext = injector.executionContextManager.onEditor(editor, context).withOldDelegate(editor)
val fromIsPrefix = KeyHandler.isPrefix(fromKeys, toKeys)
val keyHandler = KeyHandler.getInstance()
keyHandler.keyStack.addKeys(toKeys)
@ -104,7 +104,7 @@ class ToKeysMappingInfo(
while (keyHandler.keyStack.hasStroke()) {
val keyStroke = keyHandler.keyStack.feedStroke()
val recursive = isRecursive && !(first && fromIsPrefix)
keyHandler.handleKey(editor, keyStroke, editorDataContext, recursive, false)
keyHandler.handleKey(editor, keyStroke, editorDataContext, recursive, false, directTyping = true)
first = false
}
keyHandler.keyStack.removeFirst()