Changeset View
Changeset View
Standalone View
Standalone View
plugins/extensions/pykrita/plugin/plugins/scripter/syntax.py
Show All 30 Lines | 23 | operators = [ | |||
---|---|---|---|---|---|
31 | # Bitwise | 31 | # Bitwise | ||
32 | '\^', '\|', '\&', '\~', '>>', '<<', | 32 | '\^', '\|', '\&', '\~', '>>', '<<', | ||
33 | ] | 33 | ] | ||
34 | 34 | | |||
35 | # Python braces | 35 | # Python braces | ||
36 | braces = [ | 36 | braces = [ | ||
37 | '\{', '\}', '\(', '\)', '\[', '\]', | 37 | '\{', '\}', '\(', '\)', '\[', '\]', | ||
38 | ] | 38 | ] | ||
39 | | ||||
39 | def __init__(self, document, syntaxStyle): | 40 | def __init__(self, document, syntaxStyle): | ||
40 | QSyntaxHighlighter.__init__(self, document) | 41 | QSyntaxHighlighter.__init__(self, document) | ||
41 | 42 | | |||
42 | self.syntaxStyle = syntaxStyle | 43 | self.syntaxStyle = syntaxStyle | ||
43 | self.document = document | 44 | self.document = document | ||
44 | 45 | | |||
45 | # Multi-line strings (expression, flag, style) | 46 | # Multi-line strings (expression, flag, style) | ||
46 | # FIXME: The triple-quotes in these two lines will mess up the | 47 | # FIXME: The triple-quotes in these two lines will mess up the | ||
47 | # syntax highlighting from this point onward | 48 | # syntax highlighting from this point onward | ||
48 | self.tri_single = (QRegExp("'''"), 1, self.syntaxStyle['string2']) | 49 | self.tri_single = (QRegExp(r"""'''(?!")"""), 1, 'string2') | ||
49 | self.tri_double = (QRegExp('"""'), 2, self.syntaxStyle['string2']) | 50 | self.tri_double = (QRegExp(r'''"""(?!')'''), 2, 'string2') | ||
50 | 51 | | |||
51 | rules = [] | 52 | rules = [] | ||
52 | 53 | | |||
53 | # Keyword, operator, and brace rules | 54 | # Keyword, operator, and brace rules | ||
54 | rules += [(r'\b%s\b' % w, 0, self.syntaxStyle['keyword']) | 55 | rules += [(r'\b%s\b' % w, 0, 'keyword') | ||
55 | for w in PythonHighlighter.keywords] | 56 | for w in PythonHighlighter.keywords] | ||
56 | rules += [(r'%s' % o, 0, self.syntaxStyle['operator']) | 57 | rules += [(r'%s' % o, 0, 'operator') | ||
57 | for o in PythonHighlighter.operators] | 58 | for o in PythonHighlighter.operators] | ||
58 | rules += [(r'%s' % b, 0, self.syntaxStyle['brace']) | 59 | rules += [(r'%s' % b, 0, 'brace') | ||
59 | for b in PythonHighlighter.braces] | 60 | for b in PythonHighlighter.braces] | ||
60 | 61 | | |||
61 | # All other rules | 62 | # All other rules | ||
62 | rules += [ | 63 | rules += [ | ||
63 | # 'self' | 64 | # 'self' | ||
64 | (r'\bself\b', 0, self.syntaxStyle['self']), | 65 | (r'\bself\b', 0, 'self'), | ||
65 | 66 | | |||
66 | # Double-quoted string, possibly containing escape sequences | 67 | # Double-quoted string, possibly containing escape sequences | ||
67 | (r'"[^"\\]*(\\.[^"\\]*)*"', 0, self.syntaxStyle['string']), | 68 | (r'"[^"\\]*(\\.[^"\\]*)*"', 0, 'string'), | ||
68 | # Single-quoted string, possibly containing escape sequences | 69 | # Single-quoted string, possibly containing escape sequences | ||
69 | (r"'[^'\\]*(\\.[^'\\]*)*'", 0, self.syntaxStyle['string']), | 70 | (r"'[^'\\]*(\\.[^'\\]*)*'", 0, 'string'), | ||
70 | 71 | | |||
71 | # 'def' followed by an identifier | 72 | # 'def' followed by an identifier | ||
72 | (r'\bdef\b\s*(\w+)', 1, self.syntaxStyle['defclass']), | 73 | (r'\bdef\b\s*(\w+)', 1, 'defclass'), | ||
73 | # 'class' followed by an identifier | 74 | # 'class' followed by an identifier | ||
74 | (r'\bclass\b\s*(\w+)', 1, self.syntaxStyle['defclass']), | 75 | (r'\bclass\b\s*(\w+)', 1, 'defclass'), | ||
75 | 76 | | |||
76 | # From '#' until a newline | 77 | # From '#' until a newline | ||
77 | (r'#[^\n]*', 0, self.syntaxStyle['comment']), | 78 | (r'#[^\n]*', 0, 'comment'), | ||
78 | 79 | | |||
79 | # Numeric literals | 80 | # Numeric literals | ||
80 | (r'\b[+-]?[0-9]+[lL]?\b', 0, self.syntaxStyle['numbers']), | 81 | (r'\b[+-]?[0-9]+[lL]?\b', 0, 'numbers'), | ||
81 | (r'\b[+-]?0[xX][0-9A-Fa-f]+[lL]?\b', 0, self.syntaxStyle['numbers']), | 82 | (r'\b[+-]?0[xX][0-9A-Fa-f]+[lL]?\b', 0, 'numbers'), | ||
82 | (r'\b[+-]?[0-9]+(?:\.[0-9]+)?(?:[eE][+-]?[0-9]+)?\b', 0, self.syntaxStyle['numbers']), | 83 | (r'\b[+-]?[0-9]+(?:\.[0-9]+)?(?:[eE][+-]?[0-9]+)?\b', 0, 'numbers'), | ||
83 | ] | 84 | ] | ||
84 | 85 | | |||
85 | # Build a QRegExp for each pattern | 86 | # Build a QRegExp for each pattern | ||
86 | self.rules = [(QRegExp(pat), index, fmt) | 87 | self.rules = [(QRegExp(pat), index, identifier) | ||
87 | for (pat, index, fmt) in rules] | 88 | for (pat, index, identifier) in rules] | ||
88 | 89 | | |||
89 | 90 | | |||
90 | def highlightBlock(self, text): | 91 | def highlightBlock(self, text): | ||
91 | """Apply syntax highlighting to the given block of text. | 92 | """Apply syntax highlighting to the given block of text.""" | ||
92 | """ | | |||
93 | # Do other syntax formatting | 93 | # Do other syntax formatting | ||
94 | for expression, nth, format in self.rules: | 94 | for expression, nth, identifier in self.rules: | ||
95 | index = expression.indexIn(text, 0) | 95 | index = expression.indexIn(text, 0) | ||
96 | 96 | | |||
97 | while index >= 0: | 97 | while index >= 0: | ||
98 | # We actually want the index of the nth match | 98 | # We actually want the index of the nth match | ||
99 | index = expression.pos(nth) | 99 | index = expression.pos(nth) | ||
100 | length = len(expression.cap(nth)) | 100 | length = len(expression.cap(nth)) | ||
101 | self.setFormat(index, length, format) | 101 | self.setFormat(index, length, self.syntaxStyle[identifier]) | ||
102 | index = expression.indexIn(text, index + length) | 102 | index = expression.indexIn(text, index + length) | ||
103 | 103 | | |||
104 | self.setCurrentBlockState(0) | 104 | self.setCurrentBlockState(0) | ||
105 | 105 | | |||
106 | # Do multi-line strings | 106 | # Do multi-line strings | ||
107 | in_multiline = self.match_multiline(text, *self.tri_single) | 107 | in_multiline = self.match_multiline(text, *self.tri_single) | ||
108 | if not in_multiline: | 108 | if not in_multiline: | ||
109 | in_multiline = self.match_multiline(text, *self.tri_double) | 109 | in_multiline = self.match_multiline(text, *self.tri_double) | ||
Show All 24 Lines | 130 | while start >= 0: | |||
134 | if end >= add: | 134 | if end >= add: | ||
135 | length = end - start + add + delimiter.matchedLength() | 135 | length = end - start + add + delimiter.matchedLength() | ||
136 | self.setCurrentBlockState(0) | 136 | self.setCurrentBlockState(0) | ||
137 | # No; multi-line string | 137 | # No; multi-line string | ||
138 | else: | 138 | else: | ||
139 | self.setCurrentBlockState(in_state) | 139 | self.setCurrentBlockState(in_state) | ||
140 | length = len(text) - start + add | 140 | length = len(text) - start + add | ||
141 | # Apply formatting | 141 | # Apply formatting | ||
142 | self.setFormat(start, length, style) | 142 | self.setFormat(start, length, self.syntaxStyle[style]) | ||
143 | # Look for the next match | 143 | # Look for the next match | ||
144 | start = delimiter.indexIn(text, start + length) | 144 | start = delimiter.indexIn(text, start + length) | ||
145 | 145 | | |||
146 | # Return True if still inside a multi-line string, False otherwise | 146 | # Return True if still inside a multi-line string, False otherwise | ||
147 | if self.currentBlockState() == in_state: | 147 | if self.currentBlockState() == in_state: | ||
148 | return True | 148 | return True | ||
149 | else: | 149 | else: | ||
150 | return False | 150 | return False | ||
151 | 151 | | |||
152 | def getSyntaxStyle(self): | 152 | def getSyntaxStyle(self): | ||
153 | return self.syntaxStyle | 153 | return self.syntaxStyle | ||
154 | 154 | | |||
155 | def setSyntaxStyle(self, syntaxStyle): | 155 | def setSyntaxStyle(self, syntaxStyle): | ||
156 | self.syntaxStyle = syntaxStyle | 156 | self.syntaxStyle = syntaxStyle | ||
157 | PythonHighlighter(self.document, self.syntaxStyle) | |