Skip to content

Instantly share code, notes, and snippets.

@sublimator
Created September 13, 2011 06:04
Show Gist options
  • Save sublimator/1213230 to your computer and use it in GitHub Desktop.
Save sublimator/1213230 to your computer and use it in GitHub Desktop.
BrowseDirs
#coding: utf8
#################################### IMPORTS ###################################
# Std Libs
import os
import inspect
import functools
import re
import types
from os.path import ( basename, join, isdir, splitext, normpath, exists,
ismount )
# Sublime Libs
import sublime
import sublime_plugin
from scheduler import scheduled, wait_on_virtual_view
# 3rd Party Libs
from directorystructures import create_directory_structure
################################################################################
FILE = 1
FOLDER = 2
CMD = 3
COMMANDS = {}
UNWANTED = ( '.jpg', '.gif', '.png', '.pyc', '.pyo', '.bin', '.o', '.so',
'.obj', '.lib', '.pdb', '.suo', '.ncb', '.dll', '.exe', '.zip',
'.tar', '.gz', '.bz2', '.tgz', '.rar' )
PROJECT_TEMPLATE = """\
{
"folders":
[
{
"path": "${1:.}"
}
],
"settings":
{
${2:"${3:key}": "${4:value}"}
}
}"""
################################################################################
def visit_drives(c, **kw):
"""
Could be a comtypes script object:
from comtypes.client import CreateObject
fso = CreateObject('scripting.filesystemobject')
for d in sorted(fso.Drives, **kw):
c(dl + ':/')
"""
for dl in 'DEFGHZC':
c(dl + ':/')
def listdir_add_commands(folder):
isf = lambda p: isdir(join(folder, p))
filtered_list = [f for f in os.listdir(folder) if not f.endswith(UNWANTED)]
display = ( ['../'] +
[((p + '/') if isf(p) else p) for p in sorted (
filtered_list, key=isf) ] +
sorted(COMMANDS) )
visit_drives(display.append)
return display
def browse_folder(window, folder):
while 1:
sublime.status_message(normpath(folder))
d = listdir_add_commands(folder)
# Needed for the quick panel sometimes
yield scheduled.delay(0)
result = (yield window.quick_panel(d))
fn = normpath(join(folder, d[result]))
if not isdir(fn): break
else: folder = fn
ret = d[result]
if not re.match(':[a-z_]+:', ret):
ret = join(folder, ret)
yield folder, [ret]
def create_dir_entry(window, folder, is_folder=0):
av = window.active_view()
default = ( 'new' if is_folder else '$1.${2:%s}' % (
splitext(av.file_name())[-1] if av else 'py').lstrip('.'))
folder = normpath(folder)
msg = 'Create %s in %s:' % ('folder' if is_folder else 'file', folder)
while True:
try:
fn = join(folder, (yield window.input(msg, default)))
if is_folder: os.mkdir(fn)
elif not os.path.exists(fn): open(fn, 'w').close()
break
except IOError, e:
msg = unicode(e)
default = basename(fn)
continue
sublime.status_message('Created %s' % fn)
yield fn
def open_file_path(fn):
"Formats a path as /C/some/path/on/window/no/colon.txt"
fn = normpath(fn)
fn = re.sub('^([a-zA-Z]):', '/\\1', fn)
fn = re.sub(r'\\', '/', fn)
return fn
def create_dir_tree(window, folder):
title = 'Create Folder Structure'
view = (yield wait_on_virtual_view(window, title))
yield create_directory_structure (
view.buffer,
wd = folder,
safe = True,
tab_size = view.setting.tab_size )
def entry_and_type(e):
return e, ( None if not isinstance(e, basestring) else
FOLDER if (isdir(e) or ismount(e)) else
FILE if exists(e) else CMD )
def command(f):
if isinstance(f, types.FunctionType):
def wrap(f):
@functools.wraps(f)
def wrapper(*args, **kw):
yield f(*args, **kw)
return wrapper
f = wrap(f)
name = f.__name__
if name.endswith('_cmd'): name = name[:-4].lower()
COMMANDS[':%s:' % name] = f
return f
############################### QUICK BROWSE DIR ###############################
class QuickBrowseDir(sublime_plugin.WindowCommand):
def __init__(self, window):
super(QuickBrowseDir, self).__init__(window)
for name, method in inspect.getmembers(self, inspect.ismethod):
if name.endswith('_cmd'):
command(method)
@scheduled(every=None)
def run(self, folder = None, under=False):
window = self.window
fn = window.active_view().file_name()
if not folder:
if fn: folder = os.path.dirname(fn)
else: folder = os.getcwd()
if under:
view = window.active_view()
folder = view.substr(view.sel()[0])
if not os.path.exists(folder):
sublime.status_message("%s does not exist" % folder )
raise StopIteration # ~= `return` for scheduled()
yield self.main_loop(window, folder)
def main_loop(self, window, folder):
folder, entries = (yield browse_folder(window, folder))
while entries:
entry, entry_type = entry_and_type(entries.pop())
if entry_type is None: break
elif entry_type == FILE:
yield window.open_file(entry)
elif entry_type == FOLDER:
folder, more = (yield browse_folder(window, entry))
entries.extend(more)
elif entry_type == CMD:
entries.append( (yield COMMANDS[entry](window, folder)) )
def new_cmd(self, window, folder):
yield create_dir_entry(window, folder)
def mkdir_cmd(self, window, folder):
yield create_dir_entry(window, folder, is_folder=1)
def tree_cmd(self, window, folder):
yield create_dir_tree(window, folder)
def explore_cmd(self, window, folder):
window.cmd.open_dir(dir=open_file_path(folder))
def search_cmd(self, window, folder):
window.cmd.show_panel( panel = "find_in_files",
location = open_file_path(folder) )
########################### DECORATED LIKE A GRAHAVE ###########################
@command
def project(window, folder):
fn = join(folder, (yield window.input (
'Enter Project Name',
'${1:%s}.sublime-project' % basename(folder))))
if not exists(fn):
scratch = wait_on_virtual_view ( window,
title = 'New Project',
snip = PROJECT_TEMPLATE,
syntax = 'JavaScript/JSON.tmLanguage')
with open(fn, 'w') as fh:
fh.write((yield scratch).buffer)
else:
yield fn
################################################################################
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment