diff --git a/picard/ui/options/scripting.py b/picard/ui/options/scripting.py index 370b79689..e716404b8 100644 --- a/picard/ui/options/scripting.py +++ b/picard/ui/options/scripting.py @@ -32,11 +32,6 @@ class TaggerScriptSyntaxHighlighter(QtGui.QSyntaxHighlighter): self.func_fmt = QtGui.QTextCharFormat() self.func_fmt.setFontWeight(QtGui.QFont.Bold) self.func_fmt.setForeground(QtCore.Qt.blue) - self.noop_re = QtCore.QRegExp(r"\$noop\([^\)]*\)?") - self.noop_fmt = QtGui.QTextCharFormat() - self.noop_fmt.setFontWeight(QtGui.QFont.Bold) - self.noop_fmt.setFontItalic(True) - self.noop_fmt.setForeground(QtCore.Qt.darkGray) self.var_re = QtCore.QRegExp(r"%[_a-zA-Z0-9:]*%") self.var_fmt = QtGui.QTextCharFormat() self.var_fmt.setForeground(QtCore.Qt.darkCyan) @@ -46,15 +41,22 @@ class TaggerScriptSyntaxHighlighter(QtGui.QSyntaxHighlighter): self.special_re = QtCore.QRegExp(r"[^\\][(),]") self.special_fmt = QtGui.QTextCharFormat() self.special_fmt.setForeground(QtCore.Qt.blue) + self.bracket = QtCore.QRegExp(r"[()]") + self.noop_re = QtCore.QRegExp(r"\$noop\(") + self.noop_fmt = QtGui.QTextCharFormat() + self.noop_fmt.setFontWeight(QtGui.QFont.Bold) + self.noop_fmt.setFontItalic(True) + self.noop_fmt.setForeground(QtCore.Qt.darkGray) self.rules = [ (self.func_re, self.func_fmt, 0, -1), - (self.noop_re, self.noop_fmt, 0, 0), (self.var_re, self.var_fmt, 0, 0), (self.escape_re, self.escape_fmt, 0, 0), (self.special_re, self.special_fmt, 1, -1), ] def highlightBlock(self, text): + self.setCurrentBlockState(0) + for expr, fmt, a, b in self.rules: index = expr.indexIn(text) while index >= 0: @@ -62,6 +64,33 @@ class TaggerScriptSyntaxHighlighter(QtGui.QSyntaxHighlighter): self.setFormat(index + a, length + b, fmt) index = expr.indexIn(text, index + length + b) + # Ignore everything if we're already in a noop function + index = self.noop_re.indexIn(text) if self.previousBlockState() <= 0 else 0 + open_brackets = self.previousBlockState() if self.previousBlockState() > 0 else 0 + while index >= 0: + next_index = self.bracket.indexIn(text, index) + + # Skip escaped brackets + if (next_index > 0) and text[next_index - 1] == '\\': + next_index += 1 + + if (next_index > -1) and text[next_index] == '(': + open_brackets += 1 + elif (next_index > -1) and text[next_index] == ')': + open_brackets -= 1 + + if (next_index > -1): + self.setFormat(index, next_index - index + 1, self.noop_fmt) + elif (next_index == -1) and (open_brackets > 0): + self.setFormat(index, len(text) - index, self.noop_fmt) + + # Check for next noop operation, necessary for multiple noops in one line + if open_brackets == 0: + next_index = self.noop_re.indexIn(text, next_index) + + index = next_index + 1 if (next_index > -1) and (next_index < len(text)) else -1 + + self.setCurrentBlockState(open_brackets) class ScriptingOptionsPage(OptionsPage):