Управление индикаторами клавиатуры

Обсуждение программ nnCron и nnCron LITE

Управление индикаторами клавиатуры

Postby Wyz » Wed, 20 May 2009, 18:04

Должно работать на NT+ с PS/2 клавами; проверено на XP SP2. Если нужно USB или под 9x - делайте сами :-)

Если нажать на клаве Caps/Num/Scroll, то индикаторы зажгутся в соответствии с состояниями этих кнопок.

Ссылки по теме:
http://www.rsdn.ru/Forum/message/3189897.flat.aspx
http://mamedev.org/source/src/osd/windo ... til.c.html
http://sources.ru/cpp/cpp_nt_kbd_lites.shtml
http://www.rsdn.ru/forum/message/1357795.flat.aspx

Code: Select all
#( TestKbdLed
NoActive

WINAPI: DefineDosDeviceA kernel32.dll
WINAPI: DeviceIoControl  kernel32.dll

0x40000000 CONSTANT GENERIC_WRITE
\         3 CONSTANT OPEN_EXISTING
\        -1 CONSTANT INVALID_HANDLE_VALUE

         1 CONSTANT DDD_RAW_TARGET_PATH
0x000B0008 CONSTANT IOCTL_KEYBOARD_SET_INDICATORS
0x000B0040 CONSTANT IOCTL_KEYBOARD_QUERY_INDICATORS

         4 CONSTANT KEYBOARD_CAPS_LOCK_ON
         2 CONSTANT KEYBOARD_NUM_LOCK_ON
         1 CONSTANT KEYBOARD_SCROLL_LOCK_ON

\ Нет проверки ошибок :-)

: KbdPs2DeviceOpen ( -- DeviceHandle )
Z" \Device\KeyboardClass0"
Z" nnCronKeyboardControl"
DDD_RAW_TARGET_PATH DefineDosDeviceA DROP
0 0 OPEN_EXISTING 0 0 GENERIC_WRITE Z" \\.\nnCronKeyboardControl" CreateFileA
;

: KbdPs2LedSetAll { LedMask DeviceHandle \ inBuffer BytesReturned -- IoFlag }
LedMask 16 LSHIFT TO inBuffer
0               \ overlapped information
AT BytesReturned
0 0             \ size, outBuffer
4               \ size of input data buffer
AT inBuffer     \ input data buffer, KEYBOARD_INDICATOR_PARAMETERS
IOCTL_KEYBOARD_SET_INDICATORS DeviceHandle DeviceIoControl \ 0 - error
;

: KbdPs2LedGetAll { DeviceHandle \ outBuffer BytesReturned -- LedMask IoFlag }
0 AT BytesReturned 4 AT outBuffer 0 0 IOCTL_KEYBOARD_QUERY_INDICATORS DeviceHandle DeviceIoControl
outBuffer 16 RSHIFT SWAP
;

\ Зажигает указанные индикаторы, остальные - как были
: KbdPs2LedSet ( LedMask -- IoFlag )
KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP OR R@ KbdPs2LedSetAll R> CloseHandle DROP
;

\ Гасит указанные индикаторы, остальные - как были
: KbdPs2LedReset ( LedMask -- IoFlag )
INVERT KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP AND R@ KbdPs2LedSetAll R> CloseHandle DROP
;

\ На входе - маска интересующих индикаторов (можно тупо -1), вернет маску запрошенных зажженных.
: KbdPs2LedGet ( LedMask -- LedMask IoFlag )
KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll >R AND R> R> CloseHandle DROP
;

Action:
KEYBOARD_NUM_LOCK_ON KbdPs2LedSet DROP
333 PAUSE
KEYBOARD_NUM_LOCK_ON KbdPs2LedReset DROP

KEYBOARD_CAPS_LOCK_ON KbdPs2LedSet DROP
333 PAUSE
KEYBOARD_CAPS_LOCK_ON KbdPs2LedReset DROP

KEYBOARD_SCROLL_LOCK_ON KbdPs2LedSet DROP
333 PAUSE
KEYBOARD_SCROLL_LOCK_ON KbdPs2LedReset DROP

KEYBOARD_NUM_LOCK_ON DUP KbdPs2LedSet DROP 333 PAUSE KbdPs2LedReset DROP
KEYBOARD_NUM_LOCK_ON KEYBOARD_CAPS_LOCK_ON OR DUP KbdPs2LedSet DROP 333 PAUSE KbdPs2LedReset DROP
KEYBOARD_NUM_LOCK_ON KEYBOARD_CAPS_LOCK_ON OR KEYBOARD_SCROLL_LOCK_ON OR DUP KbdPs2LedSet DROP 333 PAUSE KbdPs2LedReset DROP

KEYBOARD_NUM_LOCK_ON KbdPs2LedSet DROP 333 PAUSE
KEYBOARD_CAPS_LOCK_ON KbdPs2LedSet DROP 333 PAUSE
KEYBOARD_SCROLL_LOCK_ON KbdPs2LedSet DROP
)#


-------------
2009.06.15 - Немного переделал KbdPs2LedSetAll и KbdPs2LedGetAll...
Last edited by Wyz on Mon, 15 Jun 2009, 03:54, edited 3 times in total.
Wyz
 
Posts: 389
Joined: Tue, 11 Dec 2007, 01:42

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Wed, 20 May 2009, 21:33

1. Жуткие имена - сменить. Например на CapsOn CapsOff NumOn NumOff ScrollOn ScrollOff.
2. Пустая работа - то же самое делается эмуляцией кнопок.
http://www.nncron.ru/forums/viewtopic.php?f=23&t=9476#p21478
Code: Select all
NumLock ScrollLock CapsLock
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56

Re: Управление индикаторами клавиатуры

Postby Wyz » Wed, 20 May 2009, 22:08

VoidVolker wrote:1. Жуткие имена - сменить.

Сам меняй! :-D
2. Пустая работа - то же самое делается эмуляцией кнопок.
http://www.nncron.ru/forums/viewtopic.php?f=23&t=9476#p21478
Code: Select all
NumLock ScrollLock CapsLock

Идея в мигании светодиодами, а не в "нажимании" кнопок. "CapsLock" еще и регистр букв переключать будет.
Wyz
 
Posts: 389
Joined: Tue, 11 Dec 2007, 01:42

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Wed, 20 May 2009, 23:34

Wyz wrote:Сам меняй!

Code: Select all
MODULE: KeyBoardLed

  WINAPI: DefineDosDeviceA kernel32.dll
  WINAPI: DeviceIoControl  kernel32.dll

  0x40000000 CONSTANT GENERIC_WRITE
  \         3 CONSTANT OPEN_EXISTING
  \        -1 CONSTANT INVALID_HANDLE_VALUE

           1 CONSTANT DDD_RAW_TARGET_PATH
  0x000B0008 CONSTANT IOCTL_KEYBOARD_SET_INDICATORS
  0x000B0040 CONSTANT IOCTL_KEYBOARD_QUERY_INDICATORS

  : KbdPs2DeviceOpen ( -- DeviceHandle )
    S" \Device\KeyboardClass0" DROP
    S" nnCronKeyboardControl" DROP
    DDD_RAW_TARGET_PATH DefineDosDeviceA DROP
    0 0 OPEN_EXISTING 0 0 GENERIC_WRITE S" \\.\nnCronKeyboardControl" DROP CreateFileA
  ;

  : KbdPs2LedSetAll ( LedMask DeviceHandle -- IoFlag )
    >R \ DeviceHandle
    16 LSHIFT SP@ >R \ input buffer, KEYBOARD_INDICATOR_PARAMETERS
    0 SP@ 0 SWAP 0 0 4 R> IOCTL_KEYBOARD_SET_INDICATORS R> DeviceIoControl \ 0 - error
    >R DROP DROP R>
  ;

  : KbdPs2LedGetAll ( DeviceHandle -- LedMask IoFlag )
    >R
    0 SP@ >R \  output buffer
    0 SP@ 0 SWAP 4 R> 0 0 IOCTL_KEYBOARD_QUERY_INDICATORS R> DeviceIoControl
    >R DROP 16 RSHIFT R>
  ;

EXPORT

   4 CONSTANT Caps   \ KEYBOARD_CAPS_LOCK_ON
   2 CONSTANT Num    \ KEYBOARD_NUM_LOCK_ON
   1 CONSTANT Scroll \ KEYBOARD_SCROLL_LOCK_ON
           
  : LedOn ( Led --  )  \ Включить индикатор
    KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP OR
    R@ KbdPs2LedSetAll R> CloseHandle
    2DROP
  ;

  : LedOff ( Led -- )  \ Выключить индикатор
    INVERT KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP AND
    R@ KbdPs2LedSetAll R> CloseHandle
    2DROP
  ;
 
  : LedOn? ( Led -- ? )  \ Вернуть состояние индикатора
    KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll >R AND R> R> CloseHandle 2DROP 0<>
  ;
 
  : LedInvert   ( Led -- )
    DUP LedOn?
      IF
        LedOff
      ELSE
        LedOn
      THEN
  ;

;MODULE

Wyz wrote:Идея в мигании светодиодами, а не в "нажимании" кнопок.

Ааа, ну это уже интереснее.
Last edited by VoidVolker on Thu, 13 May 2010, 05:33, edited 5 times in total.
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56

Re: Управление индикаторами клавиатуры

Postby Wyz » Thu, 21 May 2009, 00:20

Предлагаю "LedNumOn", "LedNumOff"... - чтоб было ясно, что только светодиод.
Wyz
 
Posts: 389
Joined: Tue, 11 Dec 2007, 01:42

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Thu, 21 May 2009, 10:07

Да, хорошая идея - исправил.
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56

Re: Управление индикаторами клавиатуры

Postby Wyz » Thu, 21 May 2009, 10:54

И еще: "LedsGetAll" или "LedNumGet"... - чтоб можно было вернуть состояние.
Wyz
 
Posts: 389
Joined: Tue, 11 Dec 2007, 01:42

Re: Управление индикаторами клавиатуры

Postby AlikasS » Thu, 21 May 2009, 14:07

если зажечь все три и погасить любой один, у меня гасятся все
Code: Select all
: LedAllRot { nDo nP -- }
nDo 0 DO
LedNumOn
nP PAUSE
LedCapsOn
nP PAUSE
LedScrollOn
nP PAUSE
LedScrollOff
nP PAUSE
 LedCapsOff
nP PAUSE
LedNumOff
nP PAUSE
LOOP
;

и в консоли
Code: Select all
10 500 LedAllRot
User avatar
AlikasS
 
Posts: 1437
Joined: Wed, 28 Jun 2006, 05:39
Location: Khabarovsk

Re: Управление индикаторами клавиатуры

Postby Wyz » Thu, 21 May 2009, 17:16

Да, недотестил :-)
В KbdPs2LedReset нужно заменить "NOT" на "INVERT".
Wyz
 
Posts: 389
Joined: Tue, 11 Dec 2007, 01:42

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Thu, 21 May 2009, 19:51

Ага, исправил.
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Fri, 12 Jun 2009, 22:09

Ап! Вот использовал данный код и немного подправил для более удобного использования.
Разместил в старом посте.
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56

Re: Управление индикаторами клавиатуры

Postby AlikasS » Sat, 13 Jun 2009, 16:33

у меня их предыдущего твоего поста и исправленного получился такой набор
Code: Select all
MODULE: KeyBoardLed

WINAPI: DefineDosDeviceA kernel32.dll
WINAPI: DeviceIoControl  kernel32.dll

0x40000000 CONSTANT GENERIC_WRITE
\         3 CONSTANT OPEN_EXISTING
\        -1 CONSTANT INVALID_HANDLE_VALUE

         1 CONSTANT DDD_RAW_TARGET_PATH
0x000B0008 CONSTANT IOCTL_KEYBOARD_SET_INDICATORS
0x000B0040 CONSTANT IOCTL_KEYBOARD_QUERY_INDICATORS

         4 CONSTANT KEYBOARD_CAPS_LOCK_ON
         2 CONSTANT KEYBOARD_NUM_LOCK_ON
         1 CONSTANT KEYBOARD_SCROLL_LOCK_ON

\ Нет проверки ошибок :-)

: KbdPs2DeviceOpen ( -- DeviceHandle )
Z" \Device\KeyboardClass0"
Z" nnCronKeyboardControl"
DDD_RAW_TARGET_PATH DefineDosDeviceA DROP
0 0 OPEN_EXISTING 0 0 GENERIC_WRITE Z" \\.\nnCronKeyboardControl" CreateFileA
;

: KbdPs2LedSetAll ( LedMask DeviceHandle -- IoFlag )
>R \ DeviceHandle
16 LSHIFT SP@ >R \ input buffer, KEYBOARD_INDICATOR_PARAMETERS
0 SP@ 0 SWAP 0 0 4 R> IOCTL_KEYBOARD_SET_INDICATORS R> DeviceIoControl \ 0 - error
>R DROP DROP R>
;

: KbdPs2LedGetAll ( DeviceHandle -- LedMask IoFlag )
>R
0 SP@ >R \  output buffer
0 SP@ 0 SWAP 4 R> 0 0 IOCTL_KEYBOARD_QUERY_INDICATORS R> DeviceIoControl
>R DROP 16 RSHIFT R>
;

\ Зажигает указанные индикаторы, остальные - как были
: KbdPs2LedSet ( LedMask -- IoFlag )
KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP OR R@ KbdPs2LedSetAll R> CloseHandle DROP
;

\ Гасит указанные индикаторы, остальные - как были
: KbdPs2LedReset ( LedMask -- IoFlag )
( NOT ) INVERT KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP AND R@ KbdPs2LedSetAll R> CloseHandle DROP
;

\ На входе - маска интересующих индикаторов (можно тупо -1), вернет маску запрошенных зажженных.
: KbdPs2LedGet ( LedMask -- LedMask IoFlag )
KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll >R AND R> R> CloseHandle DROP
;

EXPORT

  KEYBOARD_NUM_LOCK_ON VALUE Num
  KEYBOARD_CAPS_LOCK_ON VALUE Caps
  KEYBOARD_SCROLL_LOCK_ON VALUE Scroll

  : LedOn ( Led --  )  \ Включить индикатор
    KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP OR
    R@ KbdPs2LedSetAll R> CloseHandle
    2DROP
  ;

  : LedOff ( Led -- )  \ Выключить индикатор
    INVERT KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll DROP AND
    R@ KbdPs2LedSetAll R> CloseHandle
    2DROP
  ;
 
  : LedOn? ( Led -- ? )  \ Вернуть состояние индикатора
    KbdPs2DeviceOpen DUP >R KbdPs2LedGetAll >R AND R> R> CloseHandle 2DROP 0<>
  ;
 
  : LedInvert   ( Led -- )
    DUP LedOn?
      IF
        LedOff
      ELSE
        LedOn
      THEN
  ;

: LedNumOn KEYBOARD_NUM_LOCK_ON LedOn  ;
: LedNumOff KEYBOARD_NUM_LOCK_ON LedOff  ;

: LedCapsOn KEYBOARD_CAPS_LOCK_ON LedOn  ;
: LedCapsOff KEYBOARD_CAPS_LOCK_ON LedOff  ;

: LedScrollOn KEYBOARD_SCROLL_LOCK_ON LedOn  ;
: LedScrollOff KEYBOARD_SCROLL_LOCK_ON LedOff  ;

: save2num->adr ( Adr sound  -- adr ) HERE ROT , SWAP , DUP DP ! ;
: adr->2num ( adr -- Adr sound ) DUP @ SWAP CELL+ @ ;

DEFINITIONS
:NONAME { \ nDo nP -- }
adr->2num TO nP TO nDo
nDo 0 DO
LedNumOn nP PAUSE
LedCapsOn nP PAUSE
LedScrollOn nP PAUSE
LedScrollOff nP PAUSE
LedCapsOff nP PAUSE
LedNumOff nP PAUSE
LOOP
; TASK: ~LedAll><

EXPORT
: LedAll>< save2num->adr ~LedAll>< START DROP ;

DEFINITIONS
:NONAME { \ nDo nP -- }
adr->2num TO nP TO nDo
nDo 0 DO
LedScrollOn nP PAUSE
LedCapsOn nP PAUSE
LedNumOn nP PAUSE
LedNumOff nP PAUSE
LedCapsOff nP PAUSE
LedScrollOff nP PAUSE
LOOP
; TASK: ~LedAll<>

EXPORT
: LedAll<> save2num->adr ~LedAll<> START DROP ;

DEFINITIONS
:NONAME { \ nDo nP -- }
adr->2num TO nP TO nDo
nDo 0 DO
LedNumOn nP PAUSE
LedCapsOn nP PAUSE
LedScrollOn nP PAUSE
LedNumOff nP PAUSE
LedCapsOff nP PAUSE
LedScrollOff nP PAUSE
LOOP
; TASK: ~LedAll>
EXPORT
: LedAll> save2num->adr ~LedAll> START DROP ;

DEFINITIONS
:NONAME { \ nDo nP -- }
adr->2num TO nP TO nDo
nDo 0 DO
LedScrollOn nP PAUSE
LedCapsOn nP PAUSE
LedNumOn nP PAUSE
LedScrollOff nP PAUSE
LedCapsOff nP PAUSE
LedNumOff nP PAUSE
LOOP
; TASK: ~LedAll<
EXPORT
: LedAll< save2num->adr ~LedAll< START DROP ;

DEFINITIONS
:NONAME { \ nDo nP -- }
adr->2num TO nP TO nDo
nDo 0 DO
LedNumOn nP PAUSE
LedCapsOn nP PAUSE
LedScrollOn nP PAUSE
LedNumOff nP PAUSE
LedCapsOff nP PAUSE
LedScrollOff nP PAUSE
LedScrollOn nP PAUSE
LedCapsOn nP PAUSE
LedNumOn nP PAUSE
LedScrollOff nP PAUSE
LedCapsOff nP PAUSE
LedNumOff nP PAUSE
LOOP
; TASK: ~LedAll>-< 
EXPORT
: LedAll>-< save2num->adr ~LedAll>-< START DROP ;

DEFINITIONS
:NONAME { \ nDo nP -- }
adr->2num TO nP TO nDo
nDo 0 DO
LedNumOn
LedCapsOn
LedScrollOn
nP PAUSE
LedScrollOff
LedCapsOff
LedNumOff
nP PAUSE
LOOP
; TASK: ~LedAll
EXPORT
: LedAll save2num->adr ~LedAll START DROP ;

;MODULE
может что-то лишнее (можно посмотреть и закомментировать?), но вроде все работает...
слова
после слов EXPORT
от LedAll><
до LedAll просят на входе n - кол-во повторений, m - пауза между миганиями, LedAll>< ( n m -- )
User avatar
AlikasS
 
Posts: 1437
Joined: Wed, 28 Jun 2006, 05:39
Location: Khabarovsk

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Sat, 13 Jun 2009, 17:45

Заем же было объединять старое и новое решение?
Code: Select all
: LedNumOn KEYBOARD_NUM_LOCK_ON LedOn  ;
: LedNumOff KEYBOARD_NUM_LOCK_ON LedOff  ;

: LedCapsOn KEYBOARD_CAPS_LOCK_ON LedOn  ;
: LedCapsOff KEYBOARD_CAPS_LOCK_ON LedOff  ;

: LedScrollOn KEYBOARD_SCROLL_LOCK_ON LedOn  ;
: LedScrollOff KEYBOARD_SCROLL_LOCK_ON LedOff  ;

Я же специально упростил все:
Code: Select all
Num LedOn
Caps LedOff
Scroll LedOn?
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56

Re: Управление индикаторами клавиатуры

Postby AlikasS » Sat, 13 Jun 2009, 17:56

а зачем значение CONSTANT присваивать VALUE , смысл?
проще уж просто переименовать
User avatar
AlikasS
 
Posts: 1437
Joined: Wed, 28 Jun 2006, 05:39
Location: Khabarovsk

Re: Управление индикаторами клавиатуры

Postby VoidVolker » Sat, 13 Jun 2009, 20:57

AlikasS wrote:а зачем значение CONSTANT присваивать VALUE , смысл?
проще уж просто переименовать

:roll: Это я как-то забыл подправить... Исправил.
95% вопросов уже обсуждались на форуме или ответы на них есть в мануале.        nnCron 1.93 b15.exe
Как правильно задавать вопросы.
User avatar
VoidVolker
Site Admin
 
Posts: 2898
Joined: Tue, 25 Apr 2006, 17:56


Return to nnCron forum (Russian)

Who is online

Users browsing this forum: Google [Bot], Yahoo [Bot] and 2 guests

cron