@ -114,8 +114,9 @@ unpop_keypress(ncinputlayer* nc, int kpress){
// we assumed escapes can only be composed of 7-bit chars
// we assumed escapes can only be composed of 7-bit chars
typedef struct esctrie {
typedef struct esctrie {
uint32_t special ; // composed key terminating here
struct esctrie * * trie ; // if non-NULL, next level of radix-128 trie
struct esctrie * * trie ; // if non-NULL, next level of radix-128 trie
uint32_t special ; // composed key terminating here
bool shift , ctrl , alt ;
} esctrie ;
} esctrie ;
static esctrie *
static esctrie *
@ -124,6 +125,9 @@ create_esctrie_node(int special){
if ( e ) {
if ( e ) {
e - > special = special ;
e - > special = special ;
e - > trie = NULL ;
e - > trie = NULL ;
e - > shift = 0 ;
e - > ctrl = 0 ;
e - > alt = 0 ;
}
}
return e ;
return e ;
}
}
@ -145,14 +149,12 @@ input_free_esctrie(esctrie** eptr){
}
}
}
}
// multiple input escapes might map to the same input
static int
static int
ncinputlayer_add_input_escape ( ncinputlayer * nc , const char * esc , uint32_t special ) {
ncinputlayer_add_input_escape ( ncinputlayer * nc , const char * esc , uint32_t special ,
unsigned shift , unsigned ctrl , unsigned alt ) {
if ( esc [ 0 ] ! = NCKEY_ESC | | strlen ( esc ) < 2 ) { // assume ESC prefix + content
if ( esc [ 0 ] ! = NCKEY_ESC | | strlen ( esc ) < 2 ) { // assume ESC prefix + content
logerror ( " Not an escape: %s (0x%x) \n " , esc , special ) ;
logerror ( " not an escape: %s (0x%x) \n " , esc , special ) ;
return - 1 ;
}
if ( ! nckey_supppuab_p ( special ) & & special ! = NCKEY_CSI ) {
logerror ( " Not a supplementary-b PUA char: %u (0x%x) \n " , special , special ) ;
return - 1 ;
return - 1 ;
}
}
esctrie * * cur = & nc - > inputescapes ;
esctrie * * cur = & nc - > inputescapes ;
@ -182,9 +184,12 @@ ncinputlayer_add_input_escape(ncinputlayer* nc, const char* esc, uint32_t specia
// it appears that multiple keys can be mapped to the same escape string. as
// it appears that multiple keys can be mapped to the same escape string. as
// an example, see "kend" and "kc1" in st ("simple term" from suckless) :/.
// an example, see "kend" and "kc1" in st ("simple term" from suckless) :/.
if ( ( * cur ) - > special ! = NCKEY_INVALID ) { // already had one here!
if ( ( * cur ) - > special ! = NCKEY_INVALID ) { // already had one here!
logwarn ( " Warning: already added escape (got 0x%x, wanted 0x%x)\n " , ( * cur ) - > special , special ) ;
logwarn ( " already added escape (got 0x%x, wanted 0x%x)\n " , ( * cur ) - > special , special ) ;
} else {
} else {
( * cur ) - > special = special ;
( * cur ) - > special = special ;
( * cur ) - > shift = shift ;
( * cur ) - > ctrl = ctrl ;
( * cur ) - > alt = alt ;
}
}
return 0 ;
return 0 ;
}
}
@ -356,6 +361,9 @@ handle_getc(ncinputlayer* nc, int kpress, ncinput* ni, int leftmargin, int topma
logtrace ( " move to %p (%u) \n " , esc , esc ? esc - > special : 0 ) ;
logtrace ( " move to %p (%u) \n " , esc , esc ? esc - > special : 0 ) ;
}
}
if ( esc & & esc - > special ! = NCKEY_INVALID ) {
if ( esc & & esc - > special ! = NCKEY_INVALID ) {
ni - > shift = esc - > shift ;
ni - > ctrl = esc - > ctrl ;
ni - > alt = esc - > alt ;
return esc - > special ;
return esc - > special ;
}
}
if ( csi ) {
if ( csi ) {
@ -633,7 +641,9 @@ prep_special_keys(ncinputlayer* nc){
static const struct {
static const struct {
const char * tinfo ;
const char * tinfo ;
uint32_t key ;
uint32_t key ;
bool shift , ctrl , alt ;
} keys [ ] = {
} keys [ ] = {
{ . tinfo = " kcbt " , . key = ' \t ' , . shift = true , } ,
{ . tinfo = " kcub1 " , . key = NCKEY_LEFT , } ,
{ . tinfo = " kcub1 " , . key = NCKEY_LEFT , } ,
{ . tinfo = " kcuf1 " , . key = NCKEY_RIGHT , } ,
{ . tinfo = " kcuf1 " , . key = NCKEY_RIGHT , } ,
{ . tinfo = " kcuu1 " , . key = NCKEY_UP , } ,
{ . tinfo = " kcuu1 " , . key = NCKEY_UP , } ,
@ -720,84 +730,66 @@ prep_special_keys(ncinputlayer* nc){
{ . tinfo = " kext " , . key = NCKEY_EXIT , } ,
{ . tinfo = " kext " , . key = NCKEY_EXIT , } ,
{ . tinfo = " kprt " , . key = NCKEY_PRINT , } ,
{ . tinfo = " kprt " , . key = NCKEY_PRINT , } ,
{ . tinfo = " krfr " , . key = NCKEY_REFRESH , } ,
{ . tinfo = " krfr " , . key = NCKEY_REFRESH , } ,
{ . tinfo = " kDC " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDC " , . key = NCKEY_DEL , . shift = 1 , } ,
{ . tinfo = " kDC1 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDC3 " , . key = NCKEY_DEL , . alt = 1 , } ,
{ . tinfo = " kDC2 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDC4 " , . key = NCKEY_DEL , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kDC3 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDC5 " , . key = NCKEY_DEL , . ctrl = 1 , } ,
{ . tinfo = " kDC4 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDC6 " , . key = NCKEY_DEL , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kDC5 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDC7 " , . key = NCKEY_DEL , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kDC6 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDN " , . key = NCKEY_DOWN , . shift = 1 , } ,
{ . tinfo = " kDC7 " , . key = NCKEY_DEL , } , // FIXME plus modifier
{ . tinfo = " kDN3 " , . key = NCKEY_DOWN , . alt = 1 , } ,
{ . tinfo = " kDN " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kDN4 " , . key = NCKEY_DOWN , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kDN1 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kDN5 " , . key = NCKEY_DOWN , . ctrl = 1 , } ,
{ . tinfo = " kDN2 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kDN6 " , . key = NCKEY_DOWN , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kDN3 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kDN7 " , . key = NCKEY_DOWN , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kDN4 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kEND " , . key = NCKEY_END , . shift = 1 , } ,
{ . tinfo = " kDN5 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kEND3 " , . key = NCKEY_END , . alt = 1 , } ,
{ . tinfo = " kDN6 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kEND4 " , . key = NCKEY_END , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kDN7 " , . key = NCKEY_DOWN , } , // FIXME plus modifier
{ . tinfo = " kEND5 " , . key = NCKEY_END , . ctrl = 1 , } ,
{ . tinfo = " kEND " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kEND6 " , . key = NCKEY_END , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kEND1 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kEND7 " , . key = NCKEY_END , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kEND2 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kHOM " , . key = NCKEY_HOME , . shift = 1 , } ,
{ . tinfo = " kEND3 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kHOM3 " , . key = NCKEY_HOME , . alt = 1 , } ,
{ . tinfo = " kEND4 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kHOM4 " , . key = NCKEY_HOME , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kEND5 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kHOM5 " , . key = NCKEY_HOME , . ctrl = 1 , } ,
{ . tinfo = " kEND6 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kHOM6 " , . key = NCKEY_HOME , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kEND7 " , . key = NCKEY_END , } , // FIXME plus modifier
{ . tinfo = " kHOM7 " , . key = NCKEY_HOME , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kHOM " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kIC " , . key = NCKEY_INS , . shift = 1 , } ,
{ . tinfo = " kHOM1 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kIC3 " , . key = NCKEY_INS , . alt = 1 , } ,
{ . tinfo = " kHOM2 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kIC4 " , . key = NCKEY_INS , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kHOM3 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kIC5 " , . key = NCKEY_INS , . ctrl = 1 , } ,
{ . tinfo = " kHOM4 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kIC6 " , . key = NCKEY_INS , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kHOM5 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kIC7 " , . key = NCKEY_INS , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kHOM6 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kLFT " , . key = NCKEY_LEFT , . shift = 1 , } ,
{ . tinfo = " kHOM7 " , . key = NCKEY_HOME , } , // FIXME plus modifier
{ . tinfo = " kLFT3 " , . key = NCKEY_LEFT , . alt = 1 , } ,
{ . tinfo = " kIC " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kLFT4 " , . key = NCKEY_LEFT , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kIC1 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kLFT5 " , . key = NCKEY_LEFT , . ctrl = 1 , } ,
{ . tinfo = " kIC2 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kLFT6 " , . key = NCKEY_LEFT , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kIC3 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kLFT7 " , . key = NCKEY_LEFT , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kIC4 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kNXT " , . key = NCKEY_PGDOWN , . shift = 1 , } ,
{ . tinfo = " kIC5 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kNXT3 " , . key = NCKEY_PGDOWN , . alt = 1 , } ,
{ . tinfo = " kIC6 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kNXT4 " , . key = NCKEY_PGDOWN , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kIC7 " , . key = NCKEY_INS , } , // FIXME plus modifier
{ . tinfo = " kNXT5 " , . key = NCKEY_PGDOWN , . ctrl = 1 , } ,
{ . tinfo = " kLFT " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kNXT6 " , . key = NCKEY_PGDOWN , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kLFT1 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kNXT7 " , . key = NCKEY_PGDOWN , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kLFT2 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kPRV " , . key = NCKEY_PGUP , . shift = 1 , } ,
{ . tinfo = " kLFT3 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kPRV3 " , . key = NCKEY_PGUP , . alt = 1 , } ,
{ . tinfo = " kLFT4 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kPRV4 " , . key = NCKEY_PGUP , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kLFT5 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kPRV5 " , . key = NCKEY_PGUP , . ctrl = 1 , } ,
{ . tinfo = " kLFT6 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kPRV6 " , . key = NCKEY_PGUP , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kLFT7 " , . key = NCKEY_LEFT , } , // FIXME plus modifier
{ . tinfo = " kPRV7 " , . key = NCKEY_PGUP , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kNXT " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kRIT " , . key = NCKEY_RIGHT , . shift = 1 , } ,
{ . tinfo = " kNXT2 " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kRIT3 " , . key = NCKEY_RIGHT , . alt = 1 , } ,
{ . tinfo = " kNXT3 " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kRIT4 " , . key = NCKEY_RIGHT , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kNXT4 " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kRIT5 " , . key = NCKEY_RIGHT , . ctrl = 1 , } ,
{ . tinfo = " kNXT5 " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kRIT6 " , . key = NCKEY_RIGHT , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kNXT6 " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kRIT7 " , . key = NCKEY_RIGHT , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kNXT7 " , . key = NCKEY_PGDOWN , } , // FIXME plus modifier
{ . tinfo = " kUP " , . key = NCKEY_UP , . shift = 1 , } ,
{ . tinfo = " kPRV " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kUP3 " , . key = NCKEY_UP , . alt = 1 , } ,
{ . tinfo = " kPRV2 " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kUP4 " , . key = NCKEY_UP , . alt = 1 , . shift = 1 , } ,
{ . tinfo = " kPRV3 " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kUP5 " , . key = NCKEY_UP , . ctrl = 1 , } ,
{ . tinfo = " kPRV4 " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kUP6 " , . key = NCKEY_UP , . ctrl = 1 , . shift = 1 , } ,
{ . tinfo = " kPRV5 " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kUP7 " , . key = NCKEY_UP , . alt = 1 , . ctrl = 1 , } ,
{ . tinfo = " kPRV6 " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kPRV7 " , . key = NCKEY_PGUP , } , // FIXME plus modifier
{ . tinfo = " kRIT " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT1 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT2 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT3 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT4 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT5 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT6 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kRIT7 " , . key = NCKEY_RIGHT , } , // FIXME plus modifier
{ . tinfo = " kUP " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP1 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP2 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP3 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP4 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP5 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP6 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = " kUP7 " , . key = NCKEY_UP , } , // FIXME plus modifier
{ . tinfo = NULL , . key = NCKEY_INVALID , }
{ . tinfo = NULL , . key = NCKEY_INVALID , }
} , * k ;
} , * k ;
for ( k = keys ; k - > tinfo ; + + k ) {
for ( k = keys ; k - > tinfo ; + + k ) {
@ -807,15 +799,15 @@ prep_special_keys(ncinputlayer* nc){
continue ;
continue ;
}
}
if ( seq [ 0 ] ! = NCKEY_ESC ) {
if ( seq [ 0 ] ! = NCKEY_ESC ) {
//fprintf(stderr, "Terminfo's %s is not an escape sequence (%zub)\n", k->tinfo, strlen(seq));
loginfo ( " %s is not an escape sequence \n " , k - > tinfo ) ;
continue ;
continue ;
}
}
logdebug ( " support for terminfo's %s: %s \n " , k - > tinfo , seq ) ;
logdebug ( " support for terminfo's %s: %s \n " , k - > tinfo , seq ) ;
if ( ncinputlayer_add_input_escape ( nc , seq , k - > key )) {
if ( ncinputlayer_add_input_escape ( nc , seq , k - > key , k - > shift , k - > ctrl , k - > alt )) {
return - 1 ;
return - 1 ;
}
}
}
}
if ( ncinputlayer_add_input_escape ( nc , CSIPREFIX , NCKEY_CSI )) {
if ( ncinputlayer_add_input_escape ( nc , CSIPREFIX , NCKEY_CSI , 0 , 0 , 0 )) {
return - 1 ;
return - 1 ;
}
}
return 0 ;
return 0 ;
@ -1688,10 +1680,10 @@ void ncinput_extract_clrs(ncinputlayer* ni){
if ( rlen > = sizeof ( ni - > inputbuf ) / sizeof ( * ni - > inputbuf ) - ni - > inputbuf_write_at ) {
if ( rlen > = sizeof ( ni - > inputbuf ) / sizeof ( * ni - > inputbuf ) - ni - > inputbuf_write_at ) {
rlen = sizeof ( ni - > inputbuf ) / sizeof ( * ni - > inputbuf ) - ni - > inputbuf_write_at ;
rlen = sizeof ( ni - > inputbuf ) / sizeof ( * ni - > inputbuf ) - ni - > inputbuf_write_at ;
}
}
logdebug ( " Reading % z u from %d\n " , rlen , ni - > infd ) ;
logdebug ( " Reading % ll u from %d\n " , rlen , ni - > infd ) ;
ssize_t r ;
ssize_t r ;
if ( ( r = read ( ni - > infd , ni - > inputbuf + ni - > inputbuf_write_at , rlen ) ) > 0 ) {
if ( ( r = read ( ni - > infd , ni - > inputbuf + ni - > inputbuf_write_at , rlen ) ) > 0 ) {
logdebug ( " Read % z u from %d\n " , r , ni - > infd ) ;
logdebug ( " Read % ll u from %d\n " , r , ni - > infd ) ;
ni - > inputbuf_write_at + = r ;
ni - > inputbuf_write_at + = r ;
if ( ni - > inputbuf_write_at = = sizeof ( ni - > inputbuf ) / sizeof ( * ni - > inputbuf ) ) {
if ( ni - > inputbuf_write_at = = sizeof ( ni - > inputbuf ) / sizeof ( * ni - > inputbuf ) ) {
ni - > inputbuf_write_at = 0 ;
ni - > inputbuf_write_at = 0 ;