forked from hayaku/hayaku
-
Notifications
You must be signed in to change notification settings - Fork 0
/
add_code_block.py
120 lines (100 loc) · 4.28 KB
/
add_code_block.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
#!/usr/bin/python
import re
import sublime
import sublime_plugin
from hayaku import get_hayaku_options
__all__ = [
'HayakuAddCodeBlockContext',
'HayakuAddCodeBlockCommand',
]
REGEX_WHITESPACES = re.compile(r'^\s*$')
# Context
class HayakuAddCodeBlockContext(sublime_plugin.EventListener):
def on_query_context(self, view, key, *args):
if key != "hayaku_add_code_block":
return None
regions = view.sel()
# Multiple blocks inserting doesn't make sense
if len(regions) > 1:
return None
region = regions[0]
# TODO: understand selection, but don't replace it on code block inserting
if not region.empty():
return None
# Looking for the scope
# TODO: Ensure it would be nice in preprocessors etc.
if not view.score_selector(region.begin(),'source.css, source.stylus, source.sass, source.scss'):
return None
# Determining the left and the right parts
line = view.line(region)
left_part = view.substr(sublime.Region(line.begin(), region.begin()))
right_part = view.substr(sublime.Region(region.begin(), line.end()))
# Check if the line isn't just a line of whitespace
if REGEX_WHITESPACES.search(left_part + right_part) is not None:
return None
# Simple check if the left part is ok
if left_part.find(';') != -1:
return None
# Simple check if the right part is ok
if right_part.find(';') != -1:
return None
return True
# Command
class HayakuAddCodeBlockCommand(sublime_plugin.TextCommand):
def run(self, edit):
result = '/* OVERRIDE ME */'
# Determine the limits for place searching
regions = self.view.sel()
region = regions[0]
line = self.view.line(region)
stop_point = self.view.find('[}]\s*',line.begin())
if stop_point is not None:
end = stop_point.end()
else:
end = self.view.find('[^}]*',line.begin()).end()
where_to_search = self.view.substr(
sublime.Region(
line.begin(),
end
)
)
options = get_hayaku_options(self)
# Insert a code block if we must
found_insert_position = re.search('^([^}{]*?[^;,}{\s])\s*(?=\n|$)',where_to_search)
if found_insert_position is not None:
self.view.sel().clear()
self.view.sel().add(sublime.Region(len(found_insert_position.group(1)) + line.begin(), len(found_insert_position.group(1)) + line.begin()))
start_before = options["CSS_whitespace_block_start_before"]
start_after = options["CSS_whitespace_block_start_after"]
end_before = options["CSS_whitespace_block_end_before"]
end_after = options["CSS_whitespace_block_end_after"]
opening_brace = "{"
closing_brace = "}"
if options["CSS_syntax_no_curly_braces"]:
opening_brace = ""
closing_brace = ""
start_before = ""
end_before = ""
result = ''.join([
start_before
, opening_brace
, start_after
, "$0"
, end_before
, closing_brace
, end_after
])
else:
# Place a caret + create a new line otherwise
# FIXME: the newline is not perfectly inserted. Must rethink it so there wouldn't
# be replacement of all whitespaces and would be better insertion handling
found_insert_rule = re.search('^(([^}]*?[^;]?)\s*)(?=\})',where_to_search)
if found_insert_rule:
self.view.sel().clear()
self.view.sel().add(sublime.Region(len(found_insert_rule.group(2)) + line.begin(), len(found_insert_rule.group(1)) + line.begin()))
result = ''.join([
options["CSS_whitespace_block_start_after"]
, "$0"
, options["CSS_whitespace_block_end_before"]
])
self.view.run_command("insert_snippet", {"contents": result})