1 (изменено: RacalCucumber, 2020-12-15 21:46:51)

Тема: AHK: реакция на отжатие кнопки, как сделать?

Задача:
При отпускании одной из перечисленной кнопки, A\S\D\W кратковременно нажать кнопку m

Я как то жил на логитехе и там это решалось простыми строчками на LUA:
if (event == "G_RELEASED" and (arg == 4 or arg == 11 or arg == 10 or  arg == 12)) then ---если отпущена одни из перечисленных кнопка
Sleep(30) ---подождать остановки персонажа
PressKey("m") --- нажать
Sleep (5) ---подождать
ReleaseKey("m") ---отпустить
end

где arg == 4\11\10\12 это внутренние имена кнопок у девайсов логитеха, которым присвоены соответствующие кнопки обычной клавиатуры.

А как это перенести на AHK?

Если я пытаюсь сделать это через hotkeys типа
W::
;-код-
return

соответствующая кнопка то, указанная в строке хоткея, свое значение то дальше AHK не передает...

Есть какая то возможность у AHK сделать так, что бы нажатие клавиши хоткея было "прозрачным"?

2

Re: AHK: реакция на отжатие кнопки, как сделать?

RacalCucumber
Что означает "нажатие клавиши хоткея было прозрачным" я не понимаю. Но вот скрипт который вам нужен. Есть более сложный способ, но это самый простой.

*~$A UP:: ; Если отпущена то...
Sleep, 30 ; Подождать 30 миллисекунд.
Send, {M down} ; Зажать кнопку M.
Sleep, 5 ; Подождать 5 миллисекунд.
Send, {M up} ; Отпустить кнопку M.
return ; Ждать следующего действия пользователя.

*~$S UP:: ; Если отпущена то...
Sleep, 30 ; Подождать 30 миллисекунд.
Send, {M down} ; Зажать кнопку M.
Sleep, 5 ; Подождать 5 миллисекунд.
Send, {M up} ; Отпустить кнопку M.
return ; Ждать следующего действия пользователя.

*~$D UP:: ; Если отпущена то...
Sleep, 30 ; Подождать 30 миллисекунд.
Send, {M down} ; Зажать кнопку M.
Sleep, 5 ; Подождать 5 миллисекунд.
Send, {M up} ; Отпустить кнопку M.
return ; Ждать следующего действия пользователя.

*~$W UP:: ; Если отпущена то...
Sleep, 30 ; Подождать 30 миллисекунд.
Send, {M down} ; Зажать кнопку M.
Sleep, 5 ; Подождать 5 миллисекунд.
Send, {M up} ; Отпустить кнопку M.
return ; Ждать следующего действия пользователя.

3 (изменено: __Михаил__, 2020-12-15 23:13:31)

Re: AHK: реакция на отжатие кнопки, как сделать?

Vsevolod

О не надо постить портянки на 100500+ строк!


RacalCucumber

С эмуляцией нажатия самой себя:

*W::
*S::
*A::
*D::
S := SubStr(A_ThisHotkey, 2)
SendInput, {%S% Down}
KeyWait, %S%, U
SendInput, {%S% Up}
SendInput, {Blind}{vk4D}	;	M - клавиша.
Return

Без эмуляции - 'прозрачный перехват' клавиш. Так даже правильнее:

*~W Up::
*~S Up::
*~A Up::
*~D Up::
SendInput, {Blind}{vk4D}	;	M - клавиша.
Return
Win10x64, AHK v1.1.37.01 (Unicode 64-bit) | AHK-Wiki | Переменные и выражения | RegEx101

4

Re: AHK: реакция на отжатие кнопки, как сделать?

как же хреново быть тупым.... спасибо.

5

Re: AHK: реакция на отжатие кнопки, как сделать?

RacalCucumber

Нужно больше на форумах сидеть - там можно многому научиться.

Win10x64, AHK v1.1.37.01 (Unicode 64-bit) | AHK-Wiki | Переменные и выражения | RegEx101

6

Re: AHK: реакция на отжатие кнопки, как сделать?

RacalCucumber
Полностью согласен

7 (изменено: Vsevolod, 2020-12-16 17:04:36)

Re: AHK: реакция на отжатие кнопки, как сделать?

__Михаил__
Что означает SendInput, {Blind} ?
И чем лучше SendInput от Send? Если SendInput лучше то какая польза от Send?

8 (изменено: RacalCucumber, 2020-12-16 20:51:20)

Re: AHK: реакция на отжатие кнопки, как сделать?

Так. Все таки правильное (нет) сформулированное ТЗ половина дела. Все пошло не так...
Вопрос теперь уже наверное не по написанию программа в просто "что вообще происходит?!".

Что требовалось изначально:
- При нажатии на правую кнопку мышки тапнуть кнопку "m". "м" - это не именно именно мэ а просто некая кнопка. Вот у меня "["
- Если ПКМ удерживается - то по отпусканию кнопок W\A\S\D тапнуть кнопку "m".

Был написан вот такой говнокод:

~$*RButton:: 
;IfWinActive, tetris
{
	Sleep, 50
	SendInput, {Blind}{vkDB}
	restart:
	while (GetKeyState("RButton", "p"))
	{
		Sleep, 100
		if GetKeyState("w", "p") 
		{
			KeyWait, w
			kps()
			Break	
		}
		if GetKeyState("s", "p")
		{
			KeyWait, s
			kps()
			Break	
		}
		if GetKeyState("a", "p")
		{
			KeyWait, a
			kps()
			Break	
		}
		if GetKeyState("d", "p")
		{
			KeyWait, d
			kps()
			Break	
		}
	}
	if (GetKeyState("RButton", "p"))
	{
		Goto restart
	}
}
return

kps()
{
	Sleep, 200
	SendInput, {Blind}{vkDB}	
	return
}

Странности касаются поведения одновременно нажимаемых кнопок WASD в произвольной комбинации:
- Клавиатура Logitech G13:
последняя, из произвольно одновременно ранее удерживаемых, отжатая кнопка вызывает тап "[" Типа "как задумывалось". На самом деле нет, но именно так и должна работать по уму. 

- Клавиатура Cherry, подключенная через ps\2-usb хаб:
1. нажимаю одну кнопку
2. Нажимаю вторую кнопку
3. Отпускаю вторую кнопку
4. тапается "[".
5. Отпускаю первую кнопку
6. ничего не происходит...

Причем если я делаю отладочную закладку через msgbox в функции kps() - утверждается что после отпускания второй кнопки (п.3-п.4) статус первой уже U (отпущена). Несмотря на то, что физически она нажата.

Теперь вопрос. Где норма. А где отклонение? И попробуйте, пожалуйста, как у вас работает этот скрипт?

9 (изменено: RacalCucumber, 2020-12-16 20:46:55)

Re: AHK: реакция на отжатие кнопки, как сделать?

мисс

10

Re: AHK: реакция на отжатие кнопки, как сделать?

RacalCucumber

Если плохо поставлена задача - нет результата. Увы, у нас тут телепатов нет.

Win10x64, AHK v1.1.37.01 (Unicode 64-bit) | AHK-Wiki | Переменные и выражения | RegEx101

11

Re: AHK: реакция на отжатие кнопки, как сделать?

Ну, на самом деле, я когда начал тред еще и сам не до конца сформулировал логику работы скрипта. Хотя вот как оказалось узнал что несколько хоткеев можно завязать на одно событие.... Сам бы я до такого не додумался бы...

12

Re: AHK: реакция на отжатие кнопки, как сделать?

1) Какие у вас девайсы - глубоко побоку, все они имеют стандарт, который понимает комп и соответственно все программы. Т.е. можно не указывать - толку 0.
2) Составьте грамотное сообщение как должно получится при нажатии тех или иных клавиш. Больше вариантов. Тогда будет понятна суть.

Задачу я понял так: При отпуске любой из клавиш W/A/S/D - нажать M. Результат в 3 сообщении.

Win10x64, AHK v1.1.37.01 (Unicode 64-bit) | AHK-Wiki | Переменные и выражения | RegEx101

13

Re: AHK: реакция на отжатие кнопки, как сделать?

__Михаил__ пишет:

1) Какие у вас девайсы - глубоко побоку, все они имеют стандарт, который понимает комп и соответственно все программы. Т.е. можно не указывать - толку 0.

Вы не поверите, но нет. Еще две найденных старых клавиатуры, обычные, работают так же, как и логитех. Похоже я сутки бился головой в криво работающую клавиатуру....

__Михаил__ пишет:

2) Составьте грамотное сообщение как должно получится при нажатии тех или иных клавиш. Больше вариантов. Тогда будет понятна суть.
Задачу я понял так: При отпуске любой из клавиш W/A/S/D - нажать M. Результат в 3 сообщении.

В итоге оказалось требуется вот что:
- При нажатии на Правую Кнопку Мышки нажать-отпустить кнопку "м".
- При удерживаемой Правой Кнопки Мышки отпускание {любой одиночно нажатой кнопки из WASD} или {последней удерживаемой кнопки из комбинации нескольких нажатых кнопок WASD } один раз нажать-отпустить кнопку "м".
- Повторять нажатия-отпускания кнопки "м" в последующих случаях использования кнопок WASD при удерживаемой нажатой Правой Кнопки Мышки.

14

Re: AHK: реакция на отжатие кнопки, как сделать?

RacalCucumber

На сколько мне известно, не все клавиатуры могут обрабатывать несколько обычных клавиш (не модификаторов) за раз.
АХК хорошо перехватывает клавиши, но не стоит от него ожидать волшебства или чёрной магии.

- При нажатии на Правую Кнопку Мышки нажать-отпустить кнопку "м".

Выбрать одну строку из кода:

;Нажать M после отжатия ПКМ (с сохранением нажатого модификатора).
*vk2 Up::SendInput, {Blind}{vk4D}	; Полный перехват ПКМ.

*~vk2 Up::SendInput, {Blind}{vk4D}	; 'Прозрачный' перехват ПКМ.
Win10x64, AHK v1.1.37.01 (Unicode 64-bit) | AHK-Wiki | Переменные и выражения | RegEx101

15

Re: AHK: реакция на отжатие кнопки, как сделать?

Примерно такой код для отпуска W/A/S/D. +постоянного спама M клавиши при удержании ПКМ:

*vk2::	; Полный перехват ПКМ.
SendInput, {W Up}{A Up}{S Up}{D Up}	; Отпустить все клавиши W/A/S/D.
KeyWait, vk2, T.3		; Ожидать отжатия клавиши 0.3 секунды.
If ErrorLevel = 0	; Если ПКМ отжата:
{
 SendInput, {Blind}{vk4D}	; Нажать M
 Return
}

; Если ПКМ зажата более 0.3 сек. то:
While, % GetKeyState(SubStr(A_ThisHotkey,2),"p")	; Пока зажата ПКМ:
{
 Sleep, 100
 SendInput, {Blind}{vk4D}	; Нажать M
}
Return
Win10x64, AHK v1.1.37.01 (Unicode 64-bit) | AHK-Wiki | Переменные и выражения | RegEx101