@before { self.statementTerminator = @";"; self.singleLineCommentMarker = nil; self.multiLineCommentStartMarker = @"(:"; self.multiLineCommentEndMarker = @":)"; self.blockStartMarker = @"{"; self.blockEndMarker = @"}"; self.braces = @"( ) [ ] < > (: :)"; PKTokenizer *t = self.tokenizer; [t.symbolState add:@"//"]; [t.symbolState add:@".."]; [t.symbolState add:@":="]; [t.symbolState add:@"!="]; [t.symbolState add:@"::"]; [t.symbolState add:@"<="]; [t.symbolState add:@"=>"]; [t.symbolState add:@"(:"]; [t.symbolState add:@":)"]; NSMutableCharacterSet *cs = [[NSCharacterSet alphanumericCharacterSet] mutableCopy]; [cs addCharactersInString:@"_"]; [t.delimitState addStartMarker:@"$" endMarker:@"" allowedCharacterSet:cs]; [t setTokenizerState:t.delimitState from:'$' to:'$']; [t setTokenizerState:t.wordState from:'_' to:'_']; [t.wordState setWordChars:YES from:'-' to:'-']; [t.wordState setWordChars:YES from:'_' to:'_']; [t.wordState setWordChars:YES from:'.' to:'.']; [t.wordState setWordChars:NO from:'\\'' to:'\\'']; [t setTokenizerState:t.symbolState from:'-' to:'-']; [t setTokenizerState:t.numberState from:'.' to:'.']; [t setTokenizerState:t.numberState from:'#' to:'#']; t.numberState.allowsScientificNotation = YES; [t setTokenizerState:t.symbolState from:'/' to:'/']; // setup comments t.commentState.reportsCommentTokens = YES; [t.commentState addMultiLineStartMarker:@"(:" endMarker:@":)"]; [t setTokenizerState:t.commentState from:'(' to:'(']; [t setTokenizerState:t.commentState from:':' to:':']; [t.commentState setFallbackState:t.symbolState from:'(' to:'(']; [t.commentState setFallbackState:t.symbolState from:':' to:':']; } expr = token*; token = colon | assign | eq | ne | dot | lt | gt | separators | operators | star | braces | comment | variable | keyword | builtin | functionName | axisName | string | number | ncName; comment = Comment; colon = ':'; assign = ':='; eq = '='; ne = '!='; dot = singleDot | doubleDot; singleDot = '.'; doubleDot = '..'; lt = '<'; gt = '>'; separators = slash | doubleSlash | axisSep; slash = '/'; doubleSlash = '//'; axisSep = '::'; operators = or | and | div | mod | pipe | comma | plus | minus | question | le | ge; or = 'or'; and = 'and'; div = 'div'; mod = 'mod'; pipe = '|'; comma = ','; plus = '+'; minus = '-'; question = '?'; le = '<='; ge = '>='; star = '*'; braces = openParen | closeParen | openSquare | closeSquare | openCurly | closeCurly | symbol; openParen = '('; closeParen = ')'; openSquare = '['; closeSquare = ']'; openCurly = '{'; closeCurly = '}'; symbol = Symbol; variable = %{'$', ''}; keyword = function | declare | if | then | else | switch | case | default | for | at | in | let | to | where | order | by | ascending | descending | return | some | every | satisfies | intersect | union | except | valLt | valGt | valLe | valGe | valEq | valNe; function = 'function'; declare = 'declare'; if = 'if'; then = 'then'; else = 'else'; switch = 'switch'; case = 'case'; default = 'default'; for = 'for'; at = 'at'; in = 'in'; let = 'let'; to = 'to'; where = 'where'; order = 'order'; by = 'by'; ascending = 'ascending'; descending = 'descending'; return = 'return'; some = 'some'; every = 'every'; satisfies = 'satisfies'; intersect = 'intersect'; union = 'union'; except = 'except'; valEq = 'eq'; valNe = 'ne'; valLt = 'lt'; valGt = 'gt'; valLe = 'le'; valGe = 'ge'; builtin = commentSym | textSym | piSym | node | booleanLiteral; commentSym = 'comment'; textSym = 'text'; piSym = 'processing-instruction'; node = 'node'; booleanLiteral = true | false; true = 'true'; false = 'false'; functionName = absFn | avgFn | booleanFn | ceilingFn | compareFn | concatFn | containsFn | countFn | dataFn | distinctValuesFn | emptyFn | endsWithFn | existsFn | floorFn | headFn | idFn | indexOfFn | insertBeforeFn | langFn | lastFn | localNameFn | lowerCaseFn | matchesFn | maxFn | minFn | nameFn | namespaceUriFn | normalizeSpaceFn | normalizeUnicodeFn | notFn | numberFn | positionFn | removeFn | replaceFn | reverseFn | roundFn | startsWithFn | stringFn | stringJoinFn | stringLengthFn | subsequenceFn | substringFn | substringAfterFn | substringBeforeFn | sumFn | tailFn | traceFn | translateFn | trimSpaceFn | titleCaseFn | upperCaseFn ; absFn = 'abs'; avgFn = 'avg'; booleanFn = 'boolean'; ceilingFn = 'ceiling'; compareFn = 'compare'; concatFn = 'concat'; containsFn = 'contains'; countFn = 'count'; dataFn = 'data'; distinctValuesFn = 'distinct-values'; emptyFn = 'empty'; endsWithFn = 'ends-with'; existsFn = 'exists'; floorFn = 'floor'; headFn = 'head'; idFn = 'id'; indexOfFn = 'index-of'; insertBeforeFn = 'insert-before'; langFn = 'lang'; lastFn = 'last'; localNameFn = 'local-name'; lowerCaseFn = 'lower-case'; matchesFn = 'matches'; maxFn = 'max'; minFn = 'min'; nameFn = 'name'; namespaceUriFn = 'namespace-uri'; normalizeSpaceFn = 'normalize-space'; normalizeUnicodeFn = 'normalize-unicode'; notFn = 'not'; numberFn = 'number'; positionFn = 'position'; removeFn = 'remove'; replaceFn = 'replace'; roundFn = 'round'; reverseFn = 'reverse'; startsWithFn = 'starts-with'; stringFn = 'string'; stringJoinFn = 'string-join'; stringLengthFn = 'string-length'; subsequenceFn = 'subsequence'; substringFn = 'substring'; substringAfterFn = 'substring-after'; substringBeforeFn = 'substring-before'; sumFn = 'sum'; tailFn = 'tail'; traceFn = 'trace'; translateFn = 'translate'; trimSpaceFn = 'trim-space'; titleCaseFn = 'title-case'; upperCaseFn = 'upper-case'; axisName = atSym | 'ancestor' | 'ancestor-or-self' | 'attribute' | 'child' | 'descendant' | 'descendant-or-self' | 'following' | 'following-sibling' | 'namespace' | 'parent' | 'preceding' | 'preceding-sibling' | 'self'; atSym = '@'; string = QuotedString; number = Number; ncName = Word; /*attrNCName = Word;*/