import sublime, sublime_plugin import os.path import re import thread BINARY = re.compile('\.(apng|png|jpg|gif|jpeg|bmp|psd|ai|cdr|ico|cache|sublime-package|eot|svgz|ttf|woff|zip|tar|gz|rar|bz2|jar|xpi|mov|mpeg|avi|mpg|flv|wmv|mp3|wav|aif|aiff|snd|wma|asf|asx|pcm|pdf|doc|docx|xls|xlsx|ppt|pptx|rtf|sqlite|sqlitedb|fla|swf|exe)$', re.I); class OpenInclude(sublime_plugin.TextCommand): # run and look for different sources of paths def run(self, edit): window = sublime.active_window() view = self.view something_opened = False for region in view.sel(): opened = False # between quotes syntax = self.view.syntax_name(region.begin()) if re.match(".*string.quoted.double", syntax) or re.match(".*string.quoted.single", syntax): opened = self.resolve_path(window, view, view.substr(view.extract_scope(region.begin()))) # selected text if not opened: opened = self.resolve_path(window, view, view.substr(sublime.Region(region.begin(), region.end()))) # current lines if not opened: opened = self.resolve_path(window, view, view.substr(sublime.Region(view.line(region.begin()).begin(), view.line(region.end()).end()))) # current line quotes and parenthesis if not opened: line = view.substr(sublime.Region(view.line(region.begin()).begin(), view.line(region.end()).end())) line = line.replace(')', '"').replace('(', '"').replace("'", '"') lines = line.split('"') for line in lines: line = line.strip() if line: opened = self.resolve_path(window, view, line) if opened: break; # current lines splitted by spaces or tabs if not opened: opened = self.resolve_path(window, view, view.substr(sublime.Region(view.line(region.begin()).begin(), view.line(region.end()).end())).replace('\t', '\n').replace(' ', '\n')) if opened: something_opened = True if not something_opened: self.resolve_path(window, view, view.substr(sublime.Region(0, view.size())).replace('\t', '\n')) # resolve the path of these sources and send to try_open def resolve_path(self, window, view, paths): import urllib try: paths_decoded = urllib.unquote(paths.encode('utf8')) paths_decoded = unicode(paths_decoded.decode('utf8')); paths += '\n'+paths_decoded except: pass paths = paths.split('\n') paths.append(paths[0].replace('../', '')) paths = list(set(paths)) something_opened = False for path in paths: opened = False # remove quotes path = re.sub('^"|\'', '', re.sub('"|\'$', '', path.strip())) # remove :row:col path = re.sub('(\:[0-9]*)+$', '', path.strip()).strip() if path == '': continue # relative to view if not opened and view.file_name() != None and view.file_name() != '': maybe_path = self.resolve_relative(os.path.dirname(view.file_name()), path) opened = self.try_open(window, maybe_path) if opened: something_opened = True # relative to view dirname if not opened and view.file_name() != None and view.file_name() != '': maybe_path = self.resolve_relative(os.path.dirname(os.path.dirname(view.file_name())), path) opened = self.try_open(window, maybe_path) if opened: something_opened = True # relative to project folders for maybe_path in sublime.active_window().folders(): maybe_path_tpm = self.resolve_relative(maybe_path, path) opened = self.try_open(window, maybe_path_tpm) if opened: something_opened = True break # relative to project folders minus one folder. maybe_path_tpm = self.resolve_relative(maybe_path, '../'+path) opened = self.try_open(window, maybe_path_tpm) if opened: something_opened = True break # relative to project folders minus two folder. maybe_path_tpm = self.resolve_relative(maybe_path, '../../'+path) opened = self.try_open(window, maybe_path_tpm) if opened: something_opened = True break # absolute if not opened: opened = self.try_open(window, path) if opened: something_opened = True return something_opened # try opening the resouce def try_open(self, window, maybe_path): if maybe_path[:4] == 'http': if BINARY.search(maybe_path): try: sublime.status_message("Opening in browser " + maybe_path) import webbrowser webbrowser.open_new_tab(maybe_path) return True except: return False else: sublime.status_message("Opening URL " + maybe_path) thread.start_new_thread(self.read_url, (maybe_path, maybe_path)) return True if os.path.isfile(maybe_path): if BINARY.search(maybe_path): import sys path = os.path.join(sublime.packages_path(), 'Open-Include') if path not in sys.path: sys.path.append(path) import desktop desktop.open(maybe_path) else: window.open_file(maybe_path) sublime.status_message("Opening file " + maybe_path) return True else: return False # util def resolve_relative(self, absolute, path): subs = path.replace('\\', '/').split('/') for sub in subs: if sub != '': absolute = os.path.join(absolute, sub) return absolute def read_url(self, url, so): try: if url[:5] == 'https': url = re.sub('^https', 'http', url) import urllib2 req = urllib2.urlopen(url) content = req.read() encoding=req.headers['content-type'].split('charset=')[-1] try: content = unicode(content, encoding) except: try: content = content.encode('utf-8') except: content = '' content_type = req.headers['content-type'].split(';')[0] sublime.set_timeout(lambda:self.read_url_on_done(content, content_type), 0) except: pass def read_url_on_done(self, content, content_type): if content: window = sublime.active_window() view = window.new_file() edit = view.begin_edit() try: view.insert(edit, 0, content) finally: view.end_edit(edit) if content_type == 'text/html': view.settings().set('syntax', 'Packages/HTML/HTML.tmLanguage') elif content_type == 'text/css': view.settings().set('syntax', 'Packages/CSS/CSS.tmLanguage') elif content_type == 'text/javascript' or content_type == 'application/javascript' or content_type == 'application/x-javascript': view.settings().set('syntax', 'Packages/JavaScript/JavaScript.tmLanguage') elif content_type == 'application/json' or content_type == 'text/json': view.settings().set('syntax', 'Packages/JavaScript/JSON.tmLanguage') elif content_type == 'text/xml' or content_type == 'application/xml': view.settings().set('syntax', 'Packages/XML/XML.tmLanguage')