Skip to content

Commit

Permalink
doc: Add warning and notes for two-letter hotkey usage in README
Browse files Browse the repository at this point in the history
refactor: Extract two-letter normal mode logic to a new Vimkey class
  • Loading branch information
rcmdnk committed Sep 29, 2024
1 parent 2689573 commit b6c5adf
Show file tree
Hide file tree
Showing 3 changed files with 80 additions and 63 deletions.
24 changes: 15 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -88,13 +88,14 @@ Example line:

Multiple applications can be written by a comma-separated.

Note: This will overwrite the default applications. If you want to **add**
these applications to the default applications, add following applications
after your applications:

ahk_exe notepad.exe,ahk_exe explorer.exe,ahk_exe wordpad.exe,ahk_exe TeraPad.exe,作成,Write:,ahk_exe POWERPNT.exe,ahk_exe WINWORD.exe,ahk_exe Evernote.exe,ahk_exe Code.exe,ahk_exe onenote.exe,OneNote,ahk_exe texworks.exe,ahk_exe texstudio.exe

Or you can use GUI option setting menu described below.
> [!NOTE]
> This will overwrite the default applications. If you want to **add**
> these applications to the default applications, add following applications
> after your applications:
>
> ahk_exe notepad.exe,ahk_exe explorer.exe,ahk_exe wordpad.exe,ahk_exe TeraPad.exe,作成,Write:,ahk_exe POWERPNT.exe,ahk_exe WINWORD.exe,ahk_exe Evernote.exe,ahk_exe Code.exe,ahk_exe onenote.exe,OneNote,ahk_exe texworks.exe,ahk_exe texstudio.exe
>
> Or you can use GUI option setting menu described below.
The default setting of `VimSetTitleMatchMode` is 2,
which makes matching methods as `Contain`.
Expand All @@ -103,7 +104,7 @@ If you set `OneNote`, all windows with a title containing `OneNote`
(e.g. `XXX's OneNote`) will be included.
If you set `VimSetTitleMatchMode` as 3, only the exact title of `OneNote` will be included.

Note: It may not work on OneNote. OneNote may have a window name like
It may not work on OneNote. OneNote may have a window name like
**User's Notebook - OneNote**, instead of **OneNote**.

In that case, you need to check OneNote's window title with Window spy.
Expand Down Expand Up @@ -254,6 +255,10 @@ and a long press will change the mode to the normal mode.

If using a custom two-letter hotkey to enter the normal mode, the two letters must be different.

> [!WARNING]
> A character can be used only for one two-letter hotkey. If you specify `ab` and `bc`, `ba` (push `b` first and then `a`) does not work. If you push `a` first, then `ab` will work, though.

## Available commands in the normal mode

### Mode Change
Expand Down Expand Up @@ -281,7 +286,8 @@ If using a custom two-letter hotkey to enter the normal mode, the two letters mu
|Space| Right.|
|Enter| Move to the beginning of the next line.|

Note: Enter works only for editor applications (for other than Explorer, Q-dir, it works as Enter even in the normal mode).
> [!NOTE]
> Enter works only for editor applications (for other than Explorer, Q-dir, it works as Enter even in the normal mode).
In addition, `Repeat` is also available for some commands.

Expand Down
57 changes: 3 additions & 54 deletions lib/vim_ahk.ahk
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
#Include %A_LineFile%\..\vim_icon.ahk
#Include %A_LineFile%\..\vim_caret.ahk
#Include %A_LineFile%\..\vim_ini.ahk
#Include %A_LineFile%\..\vim_key.ahk
#Include %A_LineFile%\..\vim_menu.ahk
#Include %A_LineFile%\..\vim_move.ahk
#Include %A_LineFile%\..\vim_setting.ahk
Expand Down Expand Up @@ -38,6 +39,7 @@ class VimAhk{
this.Icon := VimIcon(this)
this.Caret := VimCaret(this)
this.Ini := VimIni(this)
this.key := Vimkey(this)
this.VimMenu := VimMenu(this)
this.Move := VimMove(this)
this.Setting := VimSetting(this)
Expand All @@ -51,11 +53,6 @@ class VimAhk{

DefaultGroup := this.SetDefaultActiveWindows()

; Two-letter normal mode
this.TwoLetterNormalIsSet := False
this.TwoLetterNormalArray := Array()
this.TwoLetterNormalMapsEnabledObj := ObjBindMethod(this, "TwoLetterNormalMapsEnabled")

; On following applications, Enter works as Enter at the normal mode.
GroupAdd("VimNonEditor", "ahk_exe explorer.exe") ; Explorer
GroupAdd("VimNonEditor", "ahk_exe Explorer.exe") ; Explorer, Explorer became also upper case, but lower case works for this
Expand Down Expand Up @@ -196,60 +193,12 @@ class VimAhk{
}
}

LoadTwoLetterMaps() {
HotIf(this.TwoLetterNormalMapsEnabledObj)
this.TwoLetterNormalIsSet := False
for value in this.TwoLetterNormalArray {
HotKey(value, "Off")
}
this.TwoLetterNormalArray := Array()

Loop Parse, this.Conf["VimTwoLetter"]["val"], this.GroupDel {
if(A_LoopField != ""){
if(StrLen(A_LoopField) != 2){
MsgBox("Two-letter should be exactly two letters: " A_LoopField)
Continue
}
this.TwoLetterNormalIsSet := True
key1 := SubStr(A_LoopField, 1, 1)
key2 := SubStr(A_LoopField, 2, 1)
this.SetTwoLetterMap(key1, key2)
}
}
HotIf()
}

SetTwoLetterMap(Key1, Key2){
SendSame := ObjBindMethod(this, "SendSame")
EnterNormal := ObjBindMethod(this, "TwoLetterEnterNormal")
EnterNormal1 := EnterNormal.Bind(Key2)
EnterNormal2 := EnterNormal.Bind(Key1)
HotKey("~" Key1, EnterNormal1)
HotKey("~" Key2, EnterNormal2)
this.TwoLetterNormalArray.Push(key1)
this.TwoLetterNormalArray.Push(key2)
}

TwoLetterNormalMapsEnabled(HotkeyName){
Return this.IsVimGroup() && (this.State.StrIsInCurrentVimMode("Insert")) && this.TwoLetterNormalIsSet
}

TwoLetterEnterNormal(EndKey, HotkeyName){
Out := InputHook("I T0.1 V L1", EndKey)
Out.Start()
EndReason := Out.Wait()
if(EndReason == "EndKey"){
SendInput("{BackSpace 2}")
Vim.State.SetNormal()
}
}

Setup(){
SetTitleMatchMode(this.Conf["VimSetTitleMatchMode"]["val"])
SetTitleMatchMode(this.Conf["VimSetTitleMatchModeFS"]["val"])
this.State.SetStatusCheck()
this.SetGroup()
this.LoadTwoLetterMaps()
this.Key.Set()
}

Initialize(){
Expand Down
62 changes: 62 additions & 0 deletions lib/vim_key.ahk
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
class Vimkey{
__New(Vim){
this.Vim := Vim

; Two-letter normal mode
this.TwoLetterNormalIsSet := False
this.TwoLetterNormalArray := Array()
this.TwoLetterNormalEnabledObj := ObjBindMethod(this, "TwoLetterNormalEnabled")
}

TwoLetterNormalEnabled(HotkeyName){
Return this.Vim.IsVimGroup() && (this.Vim.State.StrIsInCurrentVimMode("Insert")) && this.TwoLetterNormalIsSet
}

TwoLetterEnterNormal(EndKey, HotkeyName){
Out := InputHook("I T0.1 V L1", EndKey)
Out.Start()
EndReason := Out.Wait()
if(EndReason == "EndKey"){
SendInput("{BackSpace 2}")
Vim.State.SetNormal()
}
}

SetTwoLetterMap(Key1, Key2){
SendSame := ObjBindMethod(this, "SendSame")
EnterNormal := ObjBindMethod(this, "TwoLetterEnterNormal")
EnterNormal1 := EnterNormal.Bind(Key2)
EnterNormal2 := EnterNormal.Bind(Key1)
HotKey("~" Key1, EnterNormal1)
HotKey("~" Key2, EnterNormal2)
this.TwoLetterNormalArray.Push(key1)
this.TwoLetterNormalArray.Push(key2)
}

SetTwoLetterMaps() {
HotIf(this.TwoLetterNormalEnabledObj)
this.TwoLetterNormalIsSet := False
for value in this.TwoLetterNormalArray {
HotKey(value, "Off")
}
this.TwoLetterNormalArray := Array()

Loop Parse, this.Vim.Conf["VimTwoLetter"]["val"], this.Vim.GroupDel {
if(A_LoopField != ""){
if(StrLen(A_LoopField) != 2){
MsgBox("Two-letter should be exactly two letters: " A_LoopField)
Continue
}
this.TwoLetterNormalIsSet := True
key1 := SubStr(A_LoopField, 1, 1)
key2 := SubStr(A_LoopField, 2, 1)
this.SetTwoLetterMap(key1, key2)
}
}
HotIf()
}

Set(){
this.SetTwoLetterMaps()
}
}

0 comments on commit b6c5adf

Please sign in to comment.