2013-04-04 06:16:03 +00:00
/*
Copyright 2013 Jun Wako < wakojun @ gmail . com >
This program is free software : you can redistribute it and / or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation , either version 2 of the License , or
( at your option ) any later version .
This program is distributed in the hope that it will be useful ,
but WITHOUT ANY WARRANTY ; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
GNU General Public License for more details .
You should have received a copy of the GNU General Public License
along with this program . If not , see < http : //www.gnu.org/licenses/>.
*/
# ifndef ACTION_CODE_H
# define ACTION_CODE_H
/* Action codes
* = = = = = = = = = = = =
* 16 bit code : action_kind ( 4 bit ) + action_parameter ( 12 bit )
*
*
* Key Actions ( 00 xx )
* - - - - - - - - - - - - - - - - -
* ACT_MODS ( 000 r ) :
* 000 r | 0000 | 0000 0000 No action code
* 000 r | 0000 | 0000 0001 Transparent code
* 000 r | 0000 | keycode Key
* 000 r | mods | 0000 0000 Modifiers
* 000 r | mods | keycode Key and Modifiers
* r : Left / Right flag ( Left : 0 , Right : 1 )
*
* ACT_MODS_TAP ( 001 r ) :
* 0010 | mods | 0000 0000 Modifiers with OneShot
* 0010 | mods | 0000 00 xx ( reserved )
* 0010 | mods | keycode Modifiers with Tap Key
*
*
* Other Keys ( 01 xx )
* - - - - - - - - - - - - - - - -
2013-04-04 16:39:17 +00:00
* ACT_USAGE ( 0100 ) : TODO : Not needed ?
2013-04-04 06:16:03 +00:00
* 0100 | 00 | usage ( 10 ) System control ( 0x80 ) - General Desktop page ( 0x01 )
* 0100 | 01 | usage ( 10 ) Consumer control ( 0x01 ) - Consumer page ( 0x0C )
* 0100 | 10 | usage ( 10 ) ( reserved )
* 0100 | 11 | usage ( 10 ) ( reserved )
*
* ACT_MOUSEKEY ( 0110 ) : TODO : Not needed ?
* 0101 | xxxx | keycode Mouse key
*
* 011 x | xxxx xxxx xxxx ( reseved )
*
*
* Layer Actions ( 10 xx )
* - - - - - - - - - - - - - - - - - - -
* ACT_LAYER ( 1000 ) :
* 1000 | oo00 | pppE BBBB Default Layer Bitwise operation
* oo : operation ( 00 : AND , 01 : OR , 10 : XOR , 11 : SET )
* ppp : 4 - bit chunk part ( 0 - 7 )
* EBBBB : bits and extra bit
* 1000 | ooee | pppE BBBB Layer Bitwise Operation
* oo : operation ( 00 : AND , 01 : OR , 10 : XOR , 11 : SET )
* ppp : 4 - bit chunk part ( 0 - 7 )
* eBBBB : bits and extra bit
* ee : on event ( 00 : default layer , 01 : press , 10 : release , 11 : both )
*
* 1001 | xxxx | xxxx xxxx ( reserved )
2013-04-04 16:39:17 +00:00
* 1001 | oopp | BBBB BBBB 8 - bit Bitwise Operation ? ? ?
2013-04-04 06:16:03 +00:00
*
* ACT_LAYER_TAP ( 101 x ) :
* 101 E | LLLL | keycode Invert with tap key
* 101 E | LLLL | 1110 xxxx Reserved ( 0xE0 - EF )
* 101 E | LLLL | 1111 0000 Invert with tap toggle ( 0xF0 )
* 101 E | LLLL | 1111 0001 On / Off
* 101 E | LLLL | 1111 0010 Off / On
* 101 E | LLLL | 1111 0011 Set / Clear
* 101 E | LLLL | 1111 xxxx Reserved ( 0xF4 - FF )
* ELLLL : layer ( 0 - 31 )
*
*
* Extensions ( 11 xx )
* - - - - - - - - - - - - - - - -
* ACT_MACRO ( 1100 ) :
* 1100 | opt | id ( 8 ) Macro play ?
* 1100 | 1111 | id ( 8 ) Macro record ?
*
* ACT_COMMAND ( 1110 ) :
* 1110 | opt | id ( 8 ) Built - in Command exec
*
* ACT_FUNCTION ( 1111 ) :
* 1111 | address ( 12 ) Function ?
* 1111 | opt | id ( 8 ) Function ?
*/
enum action_kind_id {
/* Key Actions */
ACT_MODS = 0 b0000 ,
ACT_LMODS = 0 b0000 ,
ACT_RMODS = 0 b0001 ,
ACT_MODS_TAP = 0 b0010 ,
ACT_LMODS_TAP = 0 b0010 ,
ACT_RMODS_TAP = 0 b0011 ,
/* Other Keys */
ACT_USAGE = 0 b0100 ,
ACT_MOUSEKEY = 0 b0101 ,
/* Layer Actions */
ACT_LAYER = 0 b1000 ,
ACT_LAYER_TAP = 0 b1010 ,
ACT_LAYER_TAP1 = 0 b1011 ,
/* Extensions */
ACT_MACRO = 0 b1100 ,
ACT_COMMAND = 0 b1110 ,
ACT_FUNCTION = 0 b1111
} ;
/* Action Code Struct
*
* NOTE :
* In avr - gcc bit field seems to be assigned from LSB ( bit0 ) to MSB ( bit15 ) .
* AVR looks like a little endian in avr - gcc .
* Not portable across compiler / endianness ?
*
* Byte order and bit order of 0x1234 :
* Big endian : Little endian :
* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
* FEDC BA98 7654 3210 0123 4567 89 AB CDEF
* 0001 0010 0011 0100 0010 1100 0100 1000
* 0x12 0x34 0x34 0x12
*/
typedef union {
uint16_t code ;
struct action_kind {
uint16_t param : 12 ;
uint8_t id : 4 ;
} kind ;
struct action_key {
uint8_t code : 8 ;
uint8_t mods : 4 ;
uint8_t kind : 4 ;
} key ;
struct action_layer_bitop {
uint8_t bits : 4 ;
uint8_t xbit : 1 ;
uint8_t part : 3 ;
uint8_t on : 2 ;
uint8_t op : 2 ;
uint8_t kind : 4 ;
} layer_bitop ;
struct action_layer_tap {
uint8_t code : 8 ;
uint8_t val : 5 ;
uint8_t kind : 3 ;
} layer_tap ;
struct action_usage {
uint16_t code : 10 ;
uint8_t page : 2 ;
uint8_t kind : 4 ;
} usage ;
struct action_command {
uint8_t id : 8 ;
uint8_t opt : 4 ;
uint8_t kind : 4 ;
} command ;
struct action_function {
uint8_t id : 8 ;
uint8_t opt : 4 ;
uint8_t kind : 4 ;
} func ;
} action_t ;
/* action utility */
# define ACTION_NO 0
# define ACTION_TRANSPARENT 1
# define ACTION(kind, param) ((kind)<<12 | (param))
/*
* Key Actions
*/
/* Mod bits: 43210
* bit 0 | | | | + - Control
* bit 1 | | | + - - Shift
* bit 2 | | + - - - Alt
* bit 3 | + - - - - Gui
* bit 4 + - - - - - LR flag ( Left : 0 , Right : 1 )
*/
enum mods_bit {
MOD_LCTL = 0x01 ,
MOD_LSFT = 0x02 ,
MOD_LALT = 0x04 ,
MOD_LGUI = 0x08 ,
MOD_RCTL = 0x11 ,
MOD_RSFT = 0x12 ,
MOD_RALT = 0x14 ,
MOD_RGUI = 0x18 ,
} ;
enum mods_codes {
MODS_ONESHOT = 0x00 ,
} ;
# define ACTION_KEY(key) ACTION(ACT_MODS, (key))
# define ACTION_MODS(mods) ACTION(ACT_MODS, (mods)<<8 | 0)
# define ACTION_MODS_KEY(mods, key) ACTION(ACT_MODS, (mods)<<8 | (key))
# define ACTION_MODS_TAP_KEY(mods, key) ACTION(ACT_MODS_TAP, (mods)<<8 | (key))
# define ACTION_MODS_ONESHOT(mods) ACTION(ACT_MODS_TAP, (mods)<<8 | MODS_ONESHOT)
/*
* Other Keys
*/
enum usage_pages {
PAGE_SYSTEM ,
PAGE_CONSUMER
} ;
# define ACTION_USAGE_SYSTEM(id) ACTION(ACT_USAGE, PAGE_SYSTEM<<10 | (id))
# define ACTION_USAGE_CONSUMER(id) ACTION(ACT_USAGE, PAGE_CONSUMER<<10 | (id))
# define ACTION_MOUSEKEY(key) ACTION(ACT_MOUSEKEY, key)
/*
* Layer Actions
*/
enum layer_param_on {
ON_PRESS = 1 ,
ON_RELEASE = 2 ,
ON_BOTH = 3 ,
} ;
enum layer_param_bit_op {
OP_BIT_AND = 0 ,
OP_BIT_OR = 1 ,
OP_BIT_XOR = 2 ,
OP_BIT_SET = 3 ,
} ;
enum layer_pram_tap_op {
OP_TAP_TOGGLE = 0xF0 ,
OP_ON_OFF ,
OP_OFF_ON ,
OP_SET_CLEAR ,
} ;
# define ACTION_LAYER_BITOP(op, part, bits, on) (ACT_LAYER<<12 | (op)<<10 | (on)<<8 | (part)<<5 | ((bits)&0x1f))
# define ACTION_LAYER_TAP(layer, key) (ACT_LAYER_TAP<<12 | (layer)<<8 | (key))
2013-04-04 16:39:17 +00:00
/* Default Layer */
# define ACTION_DEFAULT_LAYER_SET(layer) ACTION_DEFAULT_LAYER_BIT_SET((layer) / 4, 1<<((layer)%4))
2013-04-04 06:16:03 +00:00
/* Layer Operation */
2013-04-04 16:39:17 +00:00
# define ACTION_LAYER_CLEAR(on) ACTION_LAYER_BIT_AND(0, 0, (on))
2013-04-04 06:16:03 +00:00
# define ACTION_LAYER_MOMENTARY(layer) ACTION_LAYER_ON_OFF(layer)
# define ACTION_LAYER_TOGGLE(layer) ACTION_LAYER_INVERT(layer, ON_RELEASE)
# define ACTION_LAYER_INVERT(layer, on) ACTION_LAYER_BIT_XOR((layer) / 4, 1<<((layer)%4), (on))
# define ACTION_LAYER_ON(layer, on) ACTION_LAYER_BIT_OR( (layer) / 4, 1<<((layer)%4), (on))
# define ACTION_LAYER_OFF(layer, on) ACTION_LAYER_BIT_AND((layer) / 4, ~(1<<((layer)%4)), (on))
# define ACTION_LAYER_SET(layer, on) ACTION_LAYER_BIT_SET((layer) / 4, 1<<((layer)%4), (on))
# define ACTION_LAYER_ON_OFF(layer) ACTION_LAYER_TAP((layer), OP_ON_OFF)
# define ACTION_LAYER_OFF_ON(layer) ACTION_LAYER_TAP((layer), OP_OFF_ON)
# define ACTION_LAYER_SET_CLEAR(layer) ACTION_LAYER_TAP((layer), OP_SET_CLEAR)
2013-04-04 16:39:17 +00:00
/* With Tapping */
# define ACTION_LAYER_TAP_KEY(layer, key) ACTION_LAYER_TAP((layer), (key))
# define ACTION_LAYER_TAP_TOGGLE(layer) ACTION_LAYER_TAP((layer), OP_TAP_TOGGLE)
2013-04-04 06:16:03 +00:00
/* Bitwise Operation */
# define ACTION_LAYER_BIT_AND(part, bits, on) ACTION_LAYER_BITOP(OP_BIT_AND, (part), (bits), (on))
# define ACTION_LAYER_BIT_OR( part, bits, on) ACTION_LAYER_BITOP(OP_BIT_OR, (part), (bits), (on))
# define ACTION_LAYER_BIT_XOR(part, bits, on) ACTION_LAYER_BITOP(OP_BIT_XOR, (part), (bits), (on))
# define ACTION_LAYER_BIT_SET(part, bits, on) ACTION_LAYER_BITOP(OP_BIT_SET, (part), (bits), (on))
/* Default Layer Bitwise Operation */
# define ACTION_DEFAULT_LAYER_BIT_AND(part, bits) ACTION_LAYER_BITOP(OP_BIT_AND, (part), (bits), 0)
# define ACTION_DEFAULT_LAYER_BIT_OR( part, bits) ACTION_LAYER_BITOP(OP_BIT_OR, (part), (bits), 0)
# define ACTION_DEFAULT_LAYER_BIT_XOR(part, bits) ACTION_LAYER_BITOP(OP_BIT_XOR, (part), (bits), 0)
# define ACTION_DEFAULT_LAYER_BIT_SET(part, bits) ACTION_LAYER_BITOP(OP_BIT_SET, (part), (bits), 0)
/*
* Extensions
*/
/* Macro */
# define ACTION_MACRO(id) ACTION(ACT_MACRO, (id))
# define ACTION_MACRO_TAP(id) ACTION(ACT_MACRO, FUNC_TAP<<8 | (id))
# define ACTION_MACRO_OPT(id, opt) ACTION(ACT_MACRO, (opt)<<8 | (id))
/* Command */
# define ACTION_COMMAND(id, opt) ACTION(ACT_COMMAND, (opt)<<8 | (addr))
/* Function */
enum function_opts {
FUNC_TAP = 0x8 , /* indciates function is tappable */
} ;
# define ACTION_FUNCTION(id) ACTION(ACT_FUNCTION, (id))
# define ACTION_FUNCTION_TAP(id) ACTION(ACT_FUNCTION, FUNC_TAP<<8 | (id))
# define ACTION_FUNCTION_OPT(id, opt) ACTION(ACT_FUNCTION, (opt)<<8 | (id))
# endif /* ACTION_CODE_H */