import * as vscode from "vscode" ; import * as utils from "./Utils" ; import { VimStyle } from "./VimStyle" ; import { IVSCodeEditorOptions , VSCodeEditor } from "./VSCodeEditor" ; import { VSCodeEditorKeyBindngs } from "./VSCodeEditorKeyBindings" ; function checkImapAction ( bindkey ) { let p = vscode . window . activeTextEditor . selection . active ; let line = vscode . window . activeTextEditor . document . lineAt ( p . line ) . text ; if ( p . character < bindkey . length - 1 ) { return false ; } for ( let i = 0 ; i < bindkey . length - 1 ; i ++ ) { if ( line [ p . character - ( bindkey . length - 1 ) + i ] !== bindkey [ i ] ) { return false ; } } if ( bindkey . length > 1 ) { let deleteRange = new vscode . Range ( new vscode . Position ( p . line , p . character - ( bindkey . length - 1 ) ) , p ) ; vscode . window . activeTextEditor . edit ( ( editBuilder ) => { editBuilder . delete ( deleteRange ) ; } ) ; } let np = new vscode . Position ( p . line , p . character - ( bindkey . length - 1 ) ) ; vscode . window . activeTextEditor . selection = new vscode . Selection ( np , np ) ; return true ; } export function activate ( context ) { if ( vscode . workspace . getConfiguration ( "vimStyle" ) . get < boolean > ( "enabled" , true ) ) { activateVimStyle ( context ) ; } } function activateVimStyle ( context ) { let editorOpt ; let vimOpt ; function loadConfiguration ( ) { let conf = vscode . workspace . getConfiguration ( "vimStyle" ) ; editorOpt = { showMode : conf . get < boolean > ( "showMode" , true ) , changeCursorStyle : conf . get < boolean > ( "changeCursorStyle" , true ) , defaultMode : conf . get < string > ( "defaultMode" , "normal" ) , imapEsc : conf . get < string > ( "imapEsc" , "" ) , } ; vimOpt = { useErgonomicKeyForMotion : conf . get < boolean > ( "useErgonomicKeyForMotion" , false ) , editorKeyBindings : VSCodeEditorKeyBindngs , vimrc : conf . get < string [ ] > ( "vimrc" , null ) , } ; } loadConfiguration ( ) ; let editor = new VSCodeEditor ( editorOpt ) ; context . subscriptions . push ( editor ) ; let vim = new VimStyle ( editor , vimOpt ) ; let disposable = vscode . workspace . onDidChangeConfiguration ( ( ) => { loadConfiguration ( ) ; vim . ApplyOptions ( vimOpt ) ; editor . ApplyOptions ( editorOpt ) ; } ) ; context . subscriptions . push ( disposable ) ; disposable = vscode . window . onDidChangeActiveTextEditor ( ( textEditor ) => { editor . ChangePositionByUser ( ) ; } ) ; context . subscriptions . push ( disposable ) ; disposable = vscode . window . onDidChangeTextEditorSelection ( ( textEditor ) => { editor . ChangePositionByUser ( ) ; } ) ; context . subscriptions . push ( disposable ) ; let imapEscPointer = 0 ; context . subscriptions . push ( vscode . commands . registerCommand ( "type" , async ( args ) => { let text ; if ( args . text && args . text . length > 0 ) { text = args . text ; let charClass = utils . GetCharClass ( text . charCodeAt ( 0 ) ) ; if ( charClass !== CharGroup . AlphabetAndNumber && charClass !== CharGroup . Marks && charClass !== CharGroup . Spaces ) { vim . PushKey ( args . text ) ; return ; } } if ( ! vscode . window . activeTextEditor ) { return ; } if ( vim . GetMode ( ) === VimMode . Insert ) { if ( editorOpt . imapEsc . length === 0 ) { vim . PushKey ( args . text ) ; return ; } if ( editorOpt . imapEsc [ imapEscPointer ] === args . text ) { imapEscPointer ++ ; if ( editorOpt . imapEsc . length === imapEscPointer ) { if ( checkImapAction ( editorOpt . imapEsc ) ) { imapEscPointer = 0 ; vim . PushEscKey ( ) ; return ; } } else { vim . PushKey ( args . text ) ; return ; } } else if ( editorOpt . imapEsc [ 0 ] === args . text ) { imapEscPointer = 1 ; vim . PushKey ( args . text ) ; return ; } imapEscPointer = 0 ; vim . PushKey ( args . text ) ; return ; } vim . PushKey ( args . text ) ; return ; } ) ) ; context . subscriptions . push ( vscode . commands . registerCommand ( "vim.Esc" , ( ) => { vim . PushEscKey ( ) ; } ) ) ; let chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890`~!@#$%^&*()-=_+[]\\{}|,./<>?" ; let otherKeys = [ "<Left>" , "<Right>" , "<Up>" , "<Down>" ] ; let addTypeVim = ( c ) => { context . subscriptions . push ( vscode . commands . registerCommand ( "vim.type-" + c , ( ) => { vim . PushKey ( c ) ; } ) ) ; } ; for ( let char of chars ) { addTypeVim ( char ) ; } for ( let key of otherKeys ) { addTypeVim ( key ) ; } vscode . commands . executeCommand ( "setContext" , "vim.enabled" , true ) ; setTimeout ( ( ) => { if ( editorOpt . defaultMode === "insert" ) { vim . PushKey ( "i" ) ; } else { vim . PushEscKey ( ) ; } } , 1000 ) ; }