1use crate::lexer::Spanned;
9use crate::token::{
10 Arrow, Color, Corner, Dir, EnvVar, Func1, Func2, LineType, Param, Prim, TextPos,
11};
12
13pub type Macros = std::collections::HashMap<String, Vec<Spanned>>;
16
17pub type Body = Vec<Spanned>;
21
22#[derive(Debug, Clone, PartialEq)]
24pub struct Picture {
25 pub width: Option<Expr>,
26 pub height: Option<Expr>,
27 pub stmts: Vec<Stmt>,
28 pub macros: Macros,
29 pub base_dir: Option<std::path::PathBuf>,
32}
33
34#[derive(Debug, Clone, PartialEq)]
36pub struct Label {
37 pub name: String,
38 pub subscript: Option<Expr>,
39}
40
41#[derive(Debug, Clone, PartialEq)]
43pub enum Stmt {
44 Object {
46 label: Option<Label>,
47 object: Object,
48 },
49 Place { label: Label, pos: Position },
51 Assign(Vec<Assignment>),
53 Direction(Dir),
55 Group(Vec<Stmt>),
57 Animate(Animate),
59 If {
61 cond: Expr,
62 then_body: Body,
63 else_body: Option<Body>,
64 },
65 For {
67 var: String,
68 subscript: Option<Expr>,
69 from: Expr,
70 to: Expr,
71 by: Expr,
72 mult: bool,
74 body: Body,
75 },
76 Print(PrintItem),
78 Exec {
80 command: StringExpr,
81 arg_frame: Option<Vec<Vec<Spanned>>>,
82 },
83 Reset(Vec<EnvVar>),
85}
86
87#[derive(Debug, Clone, PartialEq)]
88pub enum PrintItem {
89 Str(StringExpr),
90 Expr(Expr),
91}
92
93#[derive(Debug, Clone, PartialEq)]
95pub struct Animate {
96 pub target: Place,
97 pub effect: StringExpr,
98 pub duration: Option<Expr>,
99 pub timing: Timing,
100 pub delay: Option<Expr>,
101}
102
103#[derive(Debug, Clone, PartialEq)]
105pub enum Timing {
106 Sequential,
108 At(Expr),
110 After(Place),
112}
113
114#[derive(Debug, Clone, PartialEq)]
116pub struct Assignment {
117 pub target: AssignTarget,
118 pub op: AssignOp,
119 pub value: Expr,
120}
121
122#[derive(Debug, Clone, PartialEq)]
123pub enum AssignTarget {
124 Var(String, Option<Expr>),
125 Env(EnvVar),
126}
127
128#[derive(Debug, Clone, Copy, PartialEq, Eq)]
129pub enum AssignOp {
130 Set, ColonSet, Add, Sub, Mul, Div, Rem, }
138
139#[derive(Debug, Clone, PartialEq)]
141pub struct Object {
142 pub kind: ObjectKind,
143 pub attrs: Vec<Attr>,
144}
145
146#[derive(Debug, Clone, PartialEq)]
147pub enum ObjectKind {
148 Primitive(Prim),
149 Block(Vec<Stmt>),
150 Empty,
152 Text,
154 Continue,
156}
157
158#[derive(Debug, Clone, PartialEq)]
160pub enum Attr {
161 Dim(DimKind, Expr),
162 Direction(Dir, Option<Expr>),
163 Dist(Expr),
166 SplineTension(Expr),
169 LineStyle(LineType, Option<Expr>),
170 Chop(Option<Expr>),
171 Fill(Option<Expr>),
172 Arrowhead(Arrow, Option<Expr>),
173 Then,
174 Cw,
175 Ccw,
176 Same,
177 Continue,
178 Text(StringExpr),
179 TextPos(TextPos),
180 From(Position),
181 To(Position),
182 At(Position),
183 By(Position),
184 With {
185 anchor: WithAnchor,
186 at: Position,
187 },
188 Color(Color, StringExpr),
189}
190
191#[derive(Debug, Clone, Copy, PartialEq, Eq)]
192pub enum DimKind {
193 Ht,
194 Wid,
195 Rad,
196 Diam,
197 Thick,
198 Scaled,
199}
200
201#[derive(Debug, Clone, PartialEq)]
203pub enum WithAnchor {
204 Corner(Corner),
205 Pair(Expr, Expr),
206 Place(Place),
207 Plain,
208}
209
210#[derive(Debug, Clone, PartialEq)]
213pub enum Position {
214 Pair(Expr, Expr),
216 Place(Location),
218 Between {
220 frac: Box<Expr>,
221 a: Box<Position>,
222 b: Box<Position>,
223 of_the_way: bool,
224 },
225 Sum(Sign, Box<Position>, Box<Position>),
227 Scale(Box<Position>, Expr, bool),
229}
230
231#[derive(Debug, Clone, Copy, PartialEq, Eq)]
232pub enum Sign {
233 Plus,
234 Minus,
235}
236
237#[derive(Debug, Clone, PartialEq)]
239pub enum Location {
240 Place(Place),
241 Paren(Box<Position>),
243 ParenPair(Box<Position>, Box<Position>),
245}
246
247#[derive(Debug, Clone, PartialEq)]
249pub enum Place {
250 Name {
252 name: String,
253 subscript: Option<Box<Expr>>,
254 },
255 Nth {
257 count: Nth,
258 obj: PrimObj,
259 },
260 Corner(Box<Place>, Corner),
262 CornerOf(Corner, Box<Place>),
264 Member(Box<Place>, Box<Place>),
266 Here,
267}
268
269#[derive(Debug, Clone, PartialEq)]
270pub enum Nth {
271 Last,
272 Count(Box<Expr>, bool),
274}
275
276#[derive(Debug, Clone, PartialEq)]
277pub enum PrimObj {
278 Prim(Prim),
279 Block,
280 Str(String),
281 EmptyBrack,
282 Any,
285}
286
287#[derive(Debug, Clone, PartialEq)]
289pub enum StringExpr {
290 Lit(String),
291 Concat(Box<StringExpr>, Box<StringExpr>),
292 Sprintf(Box<StringExpr>, Vec<Expr>),
293 SvgFont(Vec<Expr>),
296 Arg(u32),
297}
298
299#[derive(Debug, Clone, PartialEq)]
301pub enum Expr {
302 Num(f64),
303 Str(StringExpr),
306 Index(Vec<Expr>),
308 Var(String, Option<Box<Expr>>),
309 Env(EnvVar),
310 Unary(UnOp, Box<Expr>),
311 Bin(BinOp, Box<Expr>, Box<Expr>),
312 Func1(Func1, Box<Expr>),
313 Func2(Func2, Box<Expr>, Box<Expr>),
314 Rand(Option<Box<Expr>>),
315 Assign(String, Option<Box<Expr>>, Box<Expr>),
317 DotX(Location),
318 DotY(Location),
319 PlaceAttr(Place, Param),
320}
321
322#[derive(Debug, Clone, Copy, PartialEq, Eq)]
323pub enum UnOp {
324 Neg,
325 Pos,
326 Not,
327}
328
329#[derive(Debug, Clone, Copy, PartialEq, Eq)]
330pub enum BinOp {
331 Add,
332 Sub,
333 Mul,
334 Div,
335 Mod,
336 Pow,
337 Eq,
338 Ne,
339 Lt,
340 Le,
341 Gt,
342 Ge,
343 And,
344 Or,
345}