--- /dev/null
+#include <utf.h>
+#include <x11.h>
+#include <edit.h>
+#include <win.h>
+#include "config.h"
+
+#define PRESSED(mods, btn) \
+ ((mods & (1 << (btn + 7))) == (1 << (btn + 7)))
+
+static int ExecRequest = 0;
+
+static int mouse_left(bool pressed) {
+ static int count = 0;
+ static Time before = 0;
+ if (!pressed) return MouseActNone;
+ count = ((X.now - before) <= (uint64_t)ClickTime ? count+1 : 1);
+ before = X.now;
+ if (PRESSED(X.mods, MouseRight)) {
+ return MouseActNone;
+ } else if (PRESSED(X.mods, MouseMiddle)) {
+ ExecRequest = 0;
+ return MouseActExecArg;
+ } else if (count == 1) {
+ return MouseActSel;
+ } else if (count == 2) {
+ return MouseActSelCtx;
+ } else if (count == 3) {
+ return MouseActSelWord;
+ } else {
+ return MouseActNone;
+ }
+}
+
+static int mouse_middle(bool pressed) {
+ if (pressed) { ExecRequest = 1; return MouseActNone; }
+ if (PRESSED(X.mods, MouseLeft)) {
+ return MouseActCut;
+ } else if (ExecRequest) {
+ return MouseActExec;
+ } else {
+ return MouseActNone;
+ }
+}
+
+static int mouse_right(bool pressed) {
+ if (pressed) return MouseActNone;
+ if (PRESSED(X.mods, MouseLeft)) {
+ return MouseActPaste;
+ } else {
+ return MouseActFetch;
+ }
+}
+
+int process_mouse(int btn, bool pressed) {
+ switch(btn) {
+ case MouseLeft: return mouse_left(pressed);
+ case MouseMiddle: return mouse_middle(pressed);
+ case MouseRight: return mouse_right(pressed);
+ case MouseWheelUp: return (pressed ? MouseActScrollUp : MouseActNone);
+ case MouseWheelDn: return (pressed ? MouseActScrollDn : MouseActNone);
+ }
+ return MouseActNone;
+}
static bool SyncMouse = false;
static int SearchDir = DOWN;
static char* SearchTerm = NULL;
-static int ExecRequest = 0;
#define PRESSED(mods, btn) \
((mods & (1 << (btn + 7))) == (1 << (btn + 7)))
}
}
-static void mouse_left(WinRegion id, bool pressed, size_t row, size_t col) {
- static int count = 0;
- static Time before = 0;
- if (!pressed) return;
- count = ((X.now - before) <= (uint64_t)ClickTime ? count+1 : 1);
- before = X.now;
- if (PRESSED(X.mods, MouseRight)) {
- puts("fetch tag");
- } else if (PRESSED(X.mods, MouseMiddle)) {
- /* if we didnt get an arg, find one in the selection */
- char* arg = NULL;
- if (!arg || !*arg) arg = view_getstr(win_view(EDIT));
- if (!arg || !*arg) arg = view_getstr(win_view(TAGS));
- char* str = view_fetch(win_view(id), row, col, riscmd);
- if (str) exec(str, arg);
- free(str);
- free(arg);
- ExecRequest = 0;
- } else {
- if (count == 1)
- view_setcursor(win_view(id), row, col, win_keymodsset(ModShift));
- else if (count == 2)
- view_select(win_view(id), row, col);
- else if (count == 3)
- view_selword(win_view(id), row, col);
- }
-}
-
-static void mouse_middle(WinRegion id, bool pressed, size_t row, size_t col) {
- if (pressed) { ExecRequest = 1; return; }
- if (PRESSED(X.mods, MouseLeft)) {
- cut(NULL);
- } else if (ExecRequest) {
- char* str = view_fetch(win_view(id), row, col, riscmd);
- if (str) exec(str, NULL);
- free(str);
- }
-}
-
-static void mouse_right(WinRegion id, bool pressed, size_t row, size_t col) {
- if (pressed) return;
- if (PRESSED(X.mods, MouseLeft)) {
- paste(NULL);
- } else {
- FetchCmd[2] = view_fetch(win_view(id), row, col, risfile);
- if (job_run(FetchCmd) != 0) {
- SearchDir *= (win_keymodsset(ModShift) ? -1 : +1);
- free(SearchTerm);
- SearchTerm = view_fetch(win_view(id), row, col, risfile);
- view_findstr(win_view(EDIT), SearchDir, SearchTerm);
- SyncMouse = true;
- }
- free(FetchCmd[2]);
- }
-}
-
-static void mouse_scroll(WinRegion id, bool pressed, int amount) {
- if (!pressed)
- view_scroll(win_view(id), amount);
-}
-
-static void mouse_click(int btn, bool pressed, int x, int y) {
- size_t row, col;
- Focused = (y <= Divider ? TAGS : EDIT);
- get_position(Focused, x, y, &row, &col);
- switch(btn) {
- case MouseLeft: mouse_left(Focused, pressed, row, col); break;
- case MouseMiddle: mouse_middle(Focused, pressed, row, col); break;
- case MouseRight: mouse_right(Focused, pressed, row, col); break;
- case MouseWheelUp: mouse_scroll(Focused, pressed, -ScrollBy); break;
- case MouseWheelDn: mouse_scroll(Focused, pressed, +ScrollBy); break;
- }
-}
-
size_t glyph_width(View* view, int c) {
FcChar32 rune = (FcChar32)c;
XGlyphInfo extents;
view_insert(win_view(FOCUSED), key);
}
-static void xbtnpress(XConf* x, XEvent* e) {
- (void)x;
- mouse_click(e->xbutton.button, true, e->xbutton.x, e->xbutton.y);
-}
-
-static void xbtnrelease(XConf* x, XEvent* e) {
+static void xmousebtn(XConf* x, XEvent* e) {
(void)x;
- mouse_click(e->xbutton.button, false, e->xbutton.x, e->xbutton.y);
+ size_t row, col;
+ Focused = (e->xbutton.y <= Divider ? TAGS : EDIT);
+ get_position(Focused, e->xbutton.x, e->xbutton.y, &row, &col);
+ switch (process_mouse(e->xbutton.button, (e->type == ButtonPress))) {
+ case MouseActNone:
+ break;
+ case MouseActSel:
+ view_setcursor(win_view(Focused), row, col, win_keymodsset(ModShift));
+ break;
+ case MouseActSelCtx:
+ view_select(win_view(Focused), row, col);
+ break;
+ case MouseActSelWord:
+ view_selword(win_view(Focused), row, col);
+ break;
+ case MouseActCut:
+ cut(NULL);
+ break;
+ case MouseActPaste:
+ paste(NULL);
+ break;
+ case MouseActExec: {
+ char* str = view_fetch(win_view(Focused), row, col, riscmd);
+ if (str) exec(str, NULL);
+ free(str);
+ break;
+ }
+ case MouseActExecArg: {
+ /* if we didnt get an arg, find one in the selection */
+ char* arg = NULL;
+ if (!arg || !*arg) arg = view_getstr(win_view(EDIT));
+ if (!arg || !*arg) arg = view_getstr(win_view(TAGS));
+ char* str = view_fetch(win_view(Focused), row, col, riscmd);
+ if (str) exec(str, arg);
+ free(str);
+ free(arg);
+ break;
+ }
+ case MouseActFetch: {
+ FetchCmd[2] = view_fetch(win_view(Focused), row, col, risfile);
+ if (job_run(FetchCmd) != 0) {
+ SearchDir *= (win_keymodsset(ModShift) ? -1 : +1);
+ free(SearchTerm);
+ SearchTerm = view_fetch(win_view(Focused), row, col, risfile);
+ view_findstr(win_view(EDIT), SearchDir, SearchTerm);
+ SyncMouse = true;
+ }
+ free(FetchCmd[2]);
+ break;
+ }
+ case MouseActScrollUp:
+ view_scroll(win_view(Focused), -ScrollBy);
+ break;
+ case MouseActScrollDn:
+ view_scroll(win_view(Focused), +ScrollBy);
+ break;
+ }
}
static void xbtnmotion(XConf* x, XEvent* e) {
}
static void xupdate(Job* job) {
- /* redraw if we have changes */
- if (!x11_process_events(&X, xredraw) && job) return;
+ /* redraw if we have changes or if we have input from a job */
+ if (!x11_process_events(&X, xredraw) && !job)
+ xredraw(&X);
}
void win_init(void) {
#endif
/* register event handlers */
X.eventfns[KeyPress] = xkeypress;
- X.eventfns[ButtonPress] = xbtnpress;
- X.eventfns[ButtonRelease] = xbtnrelease;
+ X.eventfns[ButtonPress] = xmousebtn;
+ X.eventfns[ButtonRelease] = xmousebtn;
X.eventfns[MotionNotify] = xbtnmotion;
X.eventfns[ClientMessage] = xclientmsg;
}
}
}
-/* Keyboard Editing Handlers
- ******************************************************************************/
-
/* Keyboard and Tag Handlers
******************************************************************************/
static void change_focus(char* arg) {