/* return value is one if auto-repeating, 0 if not */ int twiddler_key(unsigned long message) { char **table = twiddler_get_table(message); char *val; /* * These two are needed to avoid transmitting single keys when typing * chords. When the number of keys being held down decreases, data * is transmitted; but as soon as it increases the cycle is restarted. */ static int last_message; static int marked; /* * The time values are needed to implement repetition of keys */ static struct timeval tv1, tv2; static int nclick, last_pressed; #define GET_TIME(tv) (gettimeofday(&tv, (struct timezone *)NULL)) #define DIF_TIME(t1,t2) ((t2.tv_sec -t1.tv_sec) *1000+ \ (t2.tv_usec-t1.tv_usec)/1000) if (!table) return 0; message &= 0xff; val = table[message]; if ((message < last_message) && !marked) { /* ok, do it */ marked++; /* don't retransmit on release */ twiddler_use_item(table[last_message]); if (last_pressed != last_message) { nclick=1; GET_TIME(tv1); } /* first click (note: this is release) */ last_pressed = last_message; } if (message < last_message) { /* marked: just ignore */ last_message = message; return 0; } /* building up a chord or repeating */ if (message != last_pressed) { /* building up */ marked=0; last_message = message; return 0; } /* Hmmm... double click */ if (message > last_message) { marked = 0; /* but don't use it */ GET_TIME(tv2); nclick = 1+ (DIF_TIME(tv1,tv2) < 300); /* if fast, counts as double */ last_message = message; if (nclick==1) GET_TIME(tv1); /* maybe the next.. */ return 1; } /* so, we are repeating... */ if (nclick == 2) { GET_TIME(tv1); /* compute delay */ if (DIF_TIME(tv2,tv1) > 500) /* held enough */ twiddler_use_item(table[message]); return 1; } return 0; }
/* * ekg_getch() * * czeka na wci¶niêcie klawisza i je¶li wkompilowano obs³ugê pythona, * przekazuje informacjê o zdarzeniu do skryptu. * * - meta - przedrostek klawisza. * * @returns: * -2 - ignore that key * ERR - error * OK - report a (wide) character * KEY_CODE_YES - report the pressing of a function key * */ static int ekg_getch(int meta, unsigned int *ch) { int retcode; #if USE_UNICODE retcode = wget_wch(input, ch); #else *ch = wgetch(input); retcode = *ch >= KEY_MIN ? KEY_CODE_YES : OK; #endif if (retcode == ERR) return ERR; if ((retcode == KEY_CODE_YES) && (*(int *)ch == -1)) return ERR; /* Esc (delay) no key */ #ifndef HAVE_USABLE_TERMINFO /* Debian screen incomplete terminfo workaround */ if (mouse_initialized == 2 && *ch == 27) { /* escape */ int tmp; if ((tmp = wgetch(input)) != '[') ungetch(tmp); else if ((tmp = wgetch(input)) != 'M') { ungetch(tmp); ungetch('['); } else *ch = KEY_MOUSE; } #endif /* * conception is borrowed from Midnight Commander project * (www.ibiblio.org/mc/) */ #define GET_TIME(tv) (g_get_current_time(&tv)) #define DIF_TIME(t1,t2) ((t2.tv_sec -t1.tv_sec) *1000+ \ (t2.tv_usec-t1.tv_usec)/1000) if (*ch == KEY_MOUSE) { int btn, mouse_state = 0, x, y; static GTimeVal tv1 = { 0, 0 }; static GTimeVal tv2; static int clicks; static int last_btn = 0; btn = wgetch (input) - 32; if (btn == 3 && last_btn) { last_btn -= 32; switch (last_btn) { case 0: mouse_state = (clicks) ? EKG_BUTTON1_DOUBLE_CLICKED : EKG_BUTTON1_CLICKED; break; case 1: mouse_state = (clicks) ? EKG_BUTTON2_DOUBLE_CLICKED : EKG_BUTTON2_CLICKED; break; case 2: mouse_state = (clicks) ? EKG_BUTTON3_DOUBLE_CLICKED : EKG_BUTTON3_CLICKED; break; case 64: mouse_state = EKG_SCROLLED_UP; break; case 65: mouse_state = EKG_SCROLLED_DOWN; break; default: break; } last_btn = 0; GET_TIME (tv1); clicks = 0; } else if (!last_btn) { GET_TIME (tv2); if (tv1.tv_sec && (DIF_TIME (tv1,tv2) < 250)){ clicks++; clicks %= 3; } else clicks = 0; switch (btn) { case 0: case 1: case 2: case 64: case 65: btn += 32; break; default: btn = 0; break; } last_btn = btn; } else { switch (btn) { case 64: mouse_state = EKG_SCROLLED_UP; break; case 65: mouse_state = EKG_SCROLLED_DOWN; break; } } /* 33 based */ x = wgetch(input) - 32; y = wgetch(input) - 32; /* XXX query_emit UI_MOUSE ??? */ if (mouse_state) ncurses_mouse_clicked_handler(x, y, mouse_state); } #undef GET_TIME #undef DIF_TIME if (query_emit(NULL, "ui-keypress", ch) == -1) return -2; /* -2 - ignore that key */ return retcode; }