On Thu Feb 03 09:21:41 2011,
http://hype-free.blogspot.com/ wrote:
Show quoted text> (After executing it and trying to paste into gedit I don't get
> anything). However if I change (monkey patch) the order in which the
> different clipboard types are consulted so that "clipboard" is the first
> (and thus the "favorite" one selected by Clipboard::Xclip) it works.
Indeed, X11 basically has two clipboards:
primary (XA_PRIMARY): The clipboard pasted by middle-clicking, and
(usually) set to the last selection.
clipboard (XA_CLIPBOARD): The clipboard pasted by typing Ctrl+V or
Shift+Ins. **This is the clipboard users coming from Windows/Macintosh
are used to.**
A couple others recognized by xclip (both of which can be used to store
text):
secondary (XA_SECONDARY): Not used by many X11 applications. This is
*not* the same as XA_CLIPBOARD.
buffer (XA_STRING): Cut buffer ring
It looks like Clipboard::Xclip defaults to 'primary', but I think most
users would expect it to use 'clipboard'. Many (not all) text editors
in Linux store copied text into both clipboards: selecting the text puts
it in 'primary', and typing Ctrl+C puts it in 'clipboard'.
I attached a patch to try to make the copy/paste semantics on X saner.
Namely, Clipboard->copy copies to 'clipboard', and Clipboard->paste
pastes from 'clipboard'. No other selections are involved.
I also added Clipboard->copy1 and Clipboard->paste1 for manipulating the
primary buffer. On Win32 and Mac, these simply use a global variable
and do not affect the clipboard. The reason I did this is: imagine
someone wants to use this module in their terminal emulator. They want
to add middle click pasting, so they call copy1 every time a selection
is made. If copy1 used the system clipboard, that would be annoying to
the user because selecting text would destroy the clipboard contents.
Please proofread this patch, as I'm still a Perl newbie. Also, I didn't
add any tests for copy1 and paste1.
From f15b141878c3bd8f22f87573c2aa091aaeccb07e Mon Sep 17 00:00:00 2001
From: Joey Adams <joeyadams3.14159@gmail.com>
Date: Wed, 2 Mar 2011 21:46:18 -0500
Subject: [PATCH] Make Xclip copy/paste use 'clipboard'; add copy1/paste1
copy1/paste1 use 'primary' rather than 'clipboard'
in the Xclip driver, and are emulated with a global
variable in the MacPasteboard and Win32 drivers.
---
Test/MockClipboard.pm | 3 +++
lib/Clipboard.pm | 4 ++++
lib/Clipboard/MacPasteboard.pm | 9 +++++++++
lib/Clipboard/Win32.pm | 9 +++++++++
lib/Clipboard/Xclip.pm | 20 +++++++++++---------
5 files changed, 36 insertions(+), 9 deletions(-)
diff --git a/Test/MockClipboard.pm b/Test/MockClipboard.pm
index c42e0fd..6d5a116 100644
--- a/Test/MockClipboard.pm
+++ b/Test/MockClipboard.pm
@@ -1,6 +1,9 @@
package PhonyClipboard;
our $board = '';
+our $board1 = '';
sub copy { my $self = shift; $board = $_[0]; }
+sub copy1 { my $self = shift; $board1 = $_[0]; }
sub paste { my $self = shift; $board }
+sub paste1 { my $self = shift; $board1 }
$Clipboard::driver = 'PhonyClipboard';
1;
diff --git a/lib/Clipboard.pm b/lib/Clipboard.pm
index 4fb4095..4a3c7b5 100644
--- a/lib/Clipboard.pm
+++ b/lib/Clipboard.pm
@@ -6,6 +6,10 @@ sub copy { my $self = shift; $driver->copy(@_); }
sub cut { goto © }
sub paste { my $self = shift; $driver->paste(@_); }
+sub copy1 { my $self = shift; $driver->copy1(@_); }
+sub cut1 { goto ©1 }
+sub paste1 { my $self = shift; $driver->paste1(@_); }
+
sub bind_os { my $driver = shift; map { $_ => $driver } @_; }
sub find_driver {
my $self = shift;
diff --git a/lib/Clipboard/MacPasteboard.pm b/lib/Clipboard/MacPasteboard.pm
index feda58f..decebde 100644
--- a/lib/Clipboard/MacPasteboard.pm
+++ b/lib/Clipboard/MacPasteboard.pm
@@ -1,13 +1,22 @@
package Clipboard::MacPasteboard;
use Mac::Pasteboard;
our $board = Mac::Pasteboard->new();
+our $board1 = '';
$board->set( missing_ok => 1 );
sub copy {
my $self = shift;
$board->clear();
$board->copy($_[0]);
}
+sub copy1 {
+ my $self = shift;
+ $board1 = $_[0];
+}
sub paste {
my $self = shift;
return scalar $board->paste();
}
+sub paste1 {
+ my $self = shift;
+ $board1;
+}
diff --git a/lib/Clipboard/Win32.pm b/lib/Clipboard/Win32.pm
index e0e88b8..231e1e9 100644
--- a/lib/Clipboard/Win32.pm
+++ b/lib/Clipboard/Win32.pm
@@ -1,11 +1,20 @@
package Clipboard::Win32;
use Win32::Clipboard;
our $board = Win32::Clipboard();
+our $board1 = '';
sub copy {
my $self = shift;
$board->Set($_[0]);
}
+sub copy1 {
+ my $self = shift;
+ $board1 = $_[0];
+}
sub paste {
my $self = shift;
$board->Get();
}
+sub paste1 {
+ my $self = shift;
+ $board1;
+}
diff --git a/lib/Clipboard/Xclip.pm b/lib/Clipboard/Xclip.pm
index 9da20cd..403c0e1 100644
--- a/lib/Clipboard/Xclip.pm
+++ b/lib/Clipboard/Xclip.pm
@@ -3,7 +3,12 @@ use Clipboard;
sub copy {
my $self = shift;
my ($input) = @_;
- $self->copy_to_selection($self->favorite_selection, $input);
+ $self->copy_to_selection('clipboard', $input);
+}
+sub copy1 {
+ my $self = shift;
+ my ($input) = @_;
+ $self->copy_to_selection('primary', $input);
}
sub copy_to_selection {
my $self = shift;
@@ -15,11 +20,11 @@ sub copy_to_selection {
}
sub paste {
my $self = shift;
- for ($self->all_selections) {
- my $data = $self->paste_from_selection($_);
- return $data if length $data;
- }
- undef
+ return $self->paste_from_selection('clipboard');
+}
+sub paste1 {
+ my $self = shift;
+ return $self->paste_from_selection('primary');
}
sub paste_from_selection {
my $self = shift;
@@ -30,9 +35,6 @@ sub paste_from_selection {
close $exe or die "Error closing `$cmd`: $!";
return $result;
}
-# This ordering isn't officially verified, but so far seems to work the best:
-sub all_selections { qw(primary buffer clipboard secondary) }
-sub favorite_selection { my $self = shift; ($self->all_selections)[0] }
{
open my $just_checking, 'xclip -o|' or warn <<'EPIGRAPH';
--
1.7.1