Recognise SGR-style mouse encoding
This commit is contained in:
		
							parent
							
								
									ff99b29b96
								
							
						
					
					
						commit
						60b4bfaf72
					
				
							
								
								
									
										33
									
								
								driver-csi.c
									
									
									
									
									
								
							
							
						
						
									
										33
									
								
								driver-csi.c
									
									
									
									
									
								
							| @ -203,9 +203,16 @@ static TermKeyResult peekkey_csi(TermKey *tk, TermKeyCsi *csi, size_t introlen, | |||||||
|   long arg[16]; |   long arg[16]; | ||||||
|   char present = 0; |   char present = 0; | ||||||
|   int args = 0; |   int args = 0; | ||||||
|  |   int initial = 0; | ||||||
| 
 | 
 | ||||||
|   size_t p = introlen; |   size_t p = introlen; | ||||||
| 
 | 
 | ||||||
|  |   // See if there is an initial byte
 | ||||||
|  |   if(CHARAT(p) >= '<' && CHARAT(p) <= '?') { | ||||||
|  |     initial = CHARAT(p); | ||||||
|  |     p++; | ||||||
|  |   } | ||||||
|  | 
 | ||||||
|   // Now attempt to parse out up number;number;... separated values
 |   // Now attempt to parse out up number;number;... separated values
 | ||||||
|   while(p < csi_end) { |   while(p < csi_end) { | ||||||
|     unsigned char c = CHARAT(p); |     unsigned char c = CHARAT(p); | ||||||
| @ -272,10 +279,10 @@ static TermKeyResult peekkey_csi(TermKey *tk, TermKeyCsi *csi, size_t introlen, | |||||||
|     (*tk->method.emit_codepoint)(tk, arg[0], key); |     (*tk->method.emit_codepoint)(tk, arg[0], key); | ||||||
|     key->modifiers |= mod; |     key->modifiers |= mod; | ||||||
|   } |   } | ||||||
|   else if(cmd == 'M') { |   else if(cmd == 'M' || (initial == '<' && cmd == 'm')) { | ||||||
|     size_t csi_len = csi_end + 1; |     size_t csi_len = csi_end + 1; | ||||||
| 
 | 
 | ||||||
|     if(args >= 3) { |     if(!initial && args >= 3) { // rxvt protocol
 | ||||||
|       key->code.mouse[0] = arg[0]; |       key->code.mouse[0] = arg[0]; | ||||||
| 
 | 
 | ||||||
|       key->modifiers     = (key->code.mouse[0] & 0x1c) >> 2; |       key->modifiers     = (key->code.mouse[0] & 0x1c) >> 2; | ||||||
| @ -295,6 +302,28 @@ static TermKeyResult peekkey_csi(TermKey *tk, TermKeyCsi *csi, size_t introlen, | |||||||
|       return TERMKEY_RES_KEY; |       return TERMKEY_RES_KEY; | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|  |     if(initial == '<' && args >= 3) { // SGR protocol
 | ||||||
|  |       key->code.mouse[0] = arg[0]; | ||||||
|  | 
 | ||||||
|  |       key->modifiers     = (key->code.mouse[0] & 0x1c) >> 2; | ||||||
|  |       key->code.mouse[0] &= ~0x1c; | ||||||
|  | 
 | ||||||
|  |       if(arg[1] > 0xff) | ||||||
|  |         key->code.mouse[1] = 0xff; | ||||||
|  |       else | ||||||
|  |         key->code.mouse[1] = arg[1]; | ||||||
|  | 
 | ||||||
|  |       if(arg[2] > 0xff) | ||||||
|  |         key->code.mouse[2] = 0xff; | ||||||
|  |       else | ||||||
|  |         key->code.mouse[2] = arg[2]; | ||||||
|  | 
 | ||||||
|  |       key->code.mouse[3] = (cmd == 'm'); | ||||||
|  | 
 | ||||||
|  |       *nbytep = csi_len; | ||||||
|  |       return TERMKEY_RES_KEY; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     tk->buffstart += csi_len; |     tk->buffstart += csi_len; | ||||||
|     tk->buffcount -= csi_len; |     tk->buffcount -= csi_len; | ||||||
| 
 | 
 | ||||||
|  | |||||||
							
								
								
									
										27
									
								
								t/30mouse.c
									
									
									
									
									
								
							
							
						
						
									
										27
									
								
								t/30mouse.c
									
									
									
									
									
								
							| @ -10,7 +10,7 @@ int main(int argc, char *argv[]) | |||||||
|   char       buffer[32]; |   char       buffer[32]; | ||||||
|   size_t     len; |   size_t     len; | ||||||
| 
 | 
 | ||||||
|   plan_tests(46); |   plan_tests(58); | ||||||
| 
 | 
 | ||||||
|   /* vt100 doesn't have a mouse, we need xterm */ |   /* vt100 doesn't have a mouse, we need xterm */ | ||||||
|   tk = termkey_new_abstract("xterm", 0); |   tk = termkey_new_abstract("xterm", 0); | ||||||
| @ -101,6 +101,31 @@ int main(int argc, char *argv[]) | |||||||
|   is_int(col,    20,                  "mouse column for release rxvt protocol"); |   is_int(col,    20,                  "mouse column for release rxvt protocol"); | ||||||
|   is_int(key.modifiers, 0,            "modifiers for release rxvt protocol"); |   is_int(key.modifiers, 0,            "modifiers for release rxvt protocol"); | ||||||
| 
 | 
 | ||||||
|  |   // SGR protocol
 | ||||||
|  |   termkey_push_bytes(tk, "\e[<0;30;30M", 11); | ||||||
|  | 
 | ||||||
|  |   is_int(termkey_getkey(tk, &key), TERMKEY_RES_KEY, "getkey yields RES_KEY for mouse press SGR encoding"); | ||||||
|  | 
 | ||||||
|  |   is_int(key.type, TERMKEY_TYPE_MOUSE, "key.type for mouse press SGR encoding"); | ||||||
|  | 
 | ||||||
|  |   is_int(termkey_interpret_mouse(tk, &key, &ev, &button, &line, &col), TERMKEY_RES_KEY, "interpret_mouse yields RES_KEY"); | ||||||
|  | 
 | ||||||
|  |   is_int(ev,     TERMKEY_MOUSE_PRESS, "mouse event for press SGR"); | ||||||
|  |   is_int(button, 1,                   "mouse button for press SGR"); | ||||||
|  |   is_int(line,   30,                  "mouse line for press SGR"); | ||||||
|  |   is_int(col,    30,                  "mouse column for press SGR"); | ||||||
|  |   is_int(key.modifiers, 0,            "modifiers for press SGR"); | ||||||
|  | 
 | ||||||
|  |   termkey_push_bytes(tk, "\e[<0;30;30m", 11); | ||||||
|  | 
 | ||||||
|  |   is_int(termkey_getkey(tk, &key), TERMKEY_RES_KEY, "getkey yields RES_KEY for mouse release SGR encoding"); | ||||||
|  | 
 | ||||||
|  |   is_int(key.type, TERMKEY_TYPE_MOUSE, "key.type for mouse release SGR encoding"); | ||||||
|  | 
 | ||||||
|  |   is_int(termkey_interpret_mouse(tk, &key, &ev, &button, &line, &col), TERMKEY_RES_KEY, "interpret_mouse yields RES_KEY"); | ||||||
|  | 
 | ||||||
|  |   is_int(ev,     TERMKEY_MOUSE_RELEASE, "mouse event for release SGR"); | ||||||
|  | 
 | ||||||
|   termkey_destroy(tk); |   termkey_destroy(tk); | ||||||
| 
 | 
 | ||||||
|   return exit_status(); |   return exit_status(); | ||||||
|  | |||||||
| @ -894,6 +894,7 @@ static TermKeyResult peekkey_mouse(TermKey *tk, TermKeyKey *key, size_t *nbytep) | |||||||
|   key->code.mouse[0] = CHARAT(0) - 0x20; |   key->code.mouse[0] = CHARAT(0) - 0x20; | ||||||
|   key->code.mouse[1] = CHARAT(1) - 0x20; |   key->code.mouse[1] = CHARAT(1) - 0x20; | ||||||
|   key->code.mouse[2] = CHARAT(2) - 0x20; |   key->code.mouse[2] = CHARAT(2) - 0x20; | ||||||
|  |   key->code.mouse[3] = 0; | ||||||
| 
 | 
 | ||||||
|   key->modifiers     = (key->code.mouse[0] & 0x1c) >> 2; |   key->modifiers     = (key->code.mouse[0] & 0x1c) >> 2; | ||||||
|   key->code.mouse[0] &= ~0x1c; |   key->code.mouse[0] &= ~0x1c; | ||||||
| @ -953,6 +954,9 @@ TermKeyResult termkey_interpret_mouse(TermKey *tk, const TermKeyKey *key, TermKe | |||||||
|   if(button) |   if(button) | ||||||
|     *button = btn; |     *button = btn; | ||||||
| 
 | 
 | ||||||
|  |   if(key->code.mouse[3]) | ||||||
|  |     *event = TERMKEY_MOUSE_RELEASE; | ||||||
|  | 
 | ||||||
|   return TERMKEY_RES_KEY; |   return TERMKEY_RES_KEY; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | |||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user