comparison pygments_lexer_pseudocode2/algpseudocode.py @ 53:39151225fb84

Rename the new pseudocode implementation to AlgPseudocode. Because it is modelled after CTAN's algpseudocode(x).
author Franz Glasner <fzglas.hg@dom66.de>
date Sun, 26 Apr 2026 19:16:23 +0200
parents pygments_lexer_pseudocode2/pseudocode.py@5bfa9113d3c4
children e8f4af9e20a8
comparison
equal deleted inserted replaced
52:5bfa9113d3c4 53:39151225fb84
1
2 # -*- coding: utf-8 -*-
3 # :-
4 # SPDX-FileCopyrightText: © 2026 Franz Glasner
5 # SPDX-License-Identifier: MIT
6 # :-
7 r"""A pseudocode lexer along the lines of CTAN's algpseudocode or
8 algpseudocodex.
9
10 """
11
12 __all__ = ["AlgPseudocodeLexer",
13 "AlgPseudocodeLexer_DE", "AlgPseudocodeLexer_FR"]
14
15
16 import re
17
18 from pygments.lexer import include, bygroups
19 from pygments.token import (Comment, Keyword, Name, Text, Whitespace)
20
21 #
22 # Relative imports do not work with pygments.lexers.load_lexer_from_file()
23 # in all of our supported Python releases.
24 #
25 from pygments_lexer_pseudocode2.bases import LexBase
26
27
28 class AlgPseudocodeLexer(LexBase):
29
30 """A pseudocode lexer along the lines of CTAN's algpseudocode or
31 algpseudocodex.
32
33 Some ideas (e.g. strings) are borrowed from Pygment's Python lexer.
34
35 """
36
37 name = "AlgPseudocode"
38 aliases = ["algpseudocode", "algpseudo"]
39 filenames = ["*.algpseudo", "*.algpseudocode"]
40 mimetypes = []
41 flags = re.MULTILINE
42
43 LANG = "en"
44 TRANSLATIONS = {
45 "PROG": "PROGRAM",
46 "PROGRAM": "PROGRAM",
47 "ALGO": "ALGORITHM",
48 "ALGORITHM": "ALGORITHM",
49 "PROC": "PROCEDURE",
50 "PROCEDURE": "PROCEDURE",
51 "FUNC": "FUNCTION",
52 "FUNCTION": "FUNCTION",
53 "FN": "FUNCTION",
54 "CLASS": "CLASS",
55 }
56 SYMBOLS = {
57 "REMARK": "▷", # U+25B7: Unicode 1.0 (Arrows)
58 "Remark": "▷",
59 "remark": "▷",
60 "REM": "▷",
61 "Rem": "▷",
62 "rem": "▷",
63 "R": "▷",
64 "r": "▷",
65 "BLOCK": "┃", # U+2503: Unicode 1.0 (Bow Drawing)
66 "Block": "┃",
67 "block": "┃",
68 }
69
70 def op_translate(toktype):
71
72 def _op_translate(lexer, match, ctx=None):
73 kw = match.group().upper()
74 yield match.start(), toktype, lexer.TRANSLATIONS.get(kw, kw)
75
76 return _op_translate
77
78 def op_symbol(toktype):
79
80 def _op_symbol(lexer, match, ctx=None):
81 kw = match.group()
82 yield match.start(), toktype, lexer.SYMBOLS.get(kw, kw)
83
84 return _op_symbol
85
86 tokens = {
87 "root": [
88 (r"\n", Whitespace),
89 (r"/\*", Comment.Multiline, "multiline-nested-comment"),
90 (r"//.*$", Comment.Single),
91 (r"(?:\\)(REMARK|Remark|remark|REM|Rem|rem|R|r)\b(.*)$",
92 bygroups(op_symbol(Comment.Single), Comment.Single)),
93 (r"(?:\\)(BLOCK|Block|block)\b(.*)$",
94 bygroups(op_symbol(Text), Text)),
95 (r"\\\n", Text),
96 (r"(?i)\\("
97 r"(?:prog(?:ram)?)"
98 r"|(?:algo(?:rithm)?)"
99 r"|(?:proc(?:edure)?)"
100 r"|(?:func(?:tion)?|(?:fn))"
101 r"|(?:class)"
102 r")(\s*)(\{)",
103 bygroups(op_translate(Keyword), Whitespace, Name.Entity),
104 "entity-name"),
105 include("expr"),
106 (r"\s+", Text),
107 ],
108 "entity-name": [ # may be multiline
109 (r"[^\\}]+", Name.Entity),
110 (r"\\\}", Name.Entity),
111 (r"\\", Name.Entity),
112 (r"\}", Name.Entity, "#pop"),
113 ],
114 "expr": [
115 include("py-strings"),
116 include("py-numbers"),
117 include("py-name"),
118 ]
119 }
120
121
122 class AlgPseudocodeLexer_DE(AlgPseudocodeLexer):
123
124 name = "AlgPseudocodeDE"
125 aliases = ["algpseudocode-de", "algpseudo-de"]
126 filenames = ["*.algpseudo-de", "*.algpseudocode-de"]
127
128 LANG = "de"
129 TRANSLATIONS = AlgPseudocodeLexer.TRANSLATIONS.copy()
130 TRANSLATIONS.update({
131 "PROG": "PROGRAMM",
132 "PROGRAM": "PROGRAMM",
133 "ALGO": "ALGORITHMUS",
134 "ALGORITHM": "ALGORITHMUS",
135 "PROC": "PROZEDUR",
136 "PROCEDURE": "PROZEDUR",
137 "FUNC": "FUNKTION",
138 "FUNCTION": "FUNKTION",
139 "FN": "FUNKTION",
140 "CLASS": "KLASSE",
141 })
142
143
144 class AlgPseudocodeLexer_FR(AlgPseudocodeLexer):
145
146 name = "AlgPseudocodeFR"
147 aliases = ["algpseudocode-fr", "algpseudo-fr"]
148 filenames = ["*.algpseudo-fr", "*.algpseudocode-fr"]
149
150 LANG = "de"
151 TRANSLATIONS = AlgPseudocodeLexer.TRANSLATIONS.copy()
152 TRANSLATIONS.update({
153 "PROG": "PROGRAMME",
154 "PROGRAM": "PROGRAMME",
155 "ALGO": "ALGORITHME",
156 "ALGORITHM": "ALGORITHME",
157 "PROC": "PROCÉDURE",
158 "PROCEDURE": "PROCÉDURE",
159 "FUNC": "FONCTION",
160 "FUNCTION": "FOUNCTION",
161 "FN": "FONCTION",
162 "CLASS": "CLASSE",
163 })