Commits

Anonymous committed afdd84e

Basic visual mode

  • Participants
  • Parent commits dad5808

Comments (0)

Files changed (7)

File src/callback.c

 #include "entry.h"
 #include "scripts.h"
 #include "util.h"
+#include "visual.h"
 
 
 /* dwb_entry_keyrelease_cb {{{*/
         SCRIPTS_EMIT_RETURN(signal, json, true);
     }
 
-    if (e->keyval == GDK_KEY_Escape) 
+    if (mode == CARET_MODE)
+        return visual_caret(e);
+    else if (e->keyval == GDK_KEY_Escape) 
     {
         if (dwb.state.mode & COMPLETION_MODE) 
             completion_clean_completion(true);

File src/config.h

   { "win_hist_back",            {   "wh",         0,                0 }, },  
   { "win_hist_forward",         {   "wl",         0,                0 }, },  
   { "insert_mode",              {   "i",          0,                0 }, },  
+  { "visual_mode",              {   "v",          0, 0 }, }, 
   { "normal_mode",              {   "n",          GDK_CONTROL_MASK, 0 }, },  
   { "open",                     {   "o",          0,                0 }, },  
   { "open_url",                 {   "go",         0,                0 }, }, 
   { "toggle_plugins_host",      {   "ph",         0,                0 }, }, 
   { "toggle_plugins_uri_tmp",   {   "ptu",        0,                0 }, }, 
   { "toggle_plugins_host_tmp",  {   "pth",        0,                0 }, }, 
-  { "new_tab",                  {   "V",          0,                0 }, }, 
+  { "new_tab",                  {   "T",          GDK_CONTROL_MASK, 0 }, }, 
   { "new_win",                  {   "W",          0,                0 }, }, 
   { "save",                     {   "sf",         0,                0 }, }, 
   { "undo",                     {   "u",          0,                0 }, }, 
     (Func)commands_change_mode,             NULL,                              POST_SM, 
     { .n = INSERT_MODE, .b = false }, EP_NONE, { "i", "insert", NULL }, },
 
+  { { "visual_mode",           "Visual Mode",                       }, CP_COMMANDLINE | CP_HAS_MODE, 
+    (Func)commands_change_mode,             NULL,                              POST_SM, 
+    { .n = CARET_MODE, .b = false }, EP_NONE, { "visual" }, },
+
   { { "normal_mode",           "Normal Mode",                       }, CP_OVERRIDE_INSERT | CP_OVERRIDE_ENTRY | CP_OVERRIDE_ALL, 
     (Func)commands_change_mode,             NULL,                              POST_SM, 
     { .n = NORMAL_MODE, .b = true }, EP_NONE, { NULL }, },
     return STATUS_OK;
 }/*}}}*/
 
+static DwbStatus 
+dwb_caret_mode()
+{
+    dwb.state.mode = CARET_MODE;
+    dwb_set_normal_message(dwb.state.fview, false, "-- CARET --");
+    WebKitWebSettings *settings = webkit_web_view_get_settings(WEBVIEW(dwb.state.fview));
+    g_object_set(settings, "enable-caret-browsing", TRUE, NULL);
+    GdkEvent *event = gdk_event_new(GDK_BUTTON_PRESS);
+    event->button.button = 1;
+    event->button.x = 1;
+    event->button.y = 1;
+    event->button.window = g_object_ref(gtk_widget_get_window(VIEW(dwb.state.fview)->web));
+    gtk_main_do_event(event);
+    gdk_event_free(event);
+    return STATUS_OK;
+}
 /* dwb_change_mode (Mode mode, ...)   return DwbStatus {{{*/
 DwbStatus 
 dwb_change_mode(Mode mode, ...) 
             break;
         case INSERT_MODE:   ret = dwb_insert_mode(); break;
         case COMMAND_MODE:  ret = dwb_command_mode(); break;
-        case HINT_MODE:     dwb.state.mode = HINT_MODE; break;
+        case HINT_MODE:    dwb.state.mode = mode; break; 
+        case CARET_MODE:   ret = dwb_caret_mode(); break;
         default: PRINT_DEBUG("Unknown mode: %d", mode); break;
     }
     return ret;
 } BarVisibility;
 
 typedef enum {
-  NORMAL_MODE           = 1<<0,
-  INSERT_MODE           = 1<<1,
-  COMMAND_MODE          = 1<<2,
-  HINT_MODE             = 1<<3,
-  QUICK_MARK_SAVE       = 1<<4,
-  QUICK_MARK_OPEN       = 1<<5,
-  FIND_MODE             = 1<<6,
-  COMPLETION_MODE       = 1<<7,
-  AUTO_COMPLETE         = 1<<8,
-  SEARCH_FIELD_MODE     = 1<<10,
-  SETTINGS_MODE         = 1<<12,
-  KEY_MODE              = 1<<13,
-  DOWNLOAD_GET_PATH     = 1<<14,
-  SAVE_SESSION          = 1<<15,
-  COMPLETE_PATH         = 1<<16,
-  COMPLETE_BUFFER       = 1<<17,
-  COMPLETE_QUICKMARKS   = 1<<18,
-  COMPLETE_COMMAND_MODE = 1<<19,
-  CONFIRM               = 1<<21,
-  SETTINGS_MODE_LOCAL   = 1<<22,
-  COMPLETE_SCRIPTS      = 1<<23,
+  NORMAL_MODE           = 0x000001,
+  INSERT_MODE           = 0x000002,
+  COMMAND_MODE          = 0x000004,
+  HINT_MODE             = 0x000008,
+  QUICK_MARK_SAVE       = 0x000010,
+  QUICK_MARK_OPEN       = 0x000020,
+  COMPLETE_SCRIPTS      = 0x000040,
+  COMPLETION_MODE       = 0x000080,
+  AUTO_COMPLETE         = 0x000100,
+  SEARCH_FIELD_MODE     = 0x000200,
+  SETTINGS_MODE         = 0x000400,
+  KEY_MODE              = 0x000800,
+  DOWNLOAD_GET_PATH     = 0x001000,
+  SAVE_SESSION          = 0x002000,
+  COMPLETE_PATH         = 0x004000,
+  COMPLETE_BUFFER       = 0x008000,
+  COMPLETE_QUICKMARKS   = 0x010000,
+  COMPLETE_COMMAND_MODE = 0x020000,
+  CONFIRM               = 0x040000,
+  SETTINGS_MODE_LOCAL   = 0x080000,
+  FIND_MODE             = 0x100000,
+  CARET_MODE            = 0x200000,
 } Mode;
 #define BASIC_MODES(mode) ( MAX( ( (mode) & (NORMAL_MODE | INSERT_MODE | COMMAND_MODE | HINT_MODE) ), NORMAL_MODE) )
 
 view_key_ignore_cb(WebKitWebView *wv, GdkEventKey *e, GList *gl)
 {
     // passthrough none
+    if (dwb.state.mode == CARET_MODE)
+        return false;
     if (dwb.misc.passthrough == PASSTHROUGH_NONE)
         return !(dwb.state.mode & INSERT_MODE);
     // passthrough all 

File src/visual.c

+/*
+ * Copyright (c) 2013 Stefan Bolte <portix@gmx.net>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+#include "dwb.h"
+#include "js.h"
+
+static void 
+dispatch_event(guint keyval[3], guint state[3])
+{
+    GdkEvent *event = gdk_event_new(GDK_KEY_PRESS);
+    event->key.window = g_object_ref(gtk_widget_get_window(VIEW(dwb.state.fview)->web));
+    for (int i=0; i<3 && keyval[i] != 0; i++)
+    {
+        event->key.keyval = keyval[i];
+        event->key.state = state[i];
+        GdkKeymapKey *key; 
+        gint n;
+        if (gdk_keymap_get_entries_for_keyval(gdk_keymap_get_default(), keyval[i], &key, &n))
+        {
+            event->key.hardware_keycode = key[0].keycode;
+            g_free(key);
+        }
+        gtk_main_do_event(event);
+    }
+    gdk_event_free(event);
+}
+
+gboolean 
+visual_caret(GdkEventKey *e)
+{
+    static gint visual = false;
+
+    guint defaultMask = visual ? GDK_SHIFT_MASK : 0;
+
+    guint keyval[3] = { 0, 0, 0 };
+    guint state[3] = { defaultMask, defaultMask, defaultMask };
+
+    switch (e->keyval)
+    {
+        case GDK_KEY_j: 
+            keyval[0] = GDK_KEY_Down;
+            break;
+        case GDK_KEY_k: 
+            keyval[0] = GDK_KEY_Up;
+            break;
+        case GDK_KEY_h: 
+            keyval[0] = GDK_KEY_Left;
+            break;
+        case GDK_KEY_l: 
+            keyval[0] = GDK_KEY_Right;
+            break;
+        case GDK_KEY_w: 
+            keyval[0] = keyval[1] = GDK_KEY_Right;
+            keyval[2] = GDK_KEY_Left;
+            state[0] = state[1] = state[2] = GDK_CONTROL_MASK | defaultMask;
+            break;
+        case GDK_KEY_b: 
+            keyval[0] = GDK_KEY_Left;
+            state[0] = GDK_CONTROL_MASK | defaultMask;
+            break;
+        case GDK_KEY_e: 
+            keyval[0] = GDK_KEY_Right;
+            state[0] = GDK_CONTROL_MASK | defaultMask;
+            break;
+        case GDK_KEY_0: 
+            keyval[0] = GDK_KEY_Home;
+            break;
+        case GDK_KEY_dollar: 
+            keyval[0] = GDK_KEY_End;
+            break;
+        case GDK_KEY_v: 
+            visual = true;
+            dwb_set_normal_message(dwb.state.fview, false, "-- VISUAL --");
+            break;
+        case GDK_KEY_y: 
+            webkit_web_view_copy_clipboard(CURRENT_WEBVIEW());
+            dwb_set_normal_message(dwb.state.fview, true, "Yanked to clipboard");
+            dwb_change_mode(NORMAL_MODE, false); 
+            visual = false;
+            return true;
+        case GDK_KEY_Escape: 
+            if (visual)
+            {
+                dwb_set_normal_message(dwb.state.fview, false, "-- CARET --");
+                visual = false;
+            }
+            else 
+            {
+                WebKitWebSettings *settings = webkit_web_view_get_settings(CURRENT_WEBVIEW());
+                g_object_set(settings, "enable-caret-browsing", FALSE, NULL);
+                dwb_change_mode(NORMAL_MODE, true);
+            }
+            break;
+        default :return false;
+    }
+    dispatch_event(keyval, state);
+    js_call_as_function(MAIN_FRAME(), CURRENT_VIEW()->js_base, "caretUpdateCursor", NULL, kJSTypeUndefined, NULL);
+    return true;
+}

File src/visual.h

+/*
+ * Copyright (c) 2013 Stefan Bolte <portix@gmx.net>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ */
+
+#ifndef __INCLUDE_VISUAL_H
+#define __INCLUDE_VISUAL_H
+
+#include "dwb.h"
+
+gboolean visual_caret(GdkEventKey *e);
+
+#endif