about summary refs log tree commit diff stats
path: root/ranger/commands.py
diff options
context:
space:
mode:
Diffstat (limited to 'ranger/commands.py')
-rw-r--r--ranger/commands.py75
1 files changed, 73 insertions, 2 deletions
diff --git a/ranger/commands.py b/ranger/commands.py
index 2c0593a3..07fa1679 100644
--- a/ranger/commands.py
+++ b/ranger/commands.py
@@ -19,7 +19,7 @@ class Command(FileManagerAware):
 	def quick_open(self):
 		"""Override this"""
 
-	def _tab_through_directories(self):
+	def _tab_only_directories(self):
 		from os.path import dirname, basename, expanduser, join, isdir
 
 		line = parse(self.line)
@@ -30,33 +30,94 @@ class Command(FileManagerAware):
 		except IndexError:
 			rel_dest = ''
 
+		# expand the tilde into the user directory
 		if rel_dest.startswith('~'):
 			return line + expanduser(rel_dest) + '/'
 
+		# define some shortcuts
 		abs_dest = join(pwd, rel_dest)
 		abs_dirname = dirname(abs_dest)
 		rel_basename = basename(rel_dest)
 		rel_dirname = dirname(rel_dest)
 		
 		try:
+			# are we after a directory?
 			if rel_dest.endswith('/') or rel_dest == '':
 				_, dirnames, _ = os.walk(abs_dest).next()
+
+			# are we in the middle of the filename?
 			else:
 				_, dirnames, _ = os.walk(abs_dirname).next()
 				dirnames = [dn for dn in dirnames \
 						if dn.startswith(rel_basename)]
 		except (OSError, StopIteration):
+			# os.walk found nothing
 			pass
 		else:
 			dirnames.sort()
 
+			# no results, return None
 			if len(dirnames) == 0:
 				return
 
+			# one result. since it must be a directory, append a slash.
 			if len(dirnames) == 1:
 				return line + join(rel_dirname, dirnames[0]) + '/'
 
+			# more than one result. append no slash, so the user can
+			# manually type in the slash to advance into that directory
 			return (line + join(rel_dirname, dirname) for dirname in dirnames)
+	
+	def _tab_directory_content(self):
+		from os.path import dirname, basename, expanduser, join, isdir
+
+		line = parse(self.line)
+		pwd = self.fm.env.pwd.path
+
+		try:
+			rel_dest = line.rest(1)
+		except IndexError:
+			rel_dest = ''
+
+		# expand the tilde into the user directory
+		if rel_dest.startswith('~'):
+			return line + expanduser(rel_dest) + '/'
+
+		# define some shortcuts
+		abs_dest = join(pwd, rel_dest)
+		abs_dirname = dirname(abs_dest)
+		rel_basename = basename(rel_dest)
+		rel_dirname = dirname(rel_dest)
+		
+		try:
+			# are we after a directory?
+			if rel_dest.endswith('/') or rel_dest == '':
+				_, dirnames, filenames = os.walk(abs_dest).next()
+				names = dirnames + filenames
+
+			# are we in the middle of the filename?
+			else:
+				_, dirnames, filenames = os.walk(abs_dirname).next()
+				names = [name for name in (dirnames + filenames) \
+						if name.startswith(rel_basename)]
+		except (OSError, StopIteration):
+			# os.walk found nothing
+			pass
+		else:
+			names.sort()
+
+			# no results, return None
+			if len(names) == 0:
+				return
+
+			# one result. since it must be a directory, append a slash.
+			if len(names) == 1:
+				return line + join(rel_dirname, names[0]) + '/'
+
+			# more than one result. append no slash, so the user can
+			# manually type in the slash to advance into that directory
+			return (line + join(rel_dirname, name) for name in names)
+
 
 # -------------------------------- definitions
 
@@ -81,7 +142,7 @@ class cd(Command):
 			self.fm.enter_dir(destination)
 
 	def tab(self):
-		return self._tab_through_directories()
+		return self._tab_only_directories()
 	
 	def quick_open(self):
 		from os.path import isdir, join, normpath
@@ -120,6 +181,9 @@ class find(Command):
 			self.fm.block_input(0.5)
 			return True
 
+	def tab(self):
+		return self._tab_directory_content()
+
 	def _search(self):
 		self.count = 0
 		line = parse(self.line)
@@ -168,6 +232,9 @@ class rename(Command):
 	def execute(self):
 		line = parse(self.line)
 		self.fm.rename(self.fm.env.cf, line.rest(1))
+
+	def tab(self):
+		return self._tab_directory_content()
 	
 
 # -------------------------------- rest
@@ -185,3 +252,7 @@ def alias(**kw):
 		by_name[key] = value
 
 alias(q=quit)
+
+def command_generator(start):
+	return (cmd + ' ' for cmd in by_name if cmd.startswith(start))
+