aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul LeoNerd Evans <leonerd@leonerd.org.uk>2009-11-27 14:36:29 +0000
committerPaul LeoNerd Evans <leonerd@leonerd.org.uk>2009-11-27 14:36:29 +0000
commit24f97118465817c09c28103e7c94252b28fa06aa (patch)
treeb46a911ef72301f60a522d4d95be239e1ef9bc10
parent6dc2b9c72bf121aed0f9011d925b2c551a22ada2 (diff)
downloadtermo-24f97118465817c09c28103e7c94252b28fa06aa.tar.gz
termo-24f97118465817c09c28103e7c94252b28fa06aa.tar.xz
termo-24f97118465817c09c28103e7c94252b28fa06aa.zip
Return opaque mouse events in the key structure; add a function to interpret this into its component fields
-rw-r--r--termkey.c72
-rw-r--r--termkey.h.in16
-rw-r--r--termkey_getkey.3.sh14
-rw-r--r--termkey_interpret_mouse.343
4 files changed, 127 insertions, 18 deletions
diff --git a/termkey.c b/termkey.c
index 529bbf9..034a737 100644
--- a/termkey.c
+++ b/termkey.c
@@ -639,14 +639,66 @@ static TermKeyResult peekkey_mouse(TermKey *tk, TermKeyKey *key, size_t *nbytep)
return TERMKEY_RES_AGAIN;
key->type = TERMKEY_TYPE_MOUSE;
- key->code.mouse.buttons = CHARAT(0) - 0x20;
- key->code.mouse.col = CHARAT(1) - 0x20;
- key->code.mouse.line = CHARAT(2) - 0x20;
- key->modifiers = 0;
+ key->code.mouse[0] = CHARAT(0) - 0x20;
+ key->code.mouse[1] = CHARAT(1) - 0x20;
+ key->code.mouse[2] = CHARAT(2) - 0x20;
+ key->modifiers = 0;
*nbytep = 3;
return TERMKEY_RES_KEY;
}
+TermKeyResult termkey_interpret_mouse(TermKey *tk, TermKeyKey *key, TermKeyMouseEvent *event, int *button, int *line, int *col)
+{
+ if(key->type != TERMKEY_TYPE_MOUSE)
+ return TERMKEY_RES_NONE;
+
+ if(button)
+ *button = 0;
+
+ if(col)
+ *col = key->code.mouse[1];
+
+ if(line)
+ *line = key->code.mouse[2];
+
+ if(!event)
+ return TERMKEY_RES_KEY;
+
+ int btn = 0;
+
+ int code = key->code.mouse[0];
+
+ int drag = code & 0x20;
+
+ switch(code & ~0x20) {
+ case 0:
+ case 1:
+ case 2:
+ *event = drag ? TERMKEY_MOUSE_DRAG : TERMKEY_MOUSE_PRESS;
+ btn = (code & ~0x20) + 1;
+ break;
+
+ case 3:
+ *event = TERMKEY_MOUSE_RELEASE;
+ // no button hint
+ break;
+
+ case 64:
+ case 65:
+ *event = drag ? TERMKEY_MOUSE_DRAG : TERMKEY_MOUSE_PRESS;
+ btn = (code & ~0x20) + 4 - 64;
+ break;
+
+ default:
+ *event = TERMKEY_MOUSE_UNKNOWN;
+ }
+
+ if(button)
+ *button = btn;
+
+ return TERMKEY_RES_KEY;
+}
+
#ifdef DEBUG
static void print_buffer(TermKey *tk)
{
@@ -937,8 +989,16 @@ size_t termkey_snprint_key(TermKey *tk, char *buffer, size_t len, TermKeyKey *ke
l = snprintf(buffer + pos, len - pos, "F%d", key->code.number);
break;
case TERMKEY_TYPE_MOUSE:
- l = snprintf(buffer + pos, len - pos, "Mouse(0x%02x,%d,%d)",
- key->code.mouse.buttons, key->code.mouse.line, key->code.mouse.col);
+ {
+ TermKeyMouseEvent ev;
+ int button;
+ termkey_interpret_mouse(tk, key, &ev, &button, NULL, NULL);
+
+ static char *evnames[] = { "Unknown", "Press", "Drag", "Release" };
+
+ l = snprintf(buffer + pos, len - pos, "Mouse%s(%d)",
+ evnames[ev], button);
+ }
break;
}
diff --git a/termkey.h.in b/termkey.h.in
index ae11856..9ed82c5 100644
--- a/termkey.h.in
+++ b/termkey.h.in
@@ -100,6 +100,13 @@ typedef enum {
TERMKEY_RES_AGAIN,
} TermKeyResult;
+typedef enum {
+ TERMKEY_MOUSE_UNKNOWN,
+ TERMKEY_MOUSE_PRESS,
+ TERMKEY_MOUSE_DRAG,
+ TERMKEY_MOUSE_RELEASE,
+} TermKeyMouseEvent;
+
enum {
TERMKEY_KEYMOD_SHIFT = 1 << 0,
TERMKEY_KEYMOD_ALT = 1 << 1,
@@ -112,11 +119,10 @@ typedef struct {
long codepoint; // TERMKEY_TYPE_UNICODE
int number; // TERMKEY_TYPE_FUNCTION
TermKeySym sym; // TERMKEY_TYPE_KEYSYM
- struct {
- short buttons;
- short col, line;
- } mouse; // TERMKEY_TYPE_MOUSE
+ char mouse[4]; // TERMKEY_TYPE_MOUSE
+ // opaque. see termkey_interpret_mouse
} code;
+
int modifiers;
/* Any Unicode character can be UTF-8 encoded in no more than 6 bytes, plus
@@ -159,6 +165,8 @@ TermKeyResult termkey_advisereadable(TermKey *tk);
TermKeySym termkey_register_keyname(TermKey *tk, TermKeySym sym, const char *name);
const char *termkey_get_keyname(TermKey *tk, TermKeySym sym);
+TermKeyResult termkey_interpret_mouse(TermKey *tk, TermKeyKey *key, TermKeyMouseEvent *event, int *button, int *line, int *col);
+
TermKeySym termkey_keyname2sym(TermKey *tk, const char *keyname);
typedef enum {
diff --git a/termkey_getkey.3.sh b/termkey_getkey.3.sh
index b0ddc68..c4f08ee 100644
--- a/termkey_getkey.3.sh
+++ b/termkey_getkey.3.sh
@@ -40,13 +40,10 @@ The \fITermKeyKey\fP structure is defined as follows:
typedef struct {
TermKeyType type;
union {
- long codepoint; /* TERMKEY_TYPE_UNICODE */
- int number; /* TERMKEY_TYPE_FUNCTION */
- TermKeySym sym; /* TERMKEY_TYPE_KEYSYM */
- struct {
- short buttons;
- short line, col;
- } mouse; /* TERMKEY_TYPE_MOUSE */
+ long codepoint; /* TERMKEY_TYPE_UNICODE */
+ int number; /* TERMKEY_TYPE_FUNCTION */
+ TermKeySym sym; /* TERMKEY_TYPE_KEYSYM */
+ char mouse[4] /* TERMKEY_TYPE_MOUSE */
} code;
int modifiers;
char utf8[7];
@@ -66,7 +63,7 @@ a numbered function key. This value indicates that \fIcode.number\fP is valid, a
a symbolic key. This value indicates that \fIcode.sym\fP is valid, and contains the symbolic key value. This is an opaque value which may be passed to \fBtermkey_get_keyname\fP(3).
.TP
.B TERMKEY_TYPE_MOUSE
-a mouse button press, release, or movement. This value indicates that \fIcode.mouse\fP is valid. The structure will contain the button and cursor co-ordinates information from the terminal mouse event. The \fIbuttons\fP value will depend on the terminal's current mouse mode, which is beyond \fIlibtermkey\fP's control.
+a mouse button press, release, or movement. The \fIcode.mouse\fP array should be considered opaque. Use \fBtermkey_interpret_mouse\fP(3) to interpret it.
.PP
The \fImodifiers\fP bitmask is composed of a bitwise-or of the constants \fBTERMKEY_KEYMOD_SHIFT\fP, \fBTERMKEY_KEYMOD_CTRL\fP and \fBTERMKEY_KEYMOD_ALT\fP.
.PP
@@ -91,5 +88,6 @@ cat <<EOF
.BR termkey_waitkey (3),
.BR termkey_set_waittime (3),
.BR termkey_get_keyname (3),
+.BR termkey_interpret_mouse (3),
.BR termkey_snprint_key (3)
EOF
diff --git a/termkey_interpret_mouse.3 b/termkey_interpret_mouse.3
new file mode 100644
index 0000000..50f3353
--- /dev/null
+++ b/termkey_interpret_mouse.3
@@ -0,0 +1,43 @@
+.TH TERMKEY_INTERPRET_MOUSE 3
+.SH NAME
+termkey_interpret_mouse \- interpret opaque mouse event data
+.SH SYNOPSIS
+.nf
+.B #include <termkey.h>
+.sp
+.BI "TermKeyResult termkey_interpret_mouse(TermKey *" tk ", TermKeyKey *" key ", "
+.BI " TermKeyMouseEvent *" ev ", int *" button ", int *" line ", int *" col );
+.fi
+.sp
+Link with \fI-ltermkey\fP.
+.SH DESCRIPTION
+\fBtermkey_interpret_mouse\fP fills in variables in the passed pointers according to the mouse event found in \fIkey\fP. It should be called if \fBtermkey_getkey(3)\fP or similar have returned a key event with the type of \fBTERMKEY_TYPE_MOUSE\fP.
+.PP
+Any pointer may instead be given as \fBNULL\fP to not return that value.
+.PP
+The \fIev\fP variable will take one of the following values:
+.in
+.TP
+.B TERMKEY_MOUSE_UNKNOWN
+an unknown mouse event.
+.TP
+.B TERMKEY_MOUSE_PRESS
+a mouse button was pressed; \fIbutton\fP will contain its number.
+.TP
+.B TERMKEY_MOUSE_DRAG
+the mouse was moved while holding a button; \fIbutton\fP will contain its number.
+.TP
+.B TERMKEY_MOUSE_RELEASE
+a mouse button was released, or the mouse was moved while no button was pressed. If known, \fIbutton\fP will contain the number of the button released. Not all terminals can report this, so it may be 0 instead.
+.PP
+The \fIline\fP and \fIcol\fP variables will be filled in with the mouse position, indexed from 1.
+.PP
+After calling this function, it is possible that the \fImodifiers\fP field of the \fIkey\fP structure will have been set according to the modifiers reported by the terminal. This function will not otherwise alter either the \fIkey\fP or the containing \fItk\fP structure, and will be safe to call again on the same event if required.
+.SH "RETURN VALUE"
+If passed a \fIkey\fP event of the type \fBTERMKEY_TYPE_MOUSE\fP, this function will return \fBTERMKEY_RES_KEY\fP and will affect the variables whose pointers were passed in, as described above.
+.PP
+For other event types it will return \fBTERMKEY_RES_NONE\fP, and its effects on any variables whose pointers were passed in, are undefined.
+.SH "SEE ALSO"
+.BR termkey_new (3),
+.BR termkey_waitkey (3),
+.BR termkey_getkey (3),