comparison pygments_lexer_pseudocode2/algpseudocode.py @ 160:b4028838e0c8

Implement lexer option "prohibit_raiseonerror_filter". Sphinx raises by default when an Error token is seen (by means of the "raiseonerror" filter that is applied by default to lexers in Sphinx). This option skips this and allows error locations to be seen and highlighted properly. While there convert most Generic.Error tokens to Error tokens because now they can be handled by a lexer with "prohibit_raiseonerror_filter=True".
author Franz Glasner <fzglas.hg@dom66.de>
date Fri, 08 May 2026 17:46:28 +0200
parents 4ee0b1536ea6
children 00a432d14508
comparison
equal deleted inserted replaced
159:4ee0b1536ea6 160:b4028838e0c8
15 import logging 15 import logging
16 import re 16 import re
17 17
18 import pygments.util 18 import pygments.util
19 from pygments.lexer import bygroups, include, words 19 from pygments.lexer import bygroups, include, words
20 from pygments.token import (Comment, Generic, Keyword, Name, Operator, 20 from pygments.token import (Comment, Error, Generic, Keyword, Name, Operator,
21 Punctuation, Text, Whitespace) 21 Punctuation, Text, Whitespace)
22 22
23 # 23 #
24 # Relative imports do not work with pygments.lexers.load_lexer_from_file() 24 # Relative imports do not work with pygments.lexers.load_lexer_from_file()
25 # in all of our supported Python releases. 25 # in all of our supported Python releases.
332 bygroups(op_translate(Keyword))), 332 bygroups(op_translate(Keyword))),
333 include("expr"), 333 include("expr"),
334 include("unicode-separators"), 334 include("unicode-separators"),
335 include("unicode-other"), 335 include("unicode-other"),
336 (r"[^\S\n]+", Text), 336 (r"[^\S\n]+", Text),
337 (r".", Generic.Error), # tolerance for errors 337 # (r".", Generic.Error), # tolerance for errors
338 (r".", Error),
338 ], 339 ],
339 "remark": [ 340 "remark": [
340 (r"(?i)\\(remark|rem)\b(.*)$", 341 (r"(?i)\\(remark|rem)\b(.*)$",
341 bygroups(op_remark, Comment.Single)), 342 bygroups(op_remark, Comment.Single)),
342 ], 343 ],
395 (r"\\\\", LexBase.op_fixed(Text, "\\")), 396 (r"\\\\", LexBase.op_fixed(Text, "\\")),
396 (r"\\", LexBase.op_fixed(Text, "\\")), 397 (r"\\", LexBase.op_fixed(Text, "\\")),
397 include("unicode-separators"), 398 include("unicode-separators"),
398 include("unicode-other"), 399 include("unicode-other"),
399 (r"[^\S\n]+", Text), 400 (r"[^\S\n]+", Text),
400 (r".", Generic.Error), # tolerance for errors 401 (r".", Error),
401 ], 402 ],
402 "text-statement": [ # like block but default to text-mode 403 "text-statement": [ # like block but default to text-mode
403 (r"[^\\}\n]+", Text), 404 (r"[^\\}\n]+", Text),
404 (r"\}", LexBase.op_ignore, "#pop"), 405 (r"\}", LexBase.op_ignore, "#pop"),
405 (r"\n", Whitespace), 406 (r"\n", Whitespace),
409 "block-expr"), 410 "block-expr"),
410 include("explicit-tokentype"), 411 include("explicit-tokentype"),
411 include("remark"), 412 include("remark"),
412 (r"\\\\", LexBase.op_fixed(Text, "\\")), 413 (r"\\\\", LexBase.op_fixed(Text, "\\")),
413 (r"\\", LexBase.op_fixed(Text, "\\")), 414 (r"\\", LexBase.op_fixed(Text, "\\")),
414 (r".", Generic.Error), # tolerance for errors 415 (r".", Error),
415 ], 416 ],
416 "text-in-expr": [ 417 "text-in-expr": [
417 (r"[^\\}\n]+", Text), 418 (r"[^\\}\n]+", Text),
418 (r"\}", LexBase.op_ignore, "#pop"), 419 (r"\}", LexBase.op_ignore, "#pop"),
419 (r"\n", Whitespace), 420 (r"\n", Whitespace),
423 "block-expr"), 424 "block-expr"),
424 include("explicit-tokentype"), 425 include("explicit-tokentype"),
425 include("remark"), 426 include("remark"),
426 (r"\\\\", LexBase.op_fixed(Text, "\\")), 427 (r"\\\\", LexBase.op_fixed(Text, "\\")),
427 (r"\\", LexBase.op_fixed(Text, "\\")), 428 (r"\\", LexBase.op_fixed(Text, "\\")),
428 (r".", Generic.Error), # tolerance for errors 429 (r".", Error),
429 ], 430 ],
430 "math-builtins": [ 431 "math-builtins": [
431 (words(("sqrt", "pow", "cos", "sin", "tan", "arcos", "arcsin", 432 (words(("sqrt", "pow", "cos", "sin", "tan", "arcos", "arcsin",
432 "arctan", "arctan2", "mod", "exp", "ln", "log", 433 "arctan", "arctan2", "mod", "exp", "ln", "log",
433 "min", "max"), 434 "min", "max"),
523 self.symbol_gets = self.SYMBOLS["<-"] # Default: "⟵" # U+27F5 524 self.symbol_gets = self.SYMBOLS["<-"] # Default: "⟵" # U+27F5
524 self.symbol_remark = options.get("remark", None) 525 self.symbol_remark = options.get("remark", None)
525 if self.symbol_remark is None: 526 if self.symbol_remark is None:
526 self.symbol_remark = self.SYMBOLS["REM"] # Default: "▷" # U+25B7 527 self.symbol_remark = self.SYMBOLS["REM"] # Default: "▷" # U+25B7
527 LexBase.__init__(self, **options) 528 LexBase.__init__(self, **options)
529 #
530 # Do this after calling the base because a "filters" option should be
531 # allowed to set **any** filter.
532 #
533 self.prohibit_raiseonerror_filter = pygments.util.get_bool_opt(
534 options, "prohibit_raiseonerror_filter", default=False)
535
536 def add_filter(self, filter_, **options):
537 #
538 # May be called by Lexer.__init__ when self.prohibit_raiseonerror_filter
539 # is not yet set. This is intentionally so.
540 #
541 if getattr(self, "prohibit_raiseonerror_filter", False):
542 if filter_ in ("raiseonerror",):
543 return
544 LexBase.add_filter(self, filter_, **options)
528 545
529 546
530 class AlgPseudocodeLexer_DE(AlgPseudocodeLexer): 547 class AlgPseudocodeLexer_DE(AlgPseudocodeLexer):
531 548
532 """ 549 """