       else if c == '←' then 'apl-asgn'
       else if c == "'" then (if stream.match /^(?:[^'\r\n]|'')*'/ then 'apl-str' else stream.skipToEnd(); 'apl-err')
       else if c == '⍬' then 'apl-zld'
-      else if c == '(' then state.stack += c; 'apl-par'
-      else if c == '[' then state.stack += c; 'apl-sqbr'
-      else if c == '{' then state.stack += c; state.indentStack.push stream.indentation(); "apl-dfn#{++state.dfnDepth} apl-dfn"
-      else if c == ')' then (if state.stack[-1..] == '(' then state.stack = state.stack[...-1]; 'apl-par'  else 'apl-err')
-      else if c == ']' then (if state.stack[-1..] == '[' then state.stack = state.stack[...-1]; 'apl-sqbr' else 'apl-err')
+      else if c == '(' then state.brs += c; 'apl-par'
+      else if c == '[' then state.brs += c; 'apl-sqbr'
+      else if c == '{' then state.brs += c; state.inds.push stream.indentation(); "apl-dfn#{++state.dfnDepth} apl-dfn"
+      else if c == ')' then (if state.brs[-1..] == '(' then state.brs = state.brs[...-1]; 'apl-par'  else 'apl-err')
+      else if c == ']' then (if state.brs[-1..] == '[' then state.brs = state.brs[...-1]; 'apl-sqbr' else 'apl-err')
       else if c == '}'
-        if state.stack[-1..] == '{'
-          state.stack = state.stack[...-1]; state.indentStack.pop(); "apl-dfn apl-dfn#{state.dfnDepth--}"
+        if state.brs[-1..] == '{'
+          state.brs = state.brs[...-1]; state.inds.pop(); "apl-dfn apl-dfn#{state.dfnDepth--}"
         else
           'apl-err'
       else if c == ';' then 'apl-semi'

idiomsRE = ///^(?:#{idioms.sort((x, y) -> y.length - x.length).map(escIdiom).join '|'})///i

CodeMirror.defineMIME 'text/apl', 'apl'
CodeMirror.defineMode 'apl', (config) -> # https://codemirror.net/doc/manual.html#modeapi
  startState: -> isHeader: 1, stack: '', dfnDepth: 0, kwStack: [], indentStack: []
  token: (stream, state) ->
    if state.isHeader
      delete state.isHeader; stream.match /[^⍝\n\r]*/; s = stream.current()
      if dfnHeader.test s
        stream.backUp s.length # re-tokenize without isHeader
      else if /^\s*$/.test s
        delete state.vars
      else

{qw} = require './util'

# https://codemirror.net/doc/manual.html#modeapi

letter = @letter = 'A-Z_a-zÀ-ÖØ-Ýß-öø-üþ∆⍙Ⓐ-Ⓩ'
name0 = ///[#{letter}]///
