[kupfer] Put files from commandline in kupfer directly as files



commit 36105b2e0386135ef042a113bb89216fd49e810e
Author: Ulrik Sverdrup <ulrik sverdrup gmail com>
Date:   Thu Feb 11 14:20:28 2010 +0100

    Put files from commandline in kupfer directly as files
    
    When invoked with a list of files, kupfer FILE [ ... ], we put them
    directly in kupfer as files on the stack. Thus we support putting
    multiple files in Kupfer at the same time.
    
    The only way to put text queries in kupfer from the command line is to
    pipe text into the ``kupfer`` command.
    
    This is implemented with D-Bus method changes, where PutText now only
    takes a string, and PutFiles takes an array of file uris.

 Documentation/Quickstart.rst |    6 +++---
 auxdata/kupfer.desktop.in    |    2 +-
 bin/kupfer.in                |   25 ++++++++++++++++++++++---
 kupfer/core/data.py          |   16 ++++++++++++++--
 kupfer/interface.py          |    4 ++++
 kupfer/main.py               |    2 +-
 kupfer/ui/browser.py         |   22 +++++++++++++++-------
 kupfer/ui/listen.py          |   16 ++++++++++++----
 8 files changed, 72 insertions(+), 21 deletions(-)
---
diff --git a/Documentation/Quickstart.rst b/Documentation/Quickstart.rst
index 14d0d52..e0c3768 100644
--- a/Documentation/Quickstart.rst
+++ b/Documentation/Quickstart.rst
@@ -13,7 +13,7 @@ Convenient command and access tool for applications and documents
 SYNOPSIS
 ========
 
-| ``kupfer`` [ *OPTIONS* | *QUERY* ]
+| ``kupfer`` [ *OPTIONS* | *FILE* ... ]
 | ``kupfer-exec`` *FILE* ...
 
 DESCRIPTION
@@ -40,9 +40,9 @@ the program it if already running.
 If the keybinder module is installed, kupfer will listen to a
 keybinding. By default the keybinding is *Ctrl+Space* to show kupfer.
 
-Kupfer can be invoked with a text query, with
+Kupfer can be invoked with a list of files
 
-        ``kupfer`` *QUERY*
+        ``kupfer`` *FILE* ...
 
 This can be used to select files given as command-line arguments in the
 program. Then you can invoke actions even on objects from a shell-based
diff --git a/auxdata/kupfer.desktop.in b/auxdata/kupfer.desktop.in
index 6bdf3ea..f821552 100644
--- a/auxdata/kupfer.desktop.in
+++ b/auxdata/kupfer.desktop.in
@@ -4,7 +4,7 @@ _Name=Kupfer
 _GenericName=Application Launcher
 _Comment=Convenient command and access tool for applications and documents
 Icon=search
-Exec=kupfer %f
+Exec=kupfer %F
 Type=Application
 Categories=Utility;
 StartupNotify=true
diff --git a/bin/kupfer.in b/bin/kupfer.in
index cc9bcd8..f1c23c9 100755
--- a/bin/kupfer.in
+++ b/bin/kupfer.in
@@ -31,7 +31,6 @@ then
 	echo "kupfer: Reading from stdin"
 	TEXT_INPUT=$(cat)
 fi
-test -z "$TEXT_INPUT" && TEXT_INPUT="$*"
 
 # If there are any options, like "--help", we run Kupfer directly
 test "x${1:0:2}" = "x--"
@@ -43,10 +42,30 @@ KUPFER_RUNNING=$?
 if test \( -n "$TEXT_INPUT" -a $KUPFER_HAS_OPTIONS != 0 \)
 then
 	dbus-send --print-reply --dest=se.kaizer.kupfer /interface \
-	se.kaizer.kupfer.Listener.PutText string:"$PWD" string:"$TEXT_INPUT" \
-	>/dev/null 2>&1
+		se.kaizer.kupfer.Listener.PutText string:"$TEXT_INPUT" \
+		>/dev/null 2>&1
 fi
 
+_realpaths () {
+	# Emit realpaths for arguments, separated by NUL bytes
+	while test $# != 0
+	do
+		echo -ne $(realpath "$1")"\0"
+		shift
+	done
+}
+
+if test \( -n "$1" -a $KUPFER_HAS_OPTIONS != 0 \)
+then
+	# FIXME: How to handle files with , in filename
+	ARRAY=$(_realpaths "$@" | tr \\0 ,)
+	dbus-send --print-reply --dest=se.kaizer.kupfer /interface \
+		se.kaizer.kupfer.Listener.PutFiles array:string:"$ARRAY" \
+		>/dev/null 2>&1
+fi
+
+
+
 if test $KUPFER_RUNNING != 0
 then
 	exec ${PYTHON} "$PYTHONDIR/kupfer.py" $*
diff --git a/kupfer/core/data.py b/kupfer/core/data.py
index 63c136b..7c5b5bc 100644
--- a/kupfer/core/data.py
+++ b/kupfer/core/data.py
@@ -755,10 +755,22 @@ class DataController (gobject.GObject, pretty.OutputMixin):
 
 	def _insert_object(self, pane, obj):
 		"Insert @obj in @pane: prepare the object, then emit pane-reset"
-		sc = GetSourceController()
-		sc.decorate_object(obj)
+		self._decorate_object(obj)
 		self.emit("pane-reset", pane, search.wrap_rankable(obj))
 
+	def _decorate_object(self, *objects):
+		sc = GetSourceController()
+		for obj in objects:
+			sc.decorate_object(obj)
+
+	def insert_objects(self, pane, objects):
+		"Select @objects in @pane"
+		if pane != SourcePane:
+			raise ValueError("Can only insert in first pane")
+		self._decorate_object(objects[:-1])
+		self._set_object_stack(pane, objects[:-1])
+		self._insert_object(pane, objects[-1])
+
 	def _command_execution_result(self, ctx, result_type, ret):
 		if result_type == commandexec.RESULT_SOURCE:
 			self.object_stack_clear_all()
diff --git a/kupfer/interface.py b/kupfer/interface.py
index cffda62..5db72ef 100644
--- a/kupfer/interface.py
+++ b/kupfer/interface.py
@@ -25,3 +25,7 @@ def copy_to_clipboard(obj, clipboard):
 		return True
 	except AttributeError:
 		return False
+
+def get_fileleaf_for_path(pth):
+	import kupfer.objects
+	return kupfer.objects.FileLeaf(pth)
diff --git a/kupfer/main.py b/kupfer/main.py
index 3f5f0f5..f615f29 100644
--- a/kupfer/main.py
+++ b/kupfer/main.py
@@ -53,7 +53,7 @@ def get_options():
 		defaults_filename = "defaults.cfg"
 		conf_path = config.save_config_file(config_filename)
 		defaults_path = config.get_data_file(defaults_filename)
-		usage_string = _("Usage: kupfer [OPTIONS | QUERY]")
+		usage_string = _("Usage: kupfer [ OPTIONS | FILE ... ]")
 		def format_options(opts):
 			return "\n".join("  --%-15s  %s" % (o,h) for o,h in opts)
 
diff --git a/kupfer/ui/browser.py b/kupfer/ui/browser.py
index 0d82dd3..408829e 100644
--- a/kupfer/ui/browser.py
+++ b/kupfer/ui/browser.py
@@ -1349,6 +1349,12 @@ class Interface (gobject.GObject):
 		self.entry.set_text(text)
 		self.entry.set_position(-1)
 
+	def put_files(self, fileuris):
+		leaves = map(interface.get_fileleaf_for_path,
+			filter(None, [gio.File(U).get_path() for U in fileuris]))
+		if leaves:
+			self.data_controller.insert_objects(data.SourcePane, leaves)
+
 	def _changed(self, editable):
 		"""
 		The entry changed callback: Here we have to be sure to use
@@ -1506,14 +1512,15 @@ class WindowController (pretty.OutputMixin):
 			self.activate(time=event_time)
 			self.interface.select_selected_file()
 
-	def _put_text_recieved(self, sender, working_dir, text):
+	def _put_text_received(self, sender, text):
 		"""We got a search query from dbus"""
-		buildpath = os.path.join(working_dir, text)
 		self.activate()
-		if os.path.exists(buildpath):
-			self.interface.put_text(buildpath)
-		else:
-			self.interface.put_text(text)
+		self.interface.put_text(text)
+
+	def _put_files_received(self, sender, fileuris):
+		"""We got a search query from dbus"""
+		self.activate()
+		self.interface.put_files(fileuris)
 
 	def _execute_file_received(self, sender, filepath):
 		from kupfer import execfile
@@ -1611,7 +1618,8 @@ class WindowController (pretty.OutputMixin):
 		else:
 			kserv.connect("present", self.activate)
 			kserv.connect("show-hide", self.show_hide)
-			kserv.connect("put-text", self._put_text_recieved)
+			kserv.connect("put-text", self._put_text_received)
+			kserv.connect("put-files", self._put_files_received)
 			kserv.connect("execute-file", self._execute_file_received)
 			kserv.connect("quit", self.quit)
 
diff --git a/kupfer/ui/listen.py b/kupfer/ui/listen.py
index 29ec5f0..a3817d4 100644
--- a/kupfer/ui/listen.py
+++ b/kupfer/ui/listen.py
@@ -55,9 +55,13 @@ class Service (ExportedGObject):
 	def ShowHide(self):
 		self.emit("show-hide")
 
-	@dbus.service.method(interface_name, in_signature="ss")
-	def PutText(self, working_directory, text):
-		self.emit("put-text", working_directory, text)
+	@dbus.service.method(interface_name, in_signature="s")
+	def PutText(self, text):
+		self.emit("put-text", text)
+
+	@dbus.service.method(interface_name, in_signature="s")
+	def PutFiles(self, fileuris):
+		self.emit("put-files", fileuris)
 
 	@dbus.service.method(interface_name, in_signature="s")
 	def ExecuteFile(self, filepath):
@@ -73,7 +77,11 @@ gobject.signal_new("show-hide", Service, gobject.SIGNAL_RUN_LAST,
 		gobject.TYPE_BOOLEAN, ())
 
 gobject.signal_new("put-text", Service, gobject.SIGNAL_RUN_LAST,
-		gobject.TYPE_BOOLEAN, (gobject.TYPE_STRING, gobject.TYPE_STRING))
+		gobject.TYPE_BOOLEAN, (gobject.TYPE_STRING, ))
+
+gobject.signal_new("put-files", Service, gobject.SIGNAL_RUN_LAST,
+		gobject.TYPE_BOOLEAN, (gobject.TYPE_PYOBJECT, ))
+
 gobject.signal_new("execute-file", Service, gobject.SIGNAL_RUN_LAST,
 		gobject.TYPE_BOOLEAN, (gobject.TYPE_STRING,))
 



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]