Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #Requires AutoHotkey v2.0
- ; example: type `` then type "wdyw" to trigger "what do you want"
- :B0X?*:````::AutoSuggestion("
- (
- as a reminder
- as a result
- at any rate
- what do you expect
- what do you have
- what do you like
- what do you mean
- what do you think
- what do you want
- any time
- all things considered
- all-time high
- all-time low
- at the moment
- according to my memory
- at this rate
- all the same
- all that time
- attention
- )")
- AutoSuggestion(textList) {
- static txtList := Sort(textList), ih, g, LB, _ := Init(), TriggerLength := StrLen(RegExReplace(A_ThisHotkey, "^:.*?:"))
- Init() {
- ih := InputHook("V M I101")
- ih.OnChar := OnChar
- ih.OnKeyDown := OnKeyDown
- ih.KeyOpt("{LAlt}{RAlt}{LWin}{RWin}{AppsKey}{F1}{F2}{F3}{F4}{F5}{F6}{F7}{F8}{F9}{F10}{F11}{F12}{Left}{Right}{Home}{End}{PgUp}{PgDn}{Del}{Ins}{BS}{CapsLock}{ScrollLock}{NumLock}{PrintScreen}{Esc}", "N")
- g := Gui("+AlwaysOnTop -Caption +ToolWindow -DPIScale +E0x02000000") ; WS_EX_COMPOSITED
- g.SetFont("s12", "Segoe UI")
- g.MarginX := g.MarginY := 1
- LB := g.Add("ListBox", "xm ym r10 -E0x200")
- g.Show("AutoSize Hide")
- ; start the inputhook if ` is pressed
- ; restarts inputhook if ih is in progress
- HotIfWinExist "ahk_id" g.hwnd
- ; Up selects previous item or last item.
- Hotkey "Up", (*) => LB.Value = 1 ? ControlSend("{End}", LB) : --LB.Value
- ; Down selcts next item or first item.
- Hotkey "Down", (*) => LB.Value = ControlGetItems(LB).Length ? ControlSend("{Home}", LB) : ++LB.Value
- Hotkey "Esc", (*) => WinExist("ahk_id" g.hwnd) && (g.Hide(), ih.Stop() )
- Hotkey "Tab", Submit
- Hotkey "Enter", Submit
- ; Click any mouse button to close the menu
- Hotkey "~LButton", MouseAction
- Hotkey "~RButton", MouseAction
- Hotkey "~MButton", MouseAction
- Hotkey "~XButton1", MouseAction
- Hotkey "~XButton2", MouseAction
- ; bind number keys to send item at the position number
- loop 9
- Hotkey A_Index, Choose.Bind(A_Index)
- Hotkey 0, Choose.Bind(10)
- HotIf
- return 1
- }
- ih.Stop()
- g.Hide()
- ih.Start()
- Return
- MouseAction(ThisHotkey) {
- MouseGetPos(,, &Win)
- if Win = g.hwnd {
- if SubStr(ThisHotkey, 2) = "LButton" {
- KeyWait "LButton"
- Submit()
- }
- } else {
- g.Hide(), ih.Stop()
- }
- }
- Choose(p, *) {
- if ControlGetItems(LB).Length >= p {
- LB.Value := p
- Submit()
- }
- }
- Submit(*) {
- g.Hide()
- SetKeyDelay -1, 1
- RegExMatch(LB.Text, "(^\d\. )|(^ {4})|(^z)", &M) ; remove the number or space in front
- if M.Pos[1]
- Text := SubStr(LB.Text, M.Len[1] + 1)
- else if M[2]
- Text := SubStr(LB.Text, 5)
- SendEvent "{BS " StrLen(ih.Input) + TriggerLength "}" ; remove ` and input
- ; Send using the clipboard
- oc := ClipboardAll()
- Sleep 80
- A_Clipboard := Text
- Sleep 10
- SendEvent "^v"
- Sleep 10
- A_Clipboard := oc
- ih.Stop()
- }
- OnChar(ih, char) {
- if (char = "")
- || (Ord(char) >= 1 && Ord(char) <= 26) { ; Ctrl+Key
- g.Hide(), ih.Stop()
- return
- }
- if ih.Input {
- LB.Delete()
- Count := 0
- textWidth := 0
- loop parse txtList, "`n", "`r`t " {
- ; Match if input contains letters from A_Loopfield without matching exactly
- matchRegex := RegExReplace(SubStr(ih.Input, 1, 1), "(.)", "(?i:$1).*")
- if StrLen(ih.Input) > 1
- matchRegex .= RegExReplace(SubStr(ih.Input, 2), "(.)", "$1.*")
- If RegExMatch(A_LoopField, "^" matchRegex) {
- Capitalized := ""
- if IsUpper(SubStr(ih.Input, 1, 1)) ; If first letter of input is upper case
- Capitalized := RegExReplace(A_LoopField, "^(.)", "$U1") ; replace first letter of Text with upper case
- ; Number items from 1 - 9. Make last item 0.
- if ++Count <= 10
- Num := (Count < 10 ? Count : "0") ". "
- else
- Num := " "
- ItemName := Num (Capitalized || A_LoopField)
- size := GetTextSize(LB, ItemName)
- textWidth := Max(textWidth, size.W)
- LB.Add([ItemName])
- }
- }
- if Count = 0 {
- ; stop inputhook if you type `, the gui is not open, and there is not match.
- if !WinExist("ahk_id" g.hwnd)
- ih.Stop()
- return
- }
- if Count = 1 {
- LB.Choose(1)
- Submit()
- return
- }
- textWidth += 10
- if Count > 10
- textWidth += 25
- LB.Move(,, textWidth)
- } else {
- g.Hide() ; Hide menu if input is empty
- ih.Stop()
- return
- }
- LB.Choose(1)
- GetCaretPos(&X, &Y,, &H)
- hMon := DllCall("MonitorFromWindow", "ptr", g.hwnd, "uint", 2, "ptr")
- NumPut("uint", 40, MI := Buffer(40))
- DllCall("user32\GetMonitorInfo", "ptr", hMon, "ptr", MI)
- WR := NumGet(MI, 28, "int")
- WB := NumGet(MI, 32, "int")
- ; make sure menu stays within monitor
- g.GetPos(&gX, &gY, &gW, &gH)
- if X + gW > WR
- X -= gW
- if Y + gH > WB
- Y -= gH
- else
- Y += H
- g.Show("NA x" X " y" Y " AutoSize")
- }
- OnKeyDown(ih, VK, SC) {
- if vk = 8 { ; Backspace
- if GetKeyState("Ctrl")
- OnChar(ih, "")
- else
- OnChar(ih, "{BS}")
- } else
- OnChar(ih, "")
- }
- GetTextSize(ctrl, text) {
- static WM_GETFONT := 0x31, DT_CALCRECT := 0x400
- hFont := SendMessage(WM_GETFONT,,, ctrl)
- hDC := DllCall('GetDC', 'Ptr', 0, 'Ptr')
- hObj := DllCall('SelectObject', 'Ptr', hDC, 'Ptr', hFont, 'Ptr')
- RECT := Buffer(16)
- height := DllCall('DrawText', 'Ptr', hDC, 'Str', text, 'Int', StrLen(text), 'Ptr', RECT, 'UInt', DT_CALCRECT)
- DllCall('SelectObject', 'Ptr', hDC, 'Ptr', hObj, 'Ptr')
- DllCall('ReleaseDC', 'Ptr', 0, 'Ptr', hDC)
- return {w: NumGet(RECT, 8, 'UInt') - NumGet(RECT, 'UInt'), h: height}
- }
- }
- /**
- * Gets the position of the caret with UIA, Acc or CaretGetPos.
- * Descolada's implementation: https://www.autohotkey.com/boards/viewtopic.php?p=576439#p576439
- * @param X Value is set to the screen X-coordinate of the caret
- * @param Y Value is set to the screen Y-coordinate of the caret
- * @param W Value is set to the width of the caret
- * @param H Value is set to the height of the caret
- */
- GetCaretPos(&X?, &Y?, &W?, &H?) {
- ; Default caret
- savedCaret := A_CoordModeCaret
- CoordMode "Caret", "Screen"
- CaretGetPos(&X, &Y)
- CoordMode "Caret", savedCaret
- if IsInteger(X) && (X | Y) != 0 {
- W := 4, H := 20
- return
- }
- ; Acc caret
- static _ := DllCall("LoadLibrary", "Str","oleacc", "Ptr")
- try {
- idObject := 0xFFFFFFF8 ; OBJID_CARET
- if DllCall("oleacc\AccessibleObjectFromWindow", "ptr", WinExist("A"), "uint",idObject &= 0xFFFFFFFF
- , "ptr",-16 + NumPut("int64", idObject == 0xFFFFFFF0 ? 0x46000000000000C0 : 0x719B3800AA000C81, NumPut("int64", idObject == 0xFFFFFFF0 ? 0x0000000000020400 : 0x11CF3C3D618736E0, IID := Buffer(16)))
- , "ptr*", oAcc := ComValue(9,0)) = 0 {
- x:=Buffer(4), y:=Buffer(4), w:=Buffer(4), h:=Buffer(4)
- oAcc.accLocation(ComValue(0x4003, x.ptr, 1), ComValue(0x4003, y.ptr, 1), ComValue(0x4003, w.ptr, 1), ComValue(0x4003, h.ptr, 1), 0)
- X:=NumGet(x,0,"int"), Y:=NumGet(y,0,"int"), W:=NumGet(w,0,"int"), H:=NumGet(h,0,"int")
- if (X | Y) != 0
- return
- }
- }
- static JAB := InitJAB() ; Source: https://github.com/Elgin1/Java-Access-Bridge-for-AHK
- if JAB && (hWnd := WinExist("A")) && DllCall(JAB.module "\isJavaWindow", "ptr", hWnd, "CDecl Int") {
- if JAB.firstRun
- Sleep(200), JAB.firstRun := 0
- prevThreadDpiAwarenessContext := DllCall("SetThreadDpiAwarenessContext", "ptr", -2, "ptr")
- DllCall(JAB.module "\getAccessibleContextWithFocus", "ptr", hWnd, "Int*", &vmID:=0, JAB.acType "*", &ac:=0, "Cdecl Int") "`n"
- DllCall(JAB.module "\getCaretLocation", "Int", vmID, JAB.acType, ac, "Ptr", Info := Buffer(16,0), "Int", 0, "Cdecl Int")
- DllCall(JAB.module "\releaseJavaObject", "Int", vmId, JAB.acType, ac, "CDecl")
- DllCall("SetThreadDpiAwarenessContext", "ptr", prevThreadDpiAwarenessContext, "ptr")
- X := NumGet(Info, 0, "Int"), Y := NumGet(Info, 4, "Int"), W := NumGet(Info, 8, "Int"), H := NumGet(Info, 12, "Int")
- hMonitor := DllCall("MonitorFromWindow", "ptr", hWnd, "int", 2, "ptr") ; MONITOR_DEFAULTTONEAREST
- DllCall("Shcore.dll\GetDpiForMonitor", "ptr", hMonitor, "int", 0, "uint*", &dpiX:=0, "uint*", &dpiY:=0)
- if dpiX
- X := DllCall("MulDiv", "int", X, "int", dpiX, "int", 96, "int"), Y := DllCall("MulDiv", "int", Y, "int", dpiX, "int", 96, "int")
- if X || Y || W || H
- return
- }
- ; UIA caret
- static IUIA := ComObject("{e22ad333-b25f-460c-83d0-0581107395c9}", "{34723aff-0c9d-49d0-9896-7ab52df8cd8a}")
- try {
- ComCall(8, IUIA, "ptr*", &FocusedEl:=0) ; GetFocusedElement
- ComCall(16, FocusedEl, "int", 10014, "ptr*", &patternObject:=0), ObjRelease(FocusedEl) ; GetCurrentPattern. TextPattern = 10014
- if patternObject {
- ComCall(5, patternObject, "ptr*", &selectionRanges:=0), ObjRelease(patternObject) ; GetSelections
- ComCall(4, selectionRanges, "int", 0, "ptr*", &selectionRange:=0) ; GetElement
- ComCall(10, selectionRange, "ptr*", &boundingRects:=0), ObjRelease(selectionRange), ObjRelease(selectionRanges) ; GetBoundingRectangles
- if (Rect := ComValue(0x2005, boundingRects)).MaxIndex() = 3 { ; VT_ARRAY | VT_R8
- X:=Round(Rect[0]), Y:=Round(Rect[1]), W:=Round(Rect[2]), H:=Round(Rect[3])
- return
- }
- }
- }
- InitJAB() {
- ret := {}, ret.firstRun := 1, ret.module := A_PtrSize = 8 ? "WindowsAccessBridge-64.dll" : "WindowsAccessBridge-32.dll", ret.acType := "Int64"
- ret.DefineProp("__Delete", {call: (this) => DllCall("FreeLibrary", "ptr", this)})
- if !(ret.ptr := DllCall("LoadLibrary", "Str", ret.module, "ptr")) && A_PtrSize = 4 {
- ; try legacy, available only for 32-bit
- ret.acType := "Int", ret.module := "WindowsAccessBridge.dll", ret.ptr := DllCall("LoadLibrary", "Str", ret.module, "ptr")
- }
- if !ret.ptr
- return ; Failed to load library. Make sure you are running the script in the correct bitness and/or Java for the architecture is installed.
- DllCall(ret.module "\Windows_run", "Cdecl Int")
- return ret
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement