1 (изменено: Grey, 2010-12-05 11:45:01)

Тема: AHK: Залипание клавиши после нажатия другой в теле одного скрипта.

Здравствуйте, подскажите, в чём причина "залипания" горячих клавиш при работе вот этого скрипта:

#UseHook, On
;---mode switcher
RAlt & F9::
If fmsw
   {
      fmsw = 0
      fmode = 0
   }
Else
   {
      fmsw = 1
      fmode = 1
   }
Exit
;---forward
vk57:: ; w
If (fmode = 1)
   {
      SendInput, {vk45 Down} ; e
      KeyWait, vk57
      SendInput, {vk45 Up}
   }
Else
   {
            SendInput, {vk57 Down}
            KeyWait, vk57
            SendInput, {vk57 Up}
   }
Return
;---back
vk53:: ; s
If (fmode = 1)
   {
      SendInput, {vk51 Down} ; q
      KeyWait, vk53
      SendInput, {vk51 Up}
   }
Else
   {
      SendInput, {vk53 Down}
      KeyWait, vk53
      SendInput, {vk53 Up}
   }
Return
;---turn right
vk45:: ; e
If (fmode = 1)
   {
      SendInput, {vk4e Down} ; n
      KeyWait, vk45
      SendInput, {vk4e Up}
   }
Else
   {
      SendInput, {vk45 Down}
      KeyWait, vk45
      SendInput, {vk45 Up}
   }
Return
;---turn left
vk51:: ; q
If (fmode = 1)
   {
      SendInput, {vk4d Down} ; m
      KeyWait, vk51
      SendInput, {vk4d Up}
   }
Else
   {
      SendInput, {vk51 Down}
      KeyWait, vk51
      SendInput, {vk51 Up}
   }
Return
;---right strafe
vk44:: ; d
If (fmode = 1)
   {
      SendInput, {vk42 Down} ; b
      KeyWait, vk44
      SendInput, {vk42 Up}
   }
Else
   {
      SendInput, {vk44 Down}
      KeyWait, vk44
      SendInput, {vk44 Up}
   }
Return
;---left strafe
vk41:: ; a
If (fmode = 1)
   {
      SendInput, {vk56 Down} ; v
      KeyWait, vk41
      SendInput, {vk56 Up}
   }
Else
   {
      SendInput, {vk41 Down}
      KeyWait, vk41
      SendInput, {vk41 Up}
   }
Return
#UseHook, Off

При включении одного из режимов на RAlt+F9 изменяются функции горячих клавиш, и всё вроде-бы работает, но если нажать и удерживать одну из горячих клавиш и нажимать другие, то первая (и все последующие) при её физическом отпускании продолжает работать пока не будет отпущена горячая клавиша нажатая последней. Как этого избежать?

2

Re: AHK: Залипание клавиши после нажатия другой в теле одного скрипта.

Потоки

Grey пишет:

Как этого избежать?

Чтобы сказать наверняка, нужно иметь программу, которая воспринимает  нажатия клавиш. Попробуй вместо

vk57:: ; w
If (fmode = 1)
   {
      SendInput, {vk45 Down} ; e
      KeyWait, vk57
      SendInput, {vk45 Up}
   }
Else
   {
            SendInput, {vk57 Down}
            KeyWait, vk57
            SendInput, {vk57 Up}
   }
Return

писать

#UseHook
vk57::   ; w
   SendInput, % "{vk" (fmode = 1 ? 45 : 57) " Down}"
   KeyWait, vk57
   Return
   
vk57 Up:: SendInput, % "{vk" (fmode = 1 ? 45 : 57) " Up}"

и аналогично по остальным клавишам.

Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder

3

Re: AHK: Залипание клавиши после нажатия другой в теле одного скрипта.

teadrinker пишет:

...и аналогично по остальным клавишам.

Дополнив свой код тремя директивами: #MaxHotkeysPerInterval,
                                                            #MaxThreadsPerHotkey,
                                                            #MaxThreads и переписав как посоветовали через более короткий вариант конструкции if-else - я добился своей цели, за, что Вам большое-человеческое спасибо!
В этом приложении (игре) есть одна довольно таки очень утомляющая проблема - при повторном быстром нажатии курсорной клавиши w персонаж начинает бежать, хотя должен по идее идти (для бега есть сочетание этой клавиши и правой клавиши мыши). Пересмотрев этот форум, я нашел для себя решение этой проблемы и добавил в код:

#MaxHotkeysPerInterval 10000
#MaxThreadsPerHotkey 10000
#MaxThreads 10000
#UseHook, On
fmode := 0 ; 0 - move/helicopter, 1 - uav
starttime := A_TickCount
doubleclick := 0
Return
;---flight mode switcher
RAlt & F9::
If fmsw
   {
      fmsw = 0
      fmode := 0
      SendInput, {vk55}
      Sleep, 250
      SendInput, {Raw}| heli |
      SoundBeep, 5500, 100
      SendInput, {Escape}
      Sleep, 350
      SendInput, {vkc0 2}
   }
Else
   {
      fmsw = 1
      fmode := 1
      SendInput, {vk55}
      Sleep, 250
      SendInput, {Raw}| uav |
      SoundBeep, 5500, 100
      Sleep, 100
      SoundBeep, 5500, 100
      SendInput, {Escape}
      Sleep, 250
      SendInput, {vkc0 2}
   }
Exit
;---forward/block unwanted runs/heli forward/uav forward
vk57:: ; w
If (fmode = 0)
   {
      elapsedtime := A_TickCount - starttime
      IF (elapsedtime < 150) AND (doubleclick = 1)
         {
            SendInput, {vk57 Down}
            Sleep, 200
            SendInput, {RButton}
            KeyWait, vk57
            doubleclick := 0
         }
      Else
         {
            SendInput, {vk57 Down}
            KeyWait, vk57
            doubleclick := 1
         }
      starttime := A_TickCount
   }
Else
   {
      SendInput, % "{vk" (fmode = 1 ? 45 : 57) " Down}" ; e
      KeyWait, vk57
   }
Return
vk57 Up:: SendInput, % "{vk" (fmode = 1 ? 45 : 57) " Up}"
If (fmode = 0)
   {
      SendInput, {vk57 Up}
   }
Return
;---back/uav backward
vk53:: ; s
SendInput, % "{vk" (fmode = 1 ? 51 : 53) " Down}" ; q
KeyWait, vk53
Return
vk53 Up:: SendInput, % "{vk" (fmode = 1 ? 51 : 53) " Up}"
;---turn right/heli ascend/uav ascend
vk45:: ; e
SendInput, % "{vk" (fmode = 1 ? 4e : 45) " Down}" ; n
KeyWait, vk45
Return
vk45 Up:: SendInput, % "{vk" (fmode = 1 ? 4e : 45) " Up}"
;---turn left/heli descend/uav descend
vk51:: ; q
SendInput, % "{vk" (fmode = 1 ? 4d : 51) " Down}" ; m
KeyWait, vk51
Return
vk51 Up:: SendInput, % "{vk" (fmode = 1 ? 4d : 51) " Up}"
;---right strafe/heli turn right/uav turn right
vk44:: ; d
SendInput, % "{vk" (fmode = 1 ? 42 : 44) " Down}" ; b
KeyWait, vk44
Return
vk44 Up:: SendInput, % "{vk" (fmode = 1 ? 42 : 44) " Up}"
;---left strafe/heli turn left/uav turn left
vk41:: ; a
SendInput, % "{vk" (fmode = 1 ? 56 : 41) " Down}" ; v
KeyWait, vk41
Return
vk41 Up:: SendInput, % "{vk" (fmode = 1 ? 56 : 41) " Up}"

всё устраивает/всё работает, за исключением замены функции у клавиш q и e в режиме fmode = 1. Хотя вот так:

;---turn right/heli ascend/uav ascend
vk45:: ; e
If (fmode = 1)
   {
      SendInput, {vk4e Down} ; n
      KeyWait, vk45
      SendInput, {vk4e Up}
   }
Else
   {
      SendInput, {vk45 Down}
      KeyWait, vk45
      SendInput, {vk45 Up}
   }
Return
;---turn left/heli descend/uav descend
vk51:: ; q
If (fmode = 1)
   {
      SendInput, {vk4d Down} ; m
      KeyWait, vk51
      SendInput, {vk4d Up}
   }
Else
   {
      SendInput, {vk51 Down}
      KeyWait, vk51
      SendInput, {vk51 Up}
   }
Return

замена работает, а в новом варианте нет. Подскажите пожалуйста почему не работает замена в коротком варианте if-else?, сам я причины не нашел.

4

Re: AHK: Залипание клавиши после нажатия другой в теле одного скрипта.

Без наличия целевого приложения вряд ли можно сказать что-то конкретное.

Разработка AHK-скриптов:
e-mail dfiveg@mail.ru
Telegram jollycoder

5

Re: AHK: Залипание клавиши после нажатия другой в теле одного скрипта.

Не работает просто эта часть кода -

;---turn right/heli ascend/uav ascend
vk45:: ; e
SendInput, % "{vk" (fmode = 1 ? 4e : 45) " Down}" ; n
KeyWait, vk45
Return
vk45 Up:: SendInput, % "{vk" (fmode = 1 ? 4e : 45) " Up}"
;---turn left/heli descend/uav descend
vk51:: ; q
SendInput, % "{vk" (fmode = 1 ? 4d : 51) " Down}" ; m
KeyWait, vk51
Return
vk51 Up:: SendInput, % "{vk" (fmode = 1 ? 4d : 51) " Up}"

, просто нет ввода букв n и m по нажатию e и q (без приложения). Не пойму почему?, ведь составленно всё вроде правильно.

6

Re: AHK: Залипание клавиши после нажатия другой в теле одного скрипта.

Хмм..., беру самоотвод своего вопроса, я заменил виртуальный код клавиши на скан и всё заработало. Хочу ещё раз поблагодарить за помощь.