*** empty log message ***
authorroot <root>
Mon, 9 Jan 2006 00:34:36 +0000 (00:34 +0000)
committerroot <root>
Mon, 9 Jan 2006 00:34:36 +0000 (00:34 +0000)
MANIFEST
src/perl/option-popup
src/perl/selection-popup [new file with mode: 0644]
src/rxvtperl.xs
src/urxvt.pm

index 21f3fdb78a8eeb726f4b5b03f151e19def3cc49e..77101a23f3914d3efa5a8b506d262a7c3131b798 100644 (file)
--- a/MANIFEST
+++ b/MANIFEST
@@ -175,6 +175,7 @@ src/perl/example-refresh-hooks
 src/perl/block-graphics-to-ascii
 src/perl/digital-clock
 src/perl/option-popup
+src/perl/selection-popup
 src/perl/urxvt-popup
 src/perl/selection
 src/perl/mark-urls
index 18e09c20566242f1ad3840608980f0751bddad80..4ac50ca4497672048eb16ff22df20cd31565253c 100644 (file)
@@ -3,15 +3,15 @@
 sub on_start {
    my ($self) = @_;
 
-   $self->grab_button (3, urxvt::ControlMask);
+   $self->grab_button (2, urxvt::ControlMask);
 }
 
 sub on_button_press {
    my ($self, $event) = @_;
 
-   if ($event->{button} == 3 && $event->{state} & urxvt::ControlMask) {
+   if ($event->{button} == 2 && $event->{state} & urxvt::ControlMask) {
       my $popup = $self->popup ($event)
-         or return;
+         or return 1;
 
       $popup->add_title ("Options");
       $popup->add_separator;
diff --git a/src/perl/selection-popup b/src/perl/selection-popup
new file mode 100644 (file)
index 0000000..3adfd9d
--- /dev/null
@@ -0,0 +1,53 @@
+#! perl
+
+sub on_start {
+   my ($self) = @_;
+
+   $self->grab_button (3, urxvt::ControlMask);
+}
+
+sub on_button_press {
+   my ($self, $event) = @_;
+
+   if ($event->{button} == 3 && $event->{state} & urxvt::ControlMask) {
+      my $popup = $self->popup ($event)
+         or return 1;
+
+      $popup->add_title ("Convert Selection");
+
+      my $text = $self->selection;
+
+      my $title = $text;
+      $title =~ s/[\x00-\x1f\x80-\x9f]/ยท/g;
+      substr $title, 40, -1, "..." if 40 < length $title;
+      $popup->add_title ($title);
+      $popup->add_separator;
+
+      my $add_button = sub {
+         my ($title, $cb) = @_;
+
+         $popup->add_button ($title => sub {
+            for ($text) {
+               $cb->();
+               $self->selection ($_);
+            }
+         });
+      };
+
+      for ($text) {
+         /^(\S+):(\d+):?$/
+            and $add_button->("vi-commands to load '$1'" => sub { s/^(\S+):(\d+):?$/\x1b:e $1\x0d:$2\x0d/ });
+         /%[0-9a-fA-F]{2}/ && !/%[^0-9a-fA-F]/ && !/%.[^0-9a-fA-F]/
+            and $add_button->("uri unescape" => sub { s/%([0-9a-fA-F]{2})/chr hex $1/ge });
+         /^(http|ftp|telnet|irc|news):\//
+            and $add_button->("run x-www-browser" => sub { system "x-www-browser \Q$_\E &" });
+      }
+
+      $popup->show;
+
+      return 1;
+   }
+
+   ()
+}
+
index a5fdb8d6516b65fd1057900bcc7392c18972ec28..4e9e05dc0c9f6a956bc2f6f47ccc3834c8e5c38a 100644 (file)
@@ -433,6 +433,17 @@ rxvt_perl_interp::init ()
     }
 }
 
+static void
+ungrab (rxvt_term *THIS)
+{
+  if (THIS->perl.grabtime)
+    {
+      XUngrabKeyboard (THIS->display->display, THIS->perl.grabtime);
+      XUngrabPointer  (THIS->display->display, THIS->perl.grabtime);
+      THIS->perl.grabtime = 0;
+    }
+}
+
 bool
 rxvt_perl_interp::invoke (rxvt_term *term, hook_type htype, ...)
 {
@@ -584,7 +595,10 @@ rxvt_perl_interp::invoke (rxvt_term *term, hook_type htype, ...)
             LEAVE;
 
             if (SvTRUE (ERRSV))
-              rxvt_warn ("perl hook %d evaluation error: %s", htype, SvPV_nolen (ERRSV));
+              {
+                rxvt_warn ("perl hook %d evaluation error: %s", htype, SvPV_nolen (ERRSV));
+                ungrab (term); // better lose the grab than the session
+              }
 
             if (htype == HOOK_DESTROY)
               {
@@ -695,6 +709,14 @@ fatal (const char *msg)
        CODE:
         rxvt_fatal ("%s", msg);
 
+SV *
+untaint (SV *sv)
+       CODE:
+        RETVAL = newSVsv (sv);
+        SvTAINTED_off (RETVAL);
+        OUTPUT:
+        RETVAL
+
 NV
 NOW ()
        CODE:
@@ -802,14 +824,7 @@ rxvt_term::allow_events_replay ()
 void
 rxvt_term::ungrab ()
        CODE:
-{
-        if (THIS->perl.grabtime)
-          {
-            XUngrabKeyboard (THIS->display->display, THIS->perl.grabtime);
-            XUngrabPointer  (THIS->display->display, THIS->perl.grabtime);
-            THIS->perl.grabtime = 0;
-          }
-}
+        ungrab (THIS);
 
 int
 rxvt_term::strwidth (SV *str)
@@ -1262,7 +1277,9 @@ rxvt_term::selection (SV *newtext = 0)
         PPCODE:
 {
         if (GIMME_V != G_VOID)
-          XPUSHs (taint (sv_2mortal (wcs2sv (THIS->selection.text, THIS->selection.len))));
+          XPUSHs (THIS->selection.text
+                  ? taint (sv_2mortal (wcs2sv (THIS->selection.text, THIS->selection.len)))
+                  : &PL_sv_undef);
 
         if (newtext)
           {
index c9c14ad8239172d6f7a5f90c9804c49dd0dd4f89..10b057acf0c748003042c8741a6eab7f478fb42d 100644 (file)
@@ -60,9 +60,14 @@ Rot-13 the selection when activated. Used via keyboard trigger:
 
 =item option-popup (enabled by default)
 
-Binds a popup menu to Ctrl-Button3 that lets you toggle (some) options at
+Binds a popup menu to Ctrl-Button2 that lets you toggle (some) options at
 runtime.
 
+=item selection-popup (enabled by default)
+
+Binds a popup menu to Ctrl-Button3 that lets you convert the selection
+text into various other formats/action.
+
 =item digital-clock
 
 Displays a digital clock using the built-in overlay.
@@ -425,6 +430,9 @@ BEGIN {
          unless $msg =~ /\n$/;
       urxvt::warn ($msg);
    };
+
+   $ENV{PATH} = "/bin:/sbin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:/opt/bin:/opt/sbin";
+   delete $ENV{CDPATH};
 }
 
 my @hook_count;
@@ -467,14 +475,12 @@ sub extension_package($) {
       open my $fh, "<:raw", $path
          or die "$path: $!";
 
-      my $source = "package $pkg; use strict; use utf8;\n"
+      my $source = untaint "package $pkg; use strict; use utf8;\n"
                    . "use base urxvt::term::proxy::;\n"
                    . "#line 1 \"$path\"\n{\n"
                    . (do { local $/; <$fh> })
                    . "\n};\n1";
 
-      $source =~ /(.*)/s and $source = $1; # untaint
-
       eval $source or die "$path: $@";
 
       $pkg
@@ -495,7 +501,7 @@ sub invoke {
 
       for (map { split /,/, $TERM->resource ("perl_ext_$_") } 1, 2) {
          if ($_ eq "default") {
-            $want_ext{$_}++ for qw(selection option-popup);
+            $want_ext{$_}++ for qw(selection option-popup selection-popup);
          } elsif (/^-(.*)$/) {
             delete $want_ext{$1};
          } else {