home
readme
diff
tree
note
docs
0commit e402f1d7283ac8891fb9966d4af80aea3f6c4d80
1Author: Mason Wright <mason@lakefox.net>
2Date: Fri Nov 7 15:03:16 2025 -0700
3
4 added readme
5
6diff --git a/README.txt b/README.txt
7new file mode 100644
8index 0000000..4e735d7
9--- /dev/null
10+++ b/README.txt
11@@ -0,0 +1 @@
12+Grim
13diff --git a/include/grim.h b/include/grim.h
14index e67414f..4fd2493 100755
15--- a/include/grim.h
16+++ b/include/grim.h
17@@ -71,10 +71,13 @@ class Attribute {
18 };
19 };
20
21+class Window;
22+
23 class Node {
24 private:
25 std::string TagName;
26 std::unordered_map<std::string, std::string> attributes;
27+ Window* window;
28 public:
29 Node* parent;
30 std::vector<std::unique_ptr<Node>> children;
31@@ -135,17 +138,85 @@ class Node {
32 std::string print(int indent = 0);
33 };
34
35-class Document {
36- public:
37- Node* body;
38- //location;
39-};
40-
41 std::vector<std::vector<std::string>> parseSelectorParts(std::string_view);
42
43 bool testSelector(Node*, std::vector<std::vector<std::string>>);
44
45-enum class UnitType : char {
46+enum class KeyType : short {
47+ ACCENT_COLOR, ALIGN_CONTENT, ALIGN_ITEMS, ALIGN_SELF, ALIGNMENT_BASELINE, ALL, ANCHOR_NAME, ANIMATION_COMPOSITION, ANIMATION_DELAY,
48+ ANIMATION_DIRECTION, ANIMATION_DURATION, ANIMATION_FILL_MODE, ANIMATION_ITERATION_COUNT, ANIMATION_NAME, ANIMATION_PLAY_STATE, ANIMATION_RANGE_END,
49+ ANIMATION_RANGE_START, ANIMATION_RANGE, ANIMATION_TIMELINE, ANIMATION_TIMING_FUNCTION, ANIMATION, APPEARANCE, ASPECT_RATIO,
50+ BACKDROP_FILTER, BACKFACE_VISIBILITY, BACKGROUND_ATTACHMENT, BACKGROUND_BLEND_MODE, BACKGROUND_CLIP, BACKGROUND_COLOR, BACKGROUND_IMAGE,
51+ BACKGROUND_ORIGIN, BACKGROUND_POSITION_X, BACKGROUND_POSITION_Y, BACKGROUND_POSITION, BACKGROUND_REPEAT, BACKGROUND_SIZE, BACKGROUND,
52+ BLOCK_SIZE, BORDER_BLOCK_COLOR, BORDER_BLOCK_END_COLOR, BORDER_BLOCK_END_STYLE, BORDER_BLOCK_END_WIDTH, BORDER_BLOCK_END,
53+ BORDER_BLOCK_START_COLOR, BORDER_BLOCK_START_STYLE, BORDER_BLOCK_START_WIDTH, BORDER_BLOCK_START, BORDER_BLOCK_STYLE, BORDER_BLOCK_WIDTH,
54+ BORDER_BLOCK, BORDER_BOTTOM_COLOR, BORDER_BOTTOM_LEFT_RADIUS, BORDER_BOTTOM_RIGHT_RADIUS, BORDER_BOTTOM_STYLE, BORDER_BOTTOM_WIDTH,
55+ BORDER_BOTTOM, BORDER_COLLAPSE, BORDER_COLOR, BORDER_END_END_RADIUS, BORDER_END_START_RADIUS, BORDER_IMAGE_OUTSET, BORDER_IMAGE_REPEAT,
56+ BORDER_IMAGE_SLICE, BORDER_IMAGE_SOURCE, BORDER_IMAGE_WIDTH, BORDER_IMAGE, BORDER_INLINE_COLOR, BORDER_INLINE_END_COLOR, BORDER_INLINE_END_STYLE,
57+ BORDER_INLINE_END_WIDTH, BORDER_INLINE_END, BORDER_INLINE_START_COLOR, BORDER_INLINE_START_STYLE, BORDER_INLINE_START_WIDTH, BORDER_INLINE_START,
58+ BORDER_INLINE_STYLE, BORDER_INLINE_WIDTH, BORDER_INLINE, BORDER_LEFT_COLOR, BORDER_LEFT_STYLE, BORDER_LEFT_WIDTH, BORDER_LEFT, BORDER_RADIUS,
59+ BORDER_RIGHT_COLOR, BORDER_RIGHT_STYLE, BORDER_RIGHT_WIDTH, BORDER_RIGHT, BORDER_SPACING, BORDER_START_END_RADIUS, BORDER_START_START_RADIUS,
60+ BORDER_STYLE, BORDER_TOP_COLOR, BORDER_TOP_LEFT_RADIUS, BORDER_TOP_RIGHT_RADIUS, BORDER_TOP_STYLE, BORDER_TOP_WIDTH, BORDER_TOP, BORDER_WIDTH,
61+ BORDER, BOTTOM, BOX_ALIGN, BOX_DECORATION_BREAK, BOX_DIRECTION, BOX_FLEX_GROUP, BOX_FLEX, BOX_LINES, BOX_ORDINAL_GROUP, BOX_ORIENT, BOX_PACK,
62+ BOX_SHADOW, BOX_SIZING, BREAK_AFTER, BREAK_BEFORE, BREAK_INSIDE,
63+ CAPTION_SIDE, CARET_COLOR, CLEAR, CLIP_PATH, CLIP_RULE, CLIP, COLOR_INTERPOLATION_FILTERS, COLOR_INTERPOLATION, COLOR_SCHEME, COLOR, COLUMN_COUNT,
64+ COLUMN_FILL, COLUMN_GAP, COLUMN_RULE_COLOR, COLUMN_RULE_STYLE, COLUMN_RULE_WIDTH, COLUMN_RULE, COLUMN_SPAN, COLUMN_WIDTH, COLUMNS,
65+ CONTAIN_INTRINSIC_BLOCK_SIZE, CONTAIN_INTRINSIC_HEIGHT, CONTAIN_INTRINSIC_INLINE_SIZE, CONTAIN_INTRINSIC_SIZE, CONTAIN_INTRINSIC_WIDTH,
66+ CONTAIN, CONTAINER_NAME, CONTAINER_TYPE, CONTAINER, CONTENT_VISIBILITY, CONTENT, COUNTER_INCREMENT, COUNTER_RESET, COUNTER_SET, CURSOR,
67+ CX, CY,
68+ D, DIRECTION, DISPLAY, DOMINANT_BASELINE,
69+ EMPTY_CELLS,
70+ FIELD_SIZING, FILL_OPACITY, FILL_RULE, FILL, FILTER, FLEX_BASIS, FLEX_DIRECTION, FLEX_FLOW, FLEX_GROW, FLEX_SHRINK, FLEX_WRAP, FLEX,
71+ FLOAT, FLOOD_COLOR, FLOOD_OPACITY, FONT_FAMILY, FONT_FEATURE_SETTINGS, FONT_KERNING, FONT_LANGUAGE_OVERRIDE, FONT_OPTICAL_SIZING, FONT_PALETTE,
72+ FONT_SIZE_ADJUST, FONT_SIZE, FONT_SMOOTH, FONT_STRETCH, FONT_STYLE, FONT_SYNTHESIS_POSITION, FONT_SYNTHESIS_SMALL_CAPS, FONT_SYNTHESIS_STYLE,
73+ FONT_SYNTHESIS_WEIGHT, FONT_SYNTHESIS, FONT_VARIANT_ALTERNATES, FONT_VARIANT_CAPS, FONT_VARIANT_EAST_ASIAN, FONT_VARIANT_EMOJI, FONT_VARIANT_LIGATURES,
74+ FONT_VARIANT_NUMERIC, FONT_VARIANT_POSITION, FONT_VARIANT, FONT_VARIATION_SETTINGS, FONT_WEIGHT, FONT, FORCED_COLOR_ADJUST,
75+ GAP, GRID_AREA, GRID_AUTO_COLUMNS, GRID_AUTO_FLOW, GRID_AUTO_ROWS, GRID_COLUMN_END, GRID_COLUMN_START, GRID_COLUMN, GRID_ROW_END, GRID_ROW_START,
76+ GRID_ROW, GRID_TEMPLATE_AREAS, GRID_TEMPLATE_COLUMNS, GRID_TEMPLATE_ROWS, GRID_TEMPLATE, GRID,
77+ HANGING_PUNCTUATION, HEIGHT, HYPHENATE_CHARACTER, HYPHENATE_LIMIT_CHARS, HYPHENS,
78+ IMAGE_ORIENTATION, IMAGE_RENDERING, IMAGE_RESOLUTION, INITIAL_LETTER, INLINE_SIZE, INSET_BLOCK_START, INSET_BLOCK_END, INSET_BLOCK,
79+ INSET_INLINE_END, INSET_INLINE_START, INSET_INLINE, INSET, INTERPOLATE_SIZE, ISOLATION,
80+ JUSTIFY_CONTENT, JUSTIFY_ITEMS, JUSTIFY_SELF,
81+ LEFT, LETTER_SPACING, LIGHTING_COLOR, LINE_BREAK, LINE_CLAMP, LINE_HEIGHT_STEP, LINE_HEIGHT, LIST_STYLE_IMAGE, LIST_STYLE_POSITION, LIST_STYLE_TYPE,
82+ LIST_STYLE,
83+ MARGIN_BLOCK_END, MARGIN_BLOCK_START, MARGIN_BLOCK, MARGIN_BOTTOM, MARGIN_INLINE_END, MARGIN_INLINE_START, MARGIN_INLINE, MARGIN_LEFT, MARGIN_RIGHT,
84+ MARGIN_TOP, MARGIN_TRIM, MARGIN, MARKER_END, MARKER_MID, MARKER_START, MARKER, MASK_BORDER_MODE, MASK_BORDER_OUTSET, MASK_BORDER_REPEAT, MASK_BORDER_SLICE,
85+ MASK_BORDER_SOURCE, MASK_BORDER_WIDTH, MASK_BORDER, MASK_CLIP, MASK_COMPOSITE, MASK_IMAGE, MASK_MODE, MASK_ORIGIN, MASK_POSITION, MASK_REPEAT,
86+ MASK_SIZE, MASK_TYPE, MASK, MATH_DEPTH, MATH_SHIFT, MATH_STYLE, MAX_BLOCK_SIZE, MAX_HEIGHT, MAX_INLINE_SIZE, MAX_WIDTH, MIN_BLOCK_SIZE,
87+ MIN_HEIGHT, MIN_INLINE_SIZE, MIN_WIDTH, MIX_BLEND_MODE,
88+ OBJECT_FIT, OBJECT_POSITION, OFFSET_ANCHOR, OFFSET_DISTANCE, OFFSET_PATH, OFFSET_POSITION, OFFSET_ROTATE, OFFSET, OPACITY, ORDER, ORPHANS,
89+ OUTLINE_COLOR, OUTLINE_OFFSET, OUTLINE_STYLE, OUTLINE_WIDTH, OUTLINE, OVERFLOW_ANCHOR, OVERFLOW_BLOCK, OVERFLOW_CLIP_MARGIN, OVERFLOW_INLINE,
90+ OVERFLOW_WRAP, OVERFLOW_X, OVERFLOW_Y, OVERFLOW, OVERLAY, OVERSCROLL_BEHAVIOR_BLOCK, OVERSCROLL_BEHAVIOR_INLINE, OVERSCROLL_BEHAVIOR_X,
91+ OVERSCROLL_BEHAVIOR_Y, OVERSCROLL_BEHAVIOR,
92+ PADDING_BLOCK_END, PADDING_BLOCK_START, PADDING_BLOCK, PADDING_BOTTOM, PADDING_INLINE_END, PADDING_INLINE_START, PADDING_INLINE, PADDING_LEFT,
93+ PADDING_RIGHT, PADDING_TOP, PADDING, PAGE_BREAK_AFTER, PAGE_BREAK_BEFORE, PAGE_BREAK_INSIDE, PAGE, PAINT_ORDER, PERSPECTIVE_ORIGIN, PERSPECTIVE,
94+ PLACE_CONTENT, PLACE_ITEMS, PLACE_SELF, POINTER_EVENTS, POSITION_ANCHOR, POSITION_AREA, POSITION_TRY_FALLBACKS, POSITION_TRY_ORDER, POSITION_TRY,
95+ POSITION_VISIBILITY, POSITION, PRINT_COLOR_ADJUST,
96+ QUOTES,
97+ R, READING_FLOW, READING_ORDER, RESIZE, RIGHT, ROTATE, ROW_GAP, RUBY_ALIGN, RUBY_POSITION, RX, RY,
98+ SCALE, SCROLL_BEHAVIOR, SCROLL_MARGIN_BLOCK_END, SCROLL_MARGIN_BLOCK_START, SCROLL_MARGIN_BLOCK, SCROLL_MARGIN_BOTTOM, SCROLL_MARGIN_INLINE_END,
99+ SCROLL_MARGIN_INLINE_START, SCROLL_MARGIN_INLINE, SCROLL_MARGIN_LEFT, SCROLL_MARGIN_RIGHT, SCROLL_MARGIN_TOP, SCROLL_MARGIN, SCROLL_MARKER_GROUP,
100+ SCROLL_PADDING_BLOCK_END, SCROLL_PADDING_BLOCK_START, SCROLL_PADDING_BLOCK, SCROLL_PADDING_BOTTOM, SCROLL_PADDING_INLINE_END, SCROLL_PADDING_INLINE_START,
101+ SCROLL_PADDING_INLINE, SCROLL_PADDING_LEFT, SCROLL_PADDING_RIGHT, SCROLL_PADDING_TOP, SCROLL_PADDING, SCROLL_SNAP_ALIGN, SCROLL_SNAP_STOP, SCROLL_SNAP_TYPE,
102+ SCROLL_TIMELINE_AXIS, SCROLL_TIMELINE_NAME, SCROLL_TIMELINE, SCROLLBAR_COLOR, SCROLLBAR_GUTTER, SCROLLBAR_WIDTH, SHAPE_IMAGE_THRESHOLD, SHAPE_MARGIN,
103+ SHAPE_OUTSIDE, SHAPE_RENDERING, SPEAK_AS, STOP_COLOR, STOP_OPACITY, STROKE_DASHARRAY, STROKE_DASHOFFSET, STROKE_LINECAP, STROKE_LINEJOIN, STROKE_MITERLIMIT,
104+ STROKE_OPACITY, STROKE_WIDTH, STROKE,
105+ TAB_SIZE, TABLE_LAYOUT, TEXT_ALIGN_LAST, TEXT_ALIGN, TEXT_ANCHOR, TEXT_BOX_EDGE, TEXT_BOX_TRIM, TEXT_BOX, TEXT_COMBINE_UPRIGHT, TEXT_DECORATION_COLOR,
106+ TEXT_DECORATION_LINE, TEXT_DECORATION_SKIP_INK, TEXT_DECORATION_SKIP, TEXT_DECORATION_STYLE, TEXT_DECORATION_THICKNESS, TEXT_DECORATION, TEXT_EMPHASIS_COLOR,
107+ TEXT_EMPHASIS_POSITION, TEXT_EMPHASIS_STYLE, TEXT_EMPHASIS, TEXT_INDENT, TEXT_JUSTIFY, TEXT_ORIENTATION, TEXT_OVERFLOW, TEXT_RENDERING, TEXT_SHADOW,
108+ TEXT_SIZE_ADJUST, TEXT_SPACING_TRIM, TEXT_TRANSFORM, TEXT_UNDERLINE_OFFSET, TEXT_UNDERLINE_POSITION, TEXT_WRAP_MODE, TEXT_WRAP_STYLE, TEXT_WRAP,
109+ TIMELINE_SCOPE, TOP, TOUCH_ACTION, TRANSFORM_BOX, TRANSFORM_ORIGIN, TRANSFORM_STYLE, TRANSFORM, TRANSITION_BEHAVIOR, TRANSITION_DELAY, TRANSITION_DURATION,
110+ TRANSITION_PROPERTY, TRANSITION_TIMING_FUNCTION, TRANSITION, TRANSLATE,
111+ UNICODE_BIDI, USER_MODIFY, USER_SELECT,
112+ VECTOR_EFFECT, VERTICAL_ALIGN, VIEW_TIMELINE_AXIS, VIEW_TIMELINE_INSET, VIEW_TIMELINE_NAME, VIEW_TIMELINE, VIEW_TRANSITION_CLASS, VIEW_TRANSITION_NAME,
113+ VISIBILITY,
114+ WHITE_SPACE_COLLAPSE, WHITE_SPACE, WIDOWS, WIDTH, WILL_CHANGE, WORD_BREAK, WORD_SPACING, WRITING_MODE,
115+ X,
116+ Y,
117+ Z_INDEX, ZOOM
118+};
119+
120+enum class UnitType : short {
121 // Color
122 HEX, RGB, RGBA, HSL,
123 // Logic
124@@ -174,7 +245,6 @@ enum class UnitType : char {
125 NORMAL, STRETCH, BETWEEN, AROUND, EVENLY,
126 // Position
127 CENTER, START, END, TOP, LEFT, BOTTOM, RIGHT, INLINE_START, INLINE_END, BLOCK_START, BLOCK_END, SELF_START, SELF_END, FLEX_START, FLEX_END,
128- FLEX_START, FLEX_END,
129 // Overflow
130 CLIP, SCROLL,
131 SAFE, UNSAFE,
132@@ -212,7 +282,7 @@ enum class UnitType : char {
133 // Background Attachment
134 LOCAL, FIXED,
135 // Background Blend Mode
136- MULTIPLY, OVERLAY, DARKEN, LIGHTEN, COLOR_DODGE, COLOR_BURN, HARD_LIGHT, SOFT_LIGHT, DIFFERENCE, EXCLUSION, HUE, SATURATION, COLOR, LUMINOSITY
137+ MULTIPLY, OVERLAY, DARKEN, LIGHTEN, COLOR_DODGE, COLOR_BURN, HARD_LIGHT, SOFT_LIGHT, DIFFERENCE, EXCLUSION, SATURATION, COLOR, LUMINOSITY,
138 // Background Clip
139 BORDER_BOX, PADDING_BOX, CONTENT_BOX, TEXT, BORDER_AREA,
140
141@@ -227,7 +297,7 @@ enum class UnitType : char {
142 SKEW, SKEWX, SKEWY,
143
144 // Keyword
145- PRINT, SCREEN, TOKEN, FUNC, GROUP, NO_SUPPORT
146+ PRINT, SCREEN, TOKEN, FUNC, GROUP, NO_SUPPORT, IMAGE
147 };
148
149 // 4 bytes
150@@ -239,285 +309,77 @@ union UnitValue {
151 bool BOOL;
152 };
153
154-// 5 bytes
155+// 6 bytes
156 struct Unit {
157- UnitType type; // char
158+ UnitType type; // short
159 UnitValue value;
160 };
161
162-enum class KeyType : char {
163- ACCENT_COLOR, ALIGN_CONTENT, ALIGN_ITEMS, ALIGN_SELF, ALL, APPEARANCE, ASPECT_RATIO,
164- BACKDROP_FILTER, BACKGROUND_ATTACHMENT, BACKGROUND_BLEND_MODE, BACKGROUND_CLIP, BACKGROUND_COLOR,
165- BACKGROUND_IMAGE,
166-
167-}
168-
169-/*
170- std::vector is probally not a great way to store the accepted
171- UnitType's for a given key. However, that can be fixed later
172-*/
173- // \/ Move to parser.cc \/ //
174-
175-static const std::unordered_map<std::string, KeyType> keySearch {
176- {"accent-color", KeyType::ACCENT_COLOR},
177- {"align-content", KeyType::ALIGN_CONTENT},
178- {"align-items", KeyType::ALIGN_ITEMS},
179- {"align-self", KeyType::ALIGN_SELF},
180- {"all", KeyType::ALL},
181- {"appearance", KeyType::APPEARANCE},
182- {"aspect-ratio", KeyType::ASPECT_RATIO},
183- {"backdrop-filter", KeyType::BACKDROP_FILTER},
184- {"backface-visibility", KeyType::NO_SUPPORT},
185- {"background-attachment", KeyType::BACKGROUND_ATTACHMENT},
186- {"background-blend-mode", KeyType::BACKGROUND_BLEND_MODE},
187- {"background-clip", KeyType::BACKGROUND_CLIP},
188- {"background-color", KeyType::BACKGROUND_COLOR},
189-
190-}
191-
192- // It is implided that all values have the global values
193- // inherit inital revert revert-layer unset
194-
195-
196-
197-static const std::unordered_map<KeyType, std::vector<UnitType>> kAccepts {
198- {KeyType::ACCENT_COLOR, {UnitType::AUTO, UnitType::HEX, UnitType::RGB, UnitType::RGBA, UnitType::HSL}},
199- {
200- KeyType::ALIGN_CONTENT,
201- {
202- UnitType::NORMAL, UnitType::START, UnitType::CENTER, UnitType::END,
203- UnitType::FLEX_START, UnitType::FLEX_END, UnitType::BASELINE, UnitType::FIRST, UnitType::LAST, UnitType::SPACE_BETWEEN,
204- UnitType::SPACE_AROUND, UnitType::SPACE_EVENLY, UnitType::STRETCH, UnitType::SAFE, UnitType::UNSAFE, UnitType::CENTER
205- }
206- },
207- {
208- KeyType::ALIGN_ITEMS,
209- {
210- UnitType::NORMAL, UnitType::START, UnitType::CENTER, UnitType::END, UnitType::FLEX_START, UnitType::FLEX_END, UnitType::SELF_START,
211- UnitType::SELF_END, UnitType::ANCHOR_CENTER, UnitType::BASELINE, UnitType::FIRST, UnitType::LAST, UnitType::STRETCH,
212- UnitType::SAFE, UnitType::UNSAFE, UnitType::CENTER
213- }
214- },
215- {
216- KeyType::ALIGN_SELF,
217- {
218- UnitType::AUTO, UnitType::NORMAL, UnitType::START, UnitType::CENTER, UnitType::END, UnitType::FLEX_START, UnitType::FLEX_END,
219- UnitType::SELF_START, UnitType::SELF_END, UnitType::ANCHOR_CENTER, UnitType::BASELINE, UnitType::FIRST, UnitType::LAST,
220- UnitType::STRETCH, UnitType::SAFE, UnitType::UNSAFE, UnitType::CENTER
221- }
222- },
223-
224- {
225- // These are the global values but thats all "all" accepts so I put them there
226- KeyType::ALL,
227- {
228- UnitType::INTIAL, UnitType::INHERIT, UnitType::UNSET, UnitType::REVERT, UnitType::REVERT_LAYER
229- }
230- },
231-/*
232- Missing:
233-anchor-name
234-animation-composition
235-animation-delay
236-animation-direction
237-animation-duration
238-animation-fill-mode
239-animation-iteration-count
240-animation-name
241-animation-play-state
242-animation-range-end
243-animation-range-start
244-animation-range (shorthand)
245-animation-timeline
246-animation-timing-function
247-animation (shorthand)
248-*/
249- {
250- KeyType::APPEARANCE,
251- {
252- UnitType::NONE, UnitType::AUTO, UnitType::MENULIST_BUTTON, UnitType::TEXTFIELD, UnitType::BASE_SELECT, UnitType::BUTTON, UnitType::CHECKBOX
253- }
254- },
255- {
256- KeyType::ASPECT_RATIO,
257- {
258- UnitType::NUMBER, UnitType::AUTO, UnitType::DIV
259- }
260- },
261-
262-
263- {
264- KeyType::BACKDROP_FILTER,
265- {
266- UnitType::NONE, UnitType::URL, UnitType::BLUR, UnitType::BRIGHTNESS, UnitType::CONTRAST, UnitType::DROP_SHADOW, UnitType::GRAYSCALE,
267- UnitType::HURE_ROTATE, UnitType::INVERT, UnitType::OPACITY, UnitType::SEPIA, UnitType::SATURATE,
268- }
269- },
270- {
271- KeyType::BACKGROUND_ATTACHMENT,
272- {
273- UnitType::SCROLL, UnitType::FIXED, UnitType::LOCAL,
274- }
275- },
276- {
277- KeyType::BACKGROUND_BLEND_MODE,
278- {
279- UnitType::NORMAL,
280- UnitType::MULTIPLY,
281- UnitType::SCREEN,
282- UnitType::OVERLAY,
283- UnitType::DARKEN,
284- UnitType::LIGHTEN,
285- UnitType::COLOR_DODGE,
286- UnitType::COLOR_BURN,
287- UnitType::HARD_LIGHT,
288- UnitType::SOFT_LIGHT,
289- UnitType::DIFFERENCE,
290- UnitType::EXCLUSION,
291- UnitType::HUE,
292- UnitType::SATURATION,
293- UnitType::COLOR,
294- UnitType::LUMINOSITY,
295- }
296- },
297- {
298- KeyType::BACKGROUD_CLIP,
299- {
300- UnitType::BORDER_BOX,
301- UnitType::PADDING_BOX,
302- UnitType::CONTENT_BOX,
303- UnitType::TEXT,
304- UnitType::BORDER_AREA,
305- }
306- },
307- {
308- KeyType::BACKGROUND_COLOR,
309- {
310- UnitType::HEX,
311- UnitType::RGB,
312- UnitType::RGBA,
313- UnitType::HSL,
314- }
315- },
316- {
317- KeyType::,
318- {
319- UnitType::,
320- }
321- },
322- {
323- KeyType::,
324- {
325- UnitType::,
326- }
327- },
328-
329- {
330- KeyType::,
331- {
332- UnitType::,
333- }
334- },
335-}
336-
337-enum class SheetType {
338+enum class StyleType : char {
339 CONTAINER, COUNTER, FONTFACE, FONTFEATURE, SWASH, ANNOTATION, ORNAMENTS, STYLISTIC, STYLESET, CHARACTERVARIANT, FONTPALETTEVALUES,
340 IMPORT, KEYFRAMES, LAYER, NAMESPACE, PAGE, PROPERTY, ROOT, SHEET, MEDIA, STARTINGSTYLE, STYLE
341 };
342
343-// A sheet is a group of styles, layers can be nested for specifity and the order can be set via
344-// @layer order...;
345-// all style sheets are parsed into ROOT layers
346-// the non-layer styles will be placed inside of "styles" and they take priority over the layers
347-// all at rules are placed inside of "children"
348-// defining the order of the layers only effects the children with the type layer
349-// the rest are defined in the order they are parsed
350-class Sheet {
351+class Style {
352 public:
353- // basemap: Maps baseparts to a index of the styles vector pointing to a Style object
354- // because processing a CSS selector isn't trivial we want to make a short list of
355- // the styles that can possibly be a match so we aren't spending a lot of compute
356- // on a selector that applies to the wrong element. To do this we take the right most part
357- // of a selector (that is the part that targets the current element) and we do a few checks
358- // like is the tagname the same, does it have that class, and do the id's match. If so that
359- // is a candidate and we run the full selector on it. That includes checking parents,children,
360- // or what ever else the selector needs to match.
361+ Window* window;
362+
363 std::unordered_map<std::string, std::vector<size_t>> basemap;
364+ std::vector<int> indexes;
365
366+ StyleType type;
367 std::string name;
368- std::string path;
369 std::vector<std::vector<std::string>> selector;
370- std::vector<int> indexes;
371
372- std::unordered_map<Key, std::vector<Unit>> properties;
373-
374- SheetType type;
375- std::unordered_map<std::string, std::string> variables;
376-};
377-
378-class Window;
379-
380-class StyleHandler {
381- private:
382-
383- std::vector<std::string> parseNodeParts(Node* node);
384-
385- // to compute the @ rules.
386- std::unordered_map<std::string, std::string> variables;
387-
388- Window* window;
389-
390- public:
391- size_t index = 0;
392- StyleHandler(Window* w): window(w) {}
393- // Rules from the master.css file are direct styles of this object
394- // all sheets are parsed as children of the ROOT
395- Sheet root;
396+ std::unordered_map<KeyType, std::vector<Unit>> properties;
397+ std::unordered_map<std::string, std::vector<Unit>> variables;
398
399- std::unordered_map<std::string, std::string> getStyles(Node* node);
400+ // Nesting
401+ std::vector<Style> children;
402
403- void parseStream(std::istream&);
404- // make a function that will return a list of attributes the will cause style changes if set
405+ // Functions
406+ void addChild(Style s);
407+ std::unordered_map<KeyType, UnitType> getStyles(Node* n);
408 };
409
410-enum class AnyHover {
411+enum class AnyHover : char {
412 None,
413 Hover
414 };
415
416-enum class AnyPointer {
417+enum class AnyPointer : char {
418 None,
419 Fine,
420 Coarse
421 };
422
423-enum class Orientation {
424+enum class Orientation : char {
425 Landscape,
426 Portrait
427 };
428
429-enum class ColorScheme {
430+enum class ColorScheme : char {
431 Light,
432 Dark
433 };
434
435-enum class Contrast {
436+enum class Contrast : char {
437 NoPreference,
438 More,
439 Less
440 };
441
442-enum class ReducedMotion {
443+enum class ReducedMotion : char {
444 NoPreference,
445 Reduce
446 };
447
448-enum class ReducedTransparency {
449+enum class ReducedTransparency : char {
450 NoPreference,
451 Reduce
452 };
453
454-enum class Update {
455+enum class Update : char {
456 Fast,
457 Slow
458 };
459@@ -538,10 +400,13 @@ class Window {
460 Update update = Update::Fast;
461
462 public:
463-
464- StyleHandler CSS;
465-
466- Window(): CSS(this) {}
467+
468+ void loadHTML(std::istream& inputStream);
469+ void loadCSS(std::istream& inputStream);
470+
471+ Node document;
472+ Style CSS;
473+
474 // +---------------------------------------------------+
475 // | (hldfk) Window Properties |
476 // +---------------------------------------------------+
477diff --git a/include/parser.h b/include/parser.h
478index 8b71a76..aca9526 100755
479--- a/include/parser.h
480+++ b/include/parser.h
481@@ -9,13 +9,13 @@
482 #include <string_view>
483
484 class Node;
485-class StyleHandler;
486+class Style;
487
488 // Declare the parsing functions
489 std::unordered_map<std::string, std::string> parseAttributes(std::string_view& token);
490-std::unique_ptr<Node> parseHTML(std::istream& inputStream);
491-std::unique_ptr<StyleHandler> parseCSS(std::istream& inputStream);
492-std::unordered_map<std::string, std::string> parseCSSInline(std::string inlineStyles);
493+Node parseHTML(std::istream& inputStream);
494+Style parseCSS(std::istream& inputStream);
495+std::unordered_map<KeyType, std::vector<Unit>> parseCSSInline(std::string inlineStyles);
496 std::vector<Unit> getUnit(std::string);
497
498 #endif
499diff --git a/src/adapter.cc b/src/adapter.cc
500deleted file mode 100755
501index e69de29..0000000
502diff --git a/src/events.cc b/src/events.cc
503deleted file mode 100755
504index e70b57e..0000000
505--- a/src/events.cc
506+++ /dev/null
507@@ -1 +0,0 @@
508-#include <print>
509diff --git a/src/grim.cc b/src/grim.cc
510index 7e952ee..fe2341f 100755
511--- a/src/grim.cc
512+++ b/src/grim.cc
513@@ -1,4 +1,5 @@
514 #include "grim.h"
515+#include "parser.h"
516 #include <iostream>
517 #include <sstream>
518 #include <algorithm>
519@@ -68,11 +69,13 @@ void trimSpace(std::string& str) {
520 // | (hldfk) Document Parsing |
521 // +---------------------------------------------------+
522
523-// Node* CreateDocument(std::string path) {
524- // Parse document
525- // Pull links from head and get stylesheets
526- // parse css (pass window to precalculate all of the values)
527-// }
528+void Window::loadHTML(std::istream& inputStream) {
529+ document = parseHTML(inputStream);
530+}
531+
532+void Window::loadCSS(std::istream& inputStream) {
533+ CSS.addChild(parseCSS(inputStream));
534+}
535
536
537 // +---------------------------------------------------+
538@@ -646,7 +649,7 @@ std::vector<std::vector<std::string>> parseSelectorParts(std::string_view select
539 // | (luoiy) Node Selector Parsing |
540 // +---------------------------------------------------+
541 //
542-std::vector<std::string> StyleHandler::parseNodeParts(Node* node) {
543+std::vector<std::string> parseNodeParts(Node* node) {
544 // This isn't a all inclusive list of parts that can
545 // apply to the node but it narrows our search for matching
546 // classes down quite a bit
547@@ -686,26 +689,19 @@ std::vector<std::string> StyleHandler::parseNodeParts(Node* node) {
548 return parts;
549 }
550
551-/*
552-void Sheet::add(std::string selector, std::unordered_map<std::string, std::string> properties) {
553- // Type is 2d vector of selector parts
554
555- auto parts = parseSelectorParts(selector);
556+void Style::addChild(Style s) {
557+ size_t index = children.size();
558
559- for (auto pr : parts) {
560- for (auto p : pr) {
561- std::cout << p << std::endl;
562- }
563- }
564-
565- size_t index = styles.size();
566+ // Add the window
567+ s.window = window;
568
569- styles.push_back({parts,properties});
570+ children.push_back(s);
571
572 // Get the last selector group from the parsed selector parts
573 // because that is the selector that applies to an element
574 // and map them into basemap
575- std::vector<std::string> targetParts = parts[parts.size()-1];
576+ std::vector<std::string> targetParts = s.selector[s.selector.size()-1];
577 for (auto p : targetParts) {
578 if (basemap.find(p) != basemap.end()) {
579 basemap[p].push_back(index);
580@@ -715,9 +711,11 @@ void Sheet::add(std::string selector, std::unordered_map<std::string, std::strin
581 }
582 }
583 }
584-*/
585
586-void getstyles(Node* node, std::vector<std::string> node_parts, Sheet* sheet, std::unordered_map<std::string, std::string>* styles) {
587+
588+std::unordered_map<KeyType, UnitType> Style::getStyles(Node* node) {
589+ std::vector<std::string> node_parts = parseNodeParts(node);
590+ /*
591 std::vector<size_t> canidates;
592
593 // Now we have to start from the window.CSS.root, use the basemap to find styles
594@@ -765,21 +763,7 @@ void getstyles(Node* node, std::vector<std::string> node_parts, Sheet* sheet, st
595 } else if (t == SheetType::CONTAINER) {
596
597 }
598- }
599-}
600-
601-// TODO:Add variable subsutution and inheritance, fill in the & in nested
602-std::unordered_map<std::string, std::string> StyleHandler::getStyles(Node* node) {
603- // TODO: Will need to change getStyles to first consider if the style sheet applies
604- // then to check the selectors
605- std::vector<std::string> parts = parseNodeParts(node);
606-
607- std::unordered_map<std::string, std::string> styles;
608-
609- getstyles(node, parts, &window->CSS.root, &styles);
610-
611- // Now we have all styles except the inline styles and the inherited styles
612-
613+ }*/
614 }
615
616 // Used for root node without a parent
617@@ -1372,6 +1356,7 @@ bool testSelector(Node* node, std::vector<std::vector<std::string>> selector) {
618 // testQuery takes any sheet class that isn't a SheetType::STYLE
619 // and tries to calculate if the query (ie a media query or
620 // container query) applies to the node passed
621+/*
622 bool testQuery(Sheet* query, Node* node, Window* window) {
623 // First step is to understand the query
624 // it is parsed from parseSelector parts
625@@ -1385,3 +1370,4 @@ bool testQuery(Sheet* query, Node* node, Window* window) {
626
627 }
628 }
629+*/
630diff --git a/src/parser.cc b/src/parser.cc
631index 36ecc5a..3cff12a 100755
632--- a/src/parser.cc
633+++ b/src/parser.cc
634@@ -103,11 +103,11 @@ std::unordered_map<std::string, std::string> parseAttributes(std::string_view to
635 return attrs;
636 }
637
638-std::unique_ptr<Node> parseHTML(std::istream& inputStream) {
639- std::unique_ptr<Node> root = std::make_unique<Node>();
640- root->setTagName("root");
641+Node parseHTML(std::istream& inputStream) {
642+ Node root;
643+ root.setTagName("root");
644
645- Node* currentNode = root.get();
646+ Node* currentNode = &root;
647
648 bool inTag = false;
649 bool escaped = false;
650@@ -336,24 +336,498 @@ std::unique_ptr<Node> parseHTML(std::istream& inputStream) {
651 return root;
652 }
653
654-/*
655-void typeCheck(std::string key, std::string value, Unit* property, std::vector<UnitType> allowedTypes) {
656- for (size_t i = 0; i < property->children.size(); i++) {
657- bool allowed = false;
658- for (size_t j = 0; j < allowedTypes.size(); j++) {
659- if (property->children[i].type == allowedTypes[j]) {
660- allowed = true;
661- break;
662- }
663- }
664-
665- if (!allowed) {
666- std::cerr << "Invalid value of property: " << key << " Value: " << value << std::endl;
667- std::exit(10);
668- }
669- }
670-}
671-*/
672+static const std::unordered_map<std::string, KeyType> keySearch {
673+ {"accent-color", KeyType::ACCENT_COLOR},
674+ {"align-content", KeyType::ALIGN_CONTENT},
675+ {"align-items", KeyType::ALIGN_ITEMS},
676+ {"align-self", KeyType::ALIGN_SELF},
677+ {"alignment-baseline", KeyType::ALIGNMENT_BASELINE},
678+ {"all", KeyType::ALL},
679+ {"anchor-name", KeyType::ANCHOR_NAME},
680+ {"animation-composition", KeyType::ANIMATION_COMPOSITION},
681+ {"animation-delay", KeyType::ANIMATION_DELAY},
682+ {"animation-direction", KeyType::ANIMATION_DIRECTION},
683+ {"animation-duration", KeyType::ANIMATION_DURATION},
684+ {"animation-fill-mode", KeyType::ANIMATION_FILL_MODE},
685+ {"animation-iteration-count", KeyType::ANIMATION_ITERATION_COUNT},
686+ {"animation-name", KeyType::ANIMATION_NAME},
687+ {"animation-play-state", KeyType::ANIMATION_PLAY_STATE},
688+ {"animation-range-end", KeyType::ANIMATION_RANGE_END},
689+ {"animation-range-start", KeyType::ANIMATION_RANGE_START},
690+ {"animation-range", KeyType::ANIMATION_RANGE},
691+ {"animation-timeline", KeyType::ANIMATION_TIMELINE},
692+ {"animation-timing-function", KeyType::ANIMATION_TIMING_FUNCTION},
693+ {"animation", KeyType::ANIMATION},
694+ {"appearance", KeyType::APPEARANCE},
695+ {"aspect-ratio", KeyType::ASPECT_RATIO},
696+ {"backdrop-filter", KeyType::BACKDROP_FILTER},
697+ {"backface-visibility", KeyType::BACKFACE_VISIBILITY},
698+ {"background-attachment", KeyType::BACKGROUND_ATTACHMENT},
699+ {"background-blend-mode", KeyType::BACKGROUND_BLEND_MODE},
700+ {"background-clip", KeyType::BACKGROUND_CLIP},
701+ {"background-color", KeyType::BACKGROUND_COLOR},
702+ {"background-image", KeyType::BACKGROUND_IMAGE},
703+ {"background-origin", KeyType::BACKGROUND_ORIGIN},
704+ {"background-position-x", KeyType::BACKGROUND_POSITION_X},
705+ {"background-position-y", KeyType::BACKGROUND_POSITION_Y},
706+ {"background-position", KeyType::BACKGROUND_POSITION},
707+ {"background-repeat", KeyType::BACKGROUND_REPEAT},
708+ {"background-size", KeyType::BACKGROUND_SIZE},
709+ {"background", KeyType::BACKGROUND},
710+ {"block-size", KeyType::BLOCK_SIZE},
711+ {"border-block-color", KeyType::BORDER_BLOCK_COLOR},
712+ {"border-block-end-color", KeyType::BORDER_BLOCK_END_COLOR},
713+ {"border-block-end-style", KeyType::BORDER_BLOCK_END_STYLE},
714+ {"border-block-end-width", KeyType::BORDER_BLOCK_END_WIDTH},
715+ {"border-block-end", KeyType::BORDER_BLOCK_END},
716+ {"border-block-start-color", KeyType::BORDER_BLOCK_START_COLOR},
717+ {"border-block-start-style", KeyType::BORDER_BLOCK_START_STYLE},
718+ {"border-block-start-width", KeyType::BORDER_BLOCK_START_WIDTH},
719+ {"border-block-start", KeyType::BORDER_BLOCK_START},
720+ {"border-block-style", KeyType::BORDER_BLOCK_STYLE},
721+ {"border-block-width", KeyType::BORDER_BLOCK_WIDTH},
722+ {"border-block", KeyType::BORDER_BLOCK},
723+ {"border-bottom-color", KeyType::BORDER_BOTTOM_COLOR},
724+ {"border-bottom-left-radius", KeyType::BORDER_BOTTOM_LEFT_RADIUS},
725+ {"border-bottom-right-radius", KeyType::BORDER_BOTTOM_RIGHT_RADIUS},
726+ {"border-bottom-style", KeyType::BORDER_BOTTOM_STYLE},
727+ {"border-bottom-width", KeyType::BORDER_BOTTOM_WIDTH},
728+ {"border-bottom", KeyType::BORDER_BOTTOM},
729+ {"border-collapse", KeyType::BORDER_COLLAPSE},
730+ {"border-color", KeyType::BORDER_COLOR},
731+ {"border-end-end-radius", KeyType::BORDER_END_END_RADIUS},
732+ {"border-end-start-radius", KeyType::BORDER_END_START_RADIUS},
733+ {"border-image-outset", KeyType::BORDER_IMAGE_OUTSET},
734+ {"border-image-repeat", KeyType::BORDER_IMAGE_REPEAT},
735+ {"border-image-slice", KeyType::BORDER_IMAGE_SLICE},
736+ {"border-image-source", KeyType::BORDER_IMAGE_SOURCE},
737+ {"border-image-width", KeyType::BORDER_IMAGE_WIDTH},
738+ {"border-image", KeyType::BORDER_IMAGE},
739+ {"border-inline-color", KeyType::BORDER_INLINE_COLOR},
740+ {"border-inline-end-color", KeyType::BORDER_INLINE_END_COLOR},
741+ {"border-inline-end-style", KeyType::BORDER_INLINE_END_STYLE},
742+ {"border-inline-end-width", KeyType::BORDER_INLINE_END_WIDTH},
743+ {"border-inline-end", KeyType::BORDER_INLINE_END},
744+ {"border-inline-start-color", KeyType::BORDER_INLINE_START_COLOR},
745+ {"border-inline-start-style", KeyType::BORDER_INLINE_START_STYLE},
746+ {"border-inline-start-width", KeyType::BORDER_INLINE_START_WIDTH},
747+ {"border-inline-start", KeyType::BORDER_INLINE_START},
748+ {"border-inline-style", KeyType::BORDER_INLINE_STYLE},
749+ {"border-inline-width", KeyType::BORDER_INLINE_WIDTH},
750+ {"border-inline", KeyType::BORDER_INLINE},
751+ {"border-left-color", KeyType::BORDER_LEFT_COLOR},
752+ {"border-left-style", KeyType::BORDER_LEFT_STYLE},
753+ {"border-left-width", KeyType::BORDER_LEFT_WIDTH},
754+ {"border-left", KeyType::BORDER_LEFT},
755+ {"border-radius", KeyType::BORDER_RADIUS},
756+ {"border-right-color", KeyType::BORDER_RIGHT_COLOR},
757+ {"border-right-style", KeyType::BORDER_RIGHT_STYLE},
758+ {"border-right-width", KeyType::BORDER_RIGHT_WIDTH},
759+ {"border-right", KeyType::BORDER_RIGHT},
760+ {"border-spacing", KeyType::BORDER_SPACING},
761+ {"border-start-end-radius", KeyType::BORDER_START_END_RADIUS},
762+ {"border-start-start-radius", KeyType::BORDER_START_START_RADIUS},
763+ {"border-style", KeyType::BORDER_STYLE},
764+ {"border-top-color", KeyType::BORDER_TOP_COLOR},
765+ {"border-top-left-radius", KeyType::BORDER_TOP_LEFT_RADIUS},
766+ {"border-top-right-radius", KeyType::BORDER_TOP_RIGHT_RADIUS},
767+ {"border-top-style", KeyType::BORDER_TOP_STYLE},
768+ {"border-top-width", KeyType::BORDER_TOP_WIDTH},
769+ {"border-top", KeyType::BORDER_TOP},
770+ {"border-width", KeyType::BORDER_WIDTH},
771+ {"border", KeyType::BORDER},
772+ {"bottom", KeyType::BOTTOM},
773+ {"box-align", KeyType::BOX_ALIGN},
774+ {"box-decoration-break", KeyType::BOX_DECORATION_BREAK},
775+ {"box-direction", KeyType::BOX_DIRECTION},
776+ {"box-flex-group", KeyType::BOX_FLEX_GROUP},
777+ {"box-flex", KeyType::BOX_FLEX},
778+ {"box-lines", KeyType::BOX_LINES},
779+ {"box-ordinal-group", KeyType::BOX_ORDINAL_GROUP},
780+ {"box-orient", KeyType::BOX_ORIENT},
781+ {"box-pack", KeyType::BOX_PACK},
782+ {"box-shadow", KeyType::BOX_SHADOW},
783+ {"box-sizing", KeyType::BOX_SIZING},
784+ {"break-after", KeyType::BREAK_AFTER},
785+ {"break-before", KeyType::BREAK_BEFORE},
786+ {"break-inside", KeyType::BREAK_INSIDE},
787+ {"caption-side", KeyType::CAPTION_SIDE},
788+ {"caret-color", KeyType::CARET_COLOR},
789+ {"clear", KeyType::CLEAR},
790+ {"clip-path", KeyType::CLIP_PATH},
791+ {"clip-rule", KeyType::CLIP_RULE},
792+ {"clip", KeyType::CLIP},
793+ {"color-interpolation-filters", KeyType::COLOR_INTERPOLATION_FILTERS},
794+ {"color-interpolation", KeyType::COLOR_INTERPOLATION},
795+ {"color-scheme", KeyType::COLOR_SCHEME},
796+ {"color", KeyType::COLOR},
797+ {"column-count", KeyType::COLUMN_COUNT},
798+ {"column-fill", KeyType::COLUMN_FILL},
799+ {"column-gap", KeyType::COLUMN_GAP},
800+ {"column-rule-color", KeyType::COLUMN_RULE_COLOR},
801+ {"column-rule-style", KeyType::COLUMN_RULE_STYLE},
802+ {"column-rule-width", KeyType::COLUMN_RULE_WIDTH},
803+ {"column-rule", KeyType::COLUMN_RULE},
804+ {"column-span", KeyType::COLUMN_SPAN},
805+ {"column-width", KeyType::COLUMN_WIDTH},
806+ {"columns", KeyType::COLUMNS},
807+ {"contain-intrinsic-block-size", KeyType::CONTAIN_INTRINSIC_BLOCK_SIZE},
808+ {"contain-intrinsic-height", KeyType::CONTAIN_INTRINSIC_HEIGHT},
809+ {"contain-intrinsic-inline-size", KeyType::CONTAIN_INTRINSIC_INLINE_SIZE},
810+ {"contain-intrinsic-size", KeyType::CONTAIN_INTRINSIC_SIZE},
811+ {"contain-intrinsic-width", KeyType::CONTAIN_INTRINSIC_WIDTH},
812+ {"contain", KeyType::CONTAIN},
813+ {"container-name", KeyType::CONTAINER_NAME},
814+ {"container-type", KeyType::CONTAINER_TYPE},
815+ {"container", KeyType::CONTAINER},
816+ {"content-visibility", KeyType::CONTENT_VISIBILITY},
817+ {"content", KeyType::CONTENT},
818+ {"counter-increment", KeyType::COUNTER_INCREMENT},
819+ {"counter-reset", KeyType::COUNTER_RESET},
820+ {"counter-set", KeyType::COUNTER_SET},
821+ {"cursor", KeyType::CURSOR},
822+ {"cx", KeyType::CX},
823+ {"cy", KeyType::CY},
824+ {"d", KeyType::D},
825+ {"direction", KeyType::DIRECTION},
826+ {"display", KeyType::DISPLAY},
827+ {"dominant-baseline", KeyType::DOMINANT_BASELINE},
828+ {"empty-cells", KeyType::EMPTY_CELLS},
829+ {"field-sizing", KeyType::FIELD_SIZING},
830+ {"fill-opacity", KeyType::FILL_OPACITY},
831+ {"fill-rule", KeyType::FILL_RULE},
832+ {"fill", KeyType::FILL},
833+ {"filter", KeyType::FILTER},
834+ {"flex-basis", KeyType::FLEX_BASIS},
835+ {"flex-direction", KeyType::FLEX_DIRECTION},
836+ {"flex-flow", KeyType::FLEX_FLOW},
837+ {"flex-grow", KeyType::FLEX_GROW},
838+ {"flex-shrink", KeyType::FLEX_SHRINK},
839+ {"flex-wrap", KeyType::FLEX_WRAP},
840+ {"flex", KeyType::FLEX},
841+ {"float", KeyType::FLOAT},
842+ {"flood-color", KeyType::FLOOD_COLOR},
843+ {"flood-opacity", KeyType::FLOOD_OPACITY},
844+ {"font-family", KeyType::FONT_FAMILY},
845+ {"font-feature-settings", KeyType::FONT_FEATURE_SETTINGS},
846+ {"font-kerning", KeyType::FONT_KERNING},
847+ {"font-language-override", KeyType::FONT_LANGUAGE_OVERRIDE},
848+ {"font-optical-sizing", KeyType::FONT_OPTICAL_SIZING},
849+ {"font-palette", KeyType::FONT_PALETTE},
850+ {"font-size-adjust", KeyType::FONT_SIZE_ADJUST},
851+ {"font-size", KeyType::FONT_SIZE},
852+ {"font-smooth", KeyType::FONT_SMOOTH},
853+ {"font-stretch", KeyType::FONT_STRETCH},
854+ {"font-style", KeyType::FONT_STYLE},
855+ {"font-synthesis-position", KeyType::FONT_SYNTHESIS_POSITION},
856+ {"font-synthesis-small-caps", KeyType::FONT_SYNTHESIS_SMALL_CAPS},
857+ {"font-synthesis-style", KeyType::FONT_SYNTHESIS_STYLE},
858+ {"font-synthesis-weight", KeyType::FONT_SYNTHESIS_WEIGHT},
859+ {"font-synthesis", KeyType::FONT_SYNTHESIS},
860+ {"font-variant-alternates", KeyType::FONT_VARIANT_ALTERNATES},
861+ {"font-variant-caps", KeyType::FONT_VARIANT_CAPS},
862+ {"font-variant-east-asian", KeyType::FONT_VARIANT_EAST_ASIAN},
863+ {"font-variant-emoji", KeyType::FONT_VARIANT_EMOJI},
864+ {"font-variant-ligatures", KeyType::FONT_VARIANT_LIGATURES},
865+ {"font-variant-numeric", KeyType::FONT_VARIANT_NUMERIC},
866+ {"font-variant-position", KeyType::FONT_VARIANT_POSITION},
867+ {"font-variant", KeyType::FONT_VARIANT},
868+ {"font-variation-settings", KeyType::FONT_VARIATION_SETTINGS},
869+ {"font-weight", KeyType::FONT_WEIGHT},
870+ {"font", KeyType::FONT},
871+ {"forced-color-adjust", KeyType::FORCED_COLOR_ADJUST},
872+ {"gap", KeyType::GAP},
873+ {"grid-area", KeyType::GRID_AREA},
874+ {"grid-auto-columns", KeyType::GRID_AUTO_COLUMNS},
875+ {"grid-auto-flow", KeyType::GRID_AUTO_FLOW},
876+ {"grid-auto-rows", KeyType::GRID_AUTO_ROWS},
877+ {"grid-column-end", KeyType::GRID_COLUMN_END},
878+ {"grid-column-start", KeyType::GRID_COLUMN_START},
879+ {"grid-column", KeyType::GRID_COLUMN},
880+ {"grid-row-end", KeyType::GRID_ROW_END},
881+ {"grid-row-start", KeyType::GRID_ROW_START},
882+ {"grid-row", KeyType::GRID_ROW},
883+ {"grid-template-areas", KeyType::GRID_TEMPLATE_AREAS},
884+ {"grid-template-columns", KeyType::GRID_TEMPLATE_COLUMNS},
885+ {"grid-template-rows", KeyType::GRID_TEMPLATE_ROWS},
886+ {"grid-template", KeyType::GRID_TEMPLATE},
887+ {"grid", KeyType::GRID},
888+ {"hanging-punctuation", KeyType::HANGING_PUNCTUATION},
889+ {"height", KeyType::HEIGHT},
890+ {"hyphenate-character", KeyType::HYPHENATE_CHARACTER},
891+ {"hyphenate-limit-chars", KeyType::HYPHENATE_LIMIT_CHARS},
892+ {"hyphens", KeyType::HYPHENS},
893+ {"image-orientation", KeyType::IMAGE_ORIENTATION},
894+ {"image-rendering", KeyType::IMAGE_RENDERING},
895+ {"image-resolution", KeyType::IMAGE_RESOLUTION},
896+ {"initial-letter", KeyType::INITIAL_LETTER},
897+ {"inline-size", KeyType::INLINE_SIZE},
898+ {"inset-block-end", KeyType::INSET_BLOCK_END},
899+ {"inset-block-start", KeyType::INSET_BLOCK_START},
900+ {"inset-block", KeyType::INSET_BLOCK},
901+ {"inset-block", KeyType::INSET_BLOCK},
902+ {"inset-inline-end", KeyType::INSET_INLINE_END},
903+ {"inset-inline-start", KeyType::INSET_INLINE_START},
904+ {"inset-inline", KeyType::INSET_INLINE},
905+ {"inset-inline", KeyType::INSET_INLINE},
906+ {"inset", KeyType::INSET},
907+ {"inset", KeyType::INSET},
908+ {"interpolate-size", KeyType::INTERPOLATE_SIZE},
909+ {"isolation", KeyType::ISOLATION},
910+ {"justify-content", KeyType::JUSTIFY_CONTENT},
911+ {"justify-items", KeyType::JUSTIFY_ITEMS},
912+ {"justify-self", KeyType::JUSTIFY_SELF},
913+ {"left", KeyType::LEFT},
914+ {"letter-spacing", KeyType::LETTER_SPACING},
915+ {"lighting-color", KeyType::LIGHTING_COLOR},
916+ {"line-break", KeyType::LINE_BREAK},
917+ {"line-clamp", KeyType::LINE_CLAMP},
918+ {"line-height-step", KeyType::LINE_HEIGHT_STEP},
919+ {"line-height", KeyType::LINE_HEIGHT},
920+ {"list-style-image", KeyType::LIST_STYLE_IMAGE},
921+ {"list-style-position", KeyType::LIST_STYLE_POSITION},
922+ {"list-style-type", KeyType::LIST_STYLE_TYPE},
923+ {"list-style", KeyType::LIST_STYLE},
924+ {"list-style", KeyType::LIST_STYLE},
925+ {"margin-block-end", KeyType::MARGIN_BLOCK_END},
926+ {"margin-block-start", KeyType::MARGIN_BLOCK_START},
927+ {"margin-block", KeyType::MARGIN_BLOCK},
928+ {"margin-bottom", KeyType::MARGIN_BOTTOM},
929+ {"margin-inline-end", KeyType::MARGIN_INLINE_END},
930+ {"margin-inline-start", KeyType::MARGIN_INLINE_START},
931+ {"margin-inline", KeyType::MARGIN_INLINE},
932+ {"margin-left", KeyType::MARGIN_LEFT},
933+ {"margin-right", KeyType::MARGIN_RIGHT},
934+ {"margin-top", KeyType::MARGIN_TOP},
935+ {"margin-trim", KeyType::MARGIN_TRIM},
936+ {"margin", KeyType::MARGIN},
937+ {"marker-end", KeyType::MARKER_END},
938+ {"marker-mid", KeyType::MARKER_MID},
939+ {"marker-start", KeyType::MARKER_START},
940+ {"marker", KeyType::MARKER},
941+ {"mask-border-mode", KeyType::MASK_BORDER_MODE},
942+ {"mask-border-outset", KeyType::MASK_BORDER_OUTSET},
943+ {"mask-border-repeat", KeyType::MASK_BORDER_REPEAT},
944+ {"mask-border-slice", KeyType::MASK_BORDER_SLICE},
945+ {"mask-border-source", KeyType::MASK_BORDER_SOURCE},
946+ {"mask-border-width", KeyType::MASK_BORDER_WIDTH},
947+ {"mask-border", KeyType::MASK_BORDER},
948+ {"mask-clip", KeyType::MASK_CLIP},
949+ {"mask-composite", KeyType::MASK_COMPOSITE},
950+ {"mask-image", KeyType::MASK_IMAGE},
951+ {"mask-mode", KeyType::MASK_MODE},
952+ {"mask-origin", KeyType::MASK_ORIGIN},
953+ {"mask-position", KeyType::MASK_POSITION},
954+ {"mask-repeat", KeyType::MASK_REPEAT},
955+ {"mask-size", KeyType::MASK_SIZE},
956+ {"mask-type", KeyType::MASK_TYPE},
957+ {"mask", KeyType::MASK},
958+ {"math-depth", KeyType::MATH_DEPTH},
959+ {"math-shift", KeyType::MATH_SHIFT},
960+ {"math-style", KeyType::MATH_STYLE},
961+ {"max-block-size", KeyType::MAX_BLOCK_SIZE},
962+ {"max-height", KeyType::MAX_HEIGHT},
963+ {"max-inline-size", KeyType::MAX_INLINE_SIZE},
964+ {"max-width", KeyType::MAX_WIDTH},
965+ {"min-block-size", KeyType::MIN_BLOCK_SIZE},
966+ {"min-height", KeyType::MIN_HEIGHT},
967+ {"min-inline-size", KeyType::MIN_INLINE_SIZE},
968+ {"min-width", KeyType::MIN_WIDTH},
969+ {"mix-blend-mode", KeyType::MIX_BLEND_MODE},
970+ {"object-fit", KeyType::OBJECT_FIT},
971+ {"object-position", KeyType::OBJECT_POSITION},
972+ {"offset-anchor", KeyType::OFFSET_ANCHOR},
973+ {"offset-distance", KeyType::OFFSET_DISTANCE},
974+ {"offset-path", KeyType::OFFSET_PATH},
975+ {"offset-position", KeyType::OFFSET_POSITION},
976+ {"offset-rotate", KeyType::OFFSET_ROTATE},
977+ {"offset", KeyType::OFFSET},
978+ {"opacity", KeyType::OPACITY},
979+ {"order", KeyType::ORDER},
980+ {"orphans", KeyType::ORPHANS},
981+ {"outline-color", KeyType::OUTLINE_COLOR},
982+ {"outline-offset", KeyType::OUTLINE_OFFSET},
983+ {"outline-style", KeyType::OUTLINE_STYLE},
984+ {"outline-width", KeyType::OUTLINE_WIDTH},
985+ {"outline", KeyType::OUTLINE},
986+ {"overflow-anchor", KeyType::OVERFLOW_ANCHOR},
987+ {"overflow-block", KeyType::OVERFLOW_BLOCK},
988+ {"overflow-clip-margin", KeyType::OVERFLOW_CLIP_MARGIN},
989+ {"overflow-inline", KeyType::OVERFLOW_INLINE},
990+ {"overflow-wrap", KeyType::OVERFLOW_WRAP},
991+ {"overflow-x", KeyType::OVERFLOW_X},
992+ {"overflow-y", KeyType::OVERFLOW_Y},
993+ {"overflow", KeyType::OVERFLOW},
994+ {"overlay", KeyType::OVERLAY},
995+ {"overscroll-behavior-block", KeyType::OVERSCROLL_BEHAVIOR_BLOCK},
996+ {"overscroll-behavior-inline", KeyType::OVERSCROLL_BEHAVIOR_INLINE},
997+ {"overscroll-behavior-x", KeyType::OVERSCROLL_BEHAVIOR_X},
998+ {"overscroll-behavior-y", KeyType::OVERSCROLL_BEHAVIOR_Y},
999+ {"overscroll-behavior", KeyType::OVERSCROLL_BEHAVIOR},
1000+ {"padding-block-end", KeyType::PADDING_BLOCK_END},
1001+ {"padding-block-start", KeyType::PADDING_BLOCK_START},
1002+ {"padding-block", KeyType::PADDING_BLOCK},
1003+ {"padding-bottom", KeyType::PADDING_BOTTOM},
1004+ {"padding-inline-end", KeyType::PADDING_INLINE_END},
1005+ {"padding-inline-start", KeyType::PADDING_INLINE_START},
1006+ {"padding-inline", KeyType::PADDING_INLINE},
1007+ {"padding-left", KeyType::PADDING_LEFT},
1008+ {"padding-right", KeyType::PADDING_RIGHT},
1009+ {"padding-top", KeyType::PADDING_TOP},
1010+ {"padding", KeyType::PADDING},
1011+ {"page-break-after", KeyType::PAGE_BREAK_AFTER},
1012+ {"page-break-before", KeyType::PAGE_BREAK_BEFORE},
1013+ {"page-break-inside", KeyType::PAGE_BREAK_INSIDE},
1014+ {"page", KeyType::PAGE},
1015+ {"paint-order", KeyType::PAINT_ORDER},
1016+ {"perspective-origin", KeyType::PERSPECTIVE_ORIGIN},
1017+ {"perspective", KeyType::PERSPECTIVE},
1018+ {"place-content", KeyType::PLACE_CONTENT},
1019+ {"place-items", KeyType::PLACE_ITEMS},
1020+ {"place-self", KeyType::PLACE_SELF},
1021+ {"pointer-events", KeyType::POINTER_EVENTS},
1022+ {"position-anchor", KeyType::POSITION_ANCHOR},
1023+ {"position-area", KeyType::POSITION_AREA},
1024+ {"position-try-fallbacks", KeyType::POSITION_TRY_FALLBACKS},
1025+ {"position-try-order", KeyType::POSITION_TRY_ORDER},
1026+ {"position-try", KeyType::POSITION_TRY},
1027+ {"position-visibility", KeyType::POSITION_VISIBILITY},
1028+ {"position", KeyType::POSITION},
1029+ {"print-color-adjust", KeyType::PRINT_COLOR_ADJUST},
1030+ {"quotes", KeyType::QUOTES},
1031+ {"r", KeyType::R},
1032+ {"reading-flow", KeyType::READING_FLOW},
1033+ {"reading-order", KeyType::READING_ORDER},
1034+ {"resize", KeyType::RESIZE},
1035+ {"right", KeyType::RIGHT},
1036+ {"rotate", KeyType::ROTATE},
1037+ {"row-gap", KeyType::ROW_GAP},
1038+ {"ruby-align", KeyType::RUBY_ALIGN},
1039+ {"ruby-position", KeyType::RUBY_POSITION},
1040+ {"rx", KeyType::RX},
1041+ {"ry", KeyType::RY},
1042+ {"scale", KeyType::SCALE},
1043+ {"scroll-behavior", KeyType::SCROLL_BEHAVIOR},
1044+ {"scroll-margin-block-end", KeyType::SCROLL_MARGIN_BLOCK_END},
1045+ {"scroll-margin-block-start", KeyType::SCROLL_MARGIN_BLOCK_START},
1046+ {"scroll-margin-block", KeyType::SCROLL_MARGIN_BLOCK},
1047+ {"scroll-margin-bottom", KeyType::SCROLL_MARGIN_BOTTOM},
1048+ {"scroll-margin-inline-end", KeyType::SCROLL_MARGIN_INLINE_END},
1049+ {"scroll-margin-inline-start", KeyType::SCROLL_MARGIN_INLINE_START},
1050+ {"scroll-margin-inline", KeyType::SCROLL_MARGIN_INLINE},
1051+ {"scroll-margin-left", KeyType::SCROLL_MARGIN_LEFT},
1052+ {"scroll-margin-right", KeyType::SCROLL_MARGIN_RIGHT},
1053+ {"scroll-margin-top", KeyType::SCROLL_MARGIN_TOP},
1054+ {"scroll-margin", KeyType::SCROLL_MARGIN},
1055+ {"scroll-marker-group", KeyType::SCROLL_MARKER_GROUP},
1056+ {"scroll-padding-block-end", KeyType::SCROLL_PADDING_BLOCK_END},
1057+ {"scroll-padding-block-start", KeyType::SCROLL_PADDING_BLOCK_START},
1058+ {"scroll-padding-block", KeyType::SCROLL_PADDING_BLOCK},
1059+ {"scroll-padding-bottom", KeyType::SCROLL_PADDING_BOTTOM},
1060+ {"scroll-padding-inline-end", KeyType::SCROLL_PADDING_INLINE_END},
1061+ {"scroll-padding-inline-start", KeyType::SCROLL_PADDING_INLINE_START},
1062+ {"scroll-padding-inline", KeyType::SCROLL_PADDING_INLINE},
1063+ {"scroll-padding-left", KeyType::SCROLL_PADDING_LEFT},
1064+ {"scroll-padding-right", KeyType::SCROLL_PADDING_RIGHT},
1065+ {"scroll-padding-top", KeyType::SCROLL_PADDING_TOP},
1066+ {"scroll-padding", KeyType::SCROLL_PADDING},
1067+ {"scroll-snap-align", KeyType::SCROLL_SNAP_ALIGN},
1068+ {"scroll-snap-stop", KeyType::SCROLL_SNAP_STOP},
1069+ {"scroll-snap-type", KeyType::SCROLL_SNAP_TYPE},
1070+ {"scroll-timeline-axis", KeyType::SCROLL_TIMELINE_AXIS},
1071+ {"scroll-timeline-name", KeyType::SCROLL_TIMELINE_NAME},
1072+ {"scroll-timeline", KeyType::SCROLL_TIMELINE},
1073+ {"scrollbar-color", KeyType::SCROLLBAR_COLOR},
1074+ {"scrollbar-gutter", KeyType::SCROLLBAR_GUTTER},
1075+ {"scrollbar-width", KeyType::SCROLLBAR_WIDTH},
1076+ {"shape-image-threshold", KeyType::SHAPE_IMAGE_THRESHOLD},
1077+ {"shape-margin", KeyType::SHAPE_MARGIN},
1078+ {"shape-outside", KeyType::SHAPE_OUTSIDE},
1079+ {"shape-rendering", KeyType::SHAPE_RENDERING},
1080+ {"speak-as", KeyType::SPEAK_AS},
1081+ {"stop-color", KeyType::STOP_COLOR},
1082+ {"stop-opacity", KeyType::STOP_OPACITY},
1083+ {"stroke-dasharray", KeyType::STROKE_DASHARRAY},
1084+ {"stroke-dashoffset", KeyType::STROKE_DASHOFFSET},
1085+ {"stroke-linecap", KeyType::STROKE_LINECAP},
1086+ {"stroke-linejoin", KeyType::STROKE_LINEJOIN},
1087+ {"stroke-miterlimit", KeyType::STROKE_MITERLIMIT},
1088+ {"stroke-opacity", KeyType::STROKE_OPACITY},
1089+ {"stroke-width", KeyType::STROKE_WIDTH},
1090+ {"stroke", KeyType::STROKE},
1091+ {"tab-size", KeyType::TAB_SIZE},
1092+ {"table-layout", KeyType::TABLE_LAYOUT},
1093+ {"text-align-last", KeyType::TEXT_ALIGN_LAST},
1094+ {"text-align", KeyType::TEXT_ALIGN},
1095+ {"text-anchor", KeyType::TEXT_ANCHOR},
1096+ {"text-box-edge", KeyType::TEXT_BOX_EDGE},
1097+ {"text-box-trim", KeyType::TEXT_BOX_TRIM},
1098+ {"text-box", KeyType::TEXT_BOX},
1099+ {"text-combine-upright", KeyType::TEXT_COMBINE_UPRIGHT},
1100+ {"text-decoration-color", KeyType::TEXT_DECORATION_COLOR},
1101+ {"text-decoration-line", KeyType::TEXT_DECORATION_LINE},
1102+ {"text-decoration-skip-ink", KeyType::TEXT_DECORATION_SKIP_INK},
1103+ {"text-decoration-skip", KeyType::TEXT_DECORATION_SKIP},
1104+ {"text-decoration-style", KeyType::TEXT_DECORATION_STYLE},
1105+ {"text-decoration-thickness", KeyType::TEXT_DECORATION_THICKNESS},
1106+ {"text-decoration", KeyType::TEXT_DECORATION},
1107+ {"text-emphasis-color", KeyType::TEXT_EMPHASIS_COLOR},
1108+ {"text-emphasis-position", KeyType::TEXT_EMPHASIS_POSITION},
1109+ {"text-emphasis-style", KeyType::TEXT_EMPHASIS_STYLE},
1110+ {"text-emphasis", KeyType::TEXT_EMPHASIS},
1111+ {"text-indent", KeyType::TEXT_INDENT},
1112+ {"text-justify", KeyType::TEXT_JUSTIFY},
1113+ {"text-orientation", KeyType::TEXT_ORIENTATION},
1114+ {"text-overflow", KeyType::TEXT_OVERFLOW},
1115+ {"text-rendering", KeyType::TEXT_RENDERING},
1116+ {"text-shadow", KeyType::TEXT_SHADOW},
1117+ {"text-size-adjust", KeyType::TEXT_SIZE_ADJUST},
1118+ {"text-spacing-trim", KeyType::TEXT_SPACING_TRIM},
1119+ {"text-transform", KeyType::TEXT_TRANSFORM},
1120+ {"text-underline-offset", KeyType::TEXT_UNDERLINE_OFFSET},
1121+ {"text-underline-position", KeyType::TEXT_UNDERLINE_POSITION},
1122+ {"text-wrap-mode", KeyType::TEXT_WRAP_MODE},
1123+ {"text-wrap-style", KeyType::TEXT_WRAP_STYLE},
1124+ {"text-wrap", KeyType::TEXT_WRAP},
1125+ {"timeline-scope", KeyType::TIMELINE_SCOPE},
1126+ {"top", KeyType::TOP},
1127+ {"touch-action", KeyType::TOUCH_ACTION},
1128+ {"transform-box", KeyType::TRANSFORM_BOX},
1129+ {"transform-origin", KeyType::TRANSFORM_ORIGIN},
1130+ {"transform-style", KeyType::TRANSFORM_STYLE},
1131+ {"transform", KeyType::TRANSFORM},
1132+ {"transition-behavior", KeyType::TRANSITION_BEHAVIOR},
1133+ {"transition-delay", KeyType::TRANSITION_DELAY},
1134+ {"transition-duration", KeyType::TRANSITION_DURATION},
1135+ {"transition-property", KeyType::TRANSITION_PROPERTY},
1136+ {"transition-timing-function", KeyType::TRANSITION_TIMING_FUNCTION},
1137+ {"transition", KeyType::TRANSITION},
1138+ {"translate", KeyType::TRANSLATE},
1139+ {"unicode-bidi", KeyType::UNICODE_BIDI},
1140+ {"user-modify", KeyType::USER_MODIFY},
1141+ {"user-select", KeyType::USER_SELECT},
1142+ {"vector-effect", KeyType::VECTOR_EFFECT},
1143+ {"vertical-align", KeyType::VERTICAL_ALIGN},
1144+ {"view-timeline-axis", KeyType::VIEW_TIMELINE_AXIS},
1145+ {"view-timeline-inset", KeyType::VIEW_TIMELINE_INSET},
1146+ {"view-timeline-name", KeyType::VIEW_TIMELINE_NAME},
1147+ {"view-timeline", KeyType::VIEW_TIMELINE},
1148+ {"view-transition-class", KeyType::VIEW_TRANSITION_CLASS},
1149+ {"view-transition-name", KeyType::VIEW_TRANSITION_NAME},
1150+ {"visibility", KeyType::VISIBILITY},
1151+ {"white-space-collapse", KeyType::WHITE_SPACE_COLLAPSE},
1152+ {"white-space", KeyType::WHITE_SPACE},
1153+ {"widows", KeyType::WIDOWS},
1154+ {"width", KeyType::WIDTH},
1155+ {"will-change", KeyType::WILL_CHANGE},
1156+ {"word-break", KeyType::WORD_BREAK},
1157+ {"word-spacing", KeyType::WORD_SPACING},
1158+ {"writing-mode", KeyType::WRITING_MODE},
1159+ {"x", KeyType::X},
1160+ {"y", KeyType::Y},
1161+ {"z-index", KeyType::Z_INDEX},
1162+ {"zoom", KeyType::ZOOM}
1163+};
1164
1165 static const std::unordered_map<std::string_view, unsigned int> kColors {
1166 {"black", 0x000000},
1167@@ -513,7 +987,7 @@ static const std::unordered_map<std::string_view, unsigned int> kColors {
1168 {"teal", 0x008080},
1169 {"thistle", 0xd8bfd8},
1170 {"tomato", 0xff6347},
1171- {"transparent", 0x00000000.},
1172+ {"transparent", 0x00000000},
1173 {"turquoise", 0x40e0d0},
1174 {"violet", 0xee82ee},
1175 {"wheat", 0xf5deb3},
1176@@ -582,137 +1056,125 @@ static constexpr SuffixParse table[] = {
1177
1178
1179 static const std::unordered_map<std::string_view, UnitType> kMatch{
1180- {"+", UnitType::ADD},
1181- {"-", UnitType::SUB},
1182- {"*", UnitType::MULT},
1183- {"/", UnitType::DIV},
1184- {"==", UnitType::EQ},
1185- {">", UnitType::GT},
1186- {"<", UnitType::LT},
1187- {">=", UnitType::GE},
1188- {"<=", UnitType::LE},
1189- {"infinity", UnitType::INF},
1190- {"-infinity", UnitType::NEGINF},
1191- {"NaN", UnitType::NaN},
1192- {"e", UnitType::E},
1193- {"pi", UnitType::PI},
1194- {"content-box", UnitType::CONTENT},
1195- {"padding-box", UnitType::PADDING},
1196- {"border-box", UnitType::BORDER},
1197- {"margin-box", UnitType::MARGIN},
1198- {"fill-box", UnitType::FILL},
1199- {"stroke-box", UnitType::STROKE},
1200- {"view-box", UnitType::VIEW},
1201- {"space-between", UnitType::BETWEEN},
1202- {"space-around", UnitType::AROUND},
1203- {"space-evenly", UnitType::EVENLY},
1204- {"stretch", UnitType::STRETCH},
1205- {"normal", UnitType::NORMAL},
1206- {"contents", UnitType::CONTENTS},
1207- {"none", UnitType::NONE},
1208- {"flow", UnitType::FLOW},
1209- {"flow-root", UnitType::FLOW_ROOT},
1210- {"table", UnitType::TABLE},
1211- {"flex", UnitType::FLEX},
1212- {"grid", UnitType::GRID},
1213- {"ruby", UnitType::RUBY},
1214- {"table-row-group", UnitType::TABLE_ROW_GROUP},
1215- {"table-header-group", UnitType::TABLE_HEADER_GROUP},
1216- {"table-footer-group", UnitType::TABLE_FOOTER_GROUP},
1217- {"table-column-group", UnitType::TABLE_COLUMN_GROUP},
1218- {"table-row", UnitType::TABLE_ROW},
1219- {"table-cell", UnitType::TABLE_CELL},
1220- {"table-column", UnitType::TABLE_COLUMN},
1221- {"table-caption", UnitType::TABLE_CAPTION},
1222- {"ruby-base", UnitType::RUBY_BASE},
1223- {"ruby-text", UnitType::RUBY_TEXT},
1224- {"ruby-base-container", UnitType::RUBY_BASE_CONTAINER},
1225- {"ruby-text-container", UnitType::RUBY_TEXT_CONTAINER},
1226- {"inline-block", UnitType::INLINE_BLOCK},
1227- {"inline-table", UnitType::INLINE_TABLE},
1228- {"inline-flex", UnitType::INLINE_FLEX},
1229- {"inline-grid", UnitType::INLINE_GRID},
1230- {"list-item", UnitType::LISTITEM},
1231- {"block", UnitType::BLOCK},
1232- {"inline", UnitType::INLINE},
1233- {"run-in", UnitType::RUN_IN},
1234- {"linear", UnitType::LINEAR},
1235- {"ease", UnitType::EASE},
1236- {"ease-in", UnitType::EASE_IN},
1237- {"ease-out", UnitType::EASE_OUT},
1238- {"ease-in-out", UnitType::EASE_IN_OUT},
1239- {"step-start", UnitType::STEP_START},
1240- {"step-end", UnitType::STEP_END},
1241- {"jump-start", UnitType::JUMP_START},
1242- {"jump-end", UnitType::JUMP_END},
1243- {"jump-none", UnitType::JUMP_NONE},
1244- {"jump-both", UnitType::JUMP_BOTH},
1245- {"serif", UnitType::SERIF},
1246- {"sans-serif", UnitType::SANS_SERIF},
1247- {"monospace", UnitType::MONOSPACE},
1248- {"cursive", UnitType::CURSIVE},
1249- {"fantasy", UnitType::FANTASY},
1250- {"system-ui", UnitType::SYSTEM_UI},
1251- {"ui-serif", UnitType::UI_SERIF},
1252- {"ui-sans-serif", UnitType::UI_SANS_SERIF},
1253- {"ui-monospace", UnitType::UI_MONOSPACE},
1254- {"ui-rounded", UnitType::UI_ROUNDED},
1255- {"math", UnitType::MATH},
1256- {"fangsong", UnitType::FANGSONG},
1257- {"top", UnitType::TOP},
1258- {"left", UnitType::LEFT},
1259- {"bottom", UnitType::BOTTOM},
1260- {"right", UnitType::RIGHT},
1261- {"center", UnitType::CENTER},
1262- {"inline-start", UnitType::INLINE_START},
1263- {"inline-end", UnitType::INLINE_END},
1264- {"block-start", UnitType::BLOCK_START},
1265- {"block-end", UnitType::BLOCK_END},
1266- {"self-start", UnitType::SELF_START},
1267- {"self-end", UnitType::SELF_END},
1268- {"flex-start", UnitType::FLEX_START},
1269- {"flex-end", UnitType::FLEX_END},
1270- {"circle", UnitType::CIRCLE},
1271- {"ellipse", UnitType::ELLIPSE},
1272- {"shorter hue", UnitType::SHORTER_HUE},
1273- {"longer hue", UnitType::LONGER_HUE},
1274- {"increasing hue", UnitType::INCREASING_HUE},
1275- {"decreasing hue", UnitType::DECREASING_HUE},
1276- {"dotted", UnitType::DOTTED},
1277- {"dashed", UnitType::DASHED},
1278- {"solid", UnitType::SOLID},
1279- {"double", UnitType::DOUBLE},
1280- {"groove", UnitType::GROOVE},
1281- {"ridge", UnitType::RIDGE},
1282- {"inset", UnitType::INSET},
1283- {"outset", UnitType::OUTSET},
1284- {"baseline", UnitType::FIRST},
1285- {"first baseline", UnitType::FIRST},
1286- {"last baseline", UnitType::LAST},
1287- {"safe", UnitType::SAFE},
1288- {"unsafe", UnitType::UNSAFE},
1289- {"visible", UnitType::VISIBLE},
1290- {"clip", UnitType::CLIP},
1291- {"scroll", UnitType::SCROLL},
1292- {"inherit", UnitType::INHERIT},
1293- {"initial", UnitType::INITIAL},
1294- {"revert", UnitType::REVERT},
1295- {"revert-layer", UnitType::REVERT_LAYER},
1296- {"unset", UnitType::UNSET},
1297+ {"+", UnitType::ADD},
1298+ {"-", UnitType::SUB},
1299+ {"*", UnitType::MULT},
1300+ {"/", UnitType::DIV},
1301+ {"==", UnitType::EQ},
1302+ {">", UnitType::GT},
1303+ {"<", UnitType::LT},
1304+ {">=", UnitType::GE},
1305+ {"<=", UnitType::LE},
1306+ {"infinity", UnitType::INF},
1307+ {"-infinity", UnitType::NEGINF},
1308+ {"NaN", UnitType::NaN},
1309+ {"e", UnitType::E},
1310+ {"pi", UnitType::PI},
1311+ {"content-box", UnitType::CONTENT},
1312+ {"padding-box", UnitType::PADDING},
1313+ {"border-box", UnitType::BORDER},
1314+ {"margin-box", UnitType::MARGIN},
1315+ {"fill-box", UnitType::FILL},
1316+ {"stroke-box", UnitType::STROKE},
1317+ {"view-box", UnitType::VIEW},
1318+ {"space-between", UnitType::BETWEEN},
1319+ {"space-around", UnitType::AROUND},
1320+ {"space-evenly", UnitType::EVENLY},
1321+ {"stretch", UnitType::STRETCH},
1322+ {"normal", UnitType::NORMAL},
1323+ {"contents", UnitType::CONTENTS},
1324+ {"none", UnitType::NONE},
1325+ {"flow", UnitType::FLOW},
1326+ {"flow-root", UnitType::FLOW_ROOT},
1327+ {"table", UnitType::TABLE},
1328+ {"flex", UnitType::FLEX},
1329+ {"grid", UnitType::GRID},
1330+ {"ruby", UnitType::RUBY},
1331+ {"table-row-group", UnitType::TABLE_ROW_GROUP},
1332+ {"table-header-group", UnitType::TABLE_HEADER_GROUP},
1333+ {"table-footer-group", UnitType::TABLE_FOOTER_GROUP},
1334+ {"table-column-group", UnitType::TABLE_COLUMN_GROUP},
1335+ {"table-row", UnitType::TABLE_ROW},
1336+ {"table-cell", UnitType::TABLE_CELL},
1337+ {"table-column", UnitType::TABLE_COLUMN},
1338+ {"table-caption", UnitType::TABLE_CAPTION},
1339+ {"ruby-base", UnitType::RUBY_BASE},
1340+ {"ruby-text", UnitType::RUBY_TEXT},
1341+ {"ruby-base-container", UnitType::RUBY_BASE_CONTAINER},
1342+ {"ruby-text-container", UnitType::RUBY_TEXT_CONTAINER},
1343+ {"inline-block", UnitType::INLINE_BLOCK},
1344+ {"inline-table", UnitType::INLINE_TABLE},
1345+ {"inline-flex", UnitType::INLINE_FLEX},
1346+ {"inline-grid", UnitType::INLINE_GRID},
1347+ {"list-item", UnitType::LISTITEM},
1348+ {"block", UnitType::BLOCK},
1349+ {"inline", UnitType::INLINE},
1350+ {"run-in", UnitType::RUN_IN},
1351+ {"linear", UnitType::LINEAR},
1352+ {"ease", UnitType::EASE},
1353+ {"ease-in", UnitType::EASE_IN},
1354+ {"ease-out", UnitType::EASE_OUT},
1355+ {"ease-in-out", UnitType::EASE_IN_OUT},
1356+ {"step-start", UnitType::STEP_START},
1357+ {"step-end", UnitType::STEP_END},
1358+ {"jump-start", UnitType::JUMP_START},
1359+ {"jump-end", UnitType::JUMP_END},
1360+ {"jump-none", UnitType::JUMP_NONE},
1361+ {"jump-both", UnitType::JUMP_BOTH},
1362+ {"serif", UnitType::SERIF},
1363+ {"sans-serif", UnitType::SANS_SERIF},
1364+ {"monospace", UnitType::MONOSPACE},
1365+ {"cursive", UnitType::CURSIVE},
1366+ {"fantasy", UnitType::FANTASY},
1367+ {"system-ui", UnitType::SYSTEM_UI},
1368+ {"ui-serif", UnitType::UI_SERIF},
1369+ {"ui-sans-serif", UnitType::UI_SANS_SERIF},
1370+ {"ui-monospace", UnitType::UI_MONOSPACE},
1371+ {"ui-rounded", UnitType::UI_ROUNDED},
1372+ {"math", UnitType::MATH},
1373+ {"fangsong", UnitType::FANGSONG},
1374+ {"top", UnitType::TOP},
1375+ {"left", UnitType::LEFT},
1376+ {"bottom", UnitType::BOTTOM},
1377+ {"right", UnitType::RIGHT},
1378+ {"center", UnitType::CENTER},
1379+ {"inline-start", UnitType::INLINE_START},
1380+ {"inline-end", UnitType::INLINE_END},
1381+ {"block-start", UnitType::BLOCK_START},
1382+ {"block-end", UnitType::BLOCK_END},
1383+ {"self-start", UnitType::SELF_START},
1384+ {"self-end", UnitType::SELF_END},
1385+ {"flex-start", UnitType::FLEX_START},
1386+ {"flex-end", UnitType::FLEX_END},
1387+ {"circle", UnitType::CIRCLE},
1388+ {"ellipse", UnitType::ELLIPSE},
1389+ {"shorter hue", UnitType::SHORTER_HUE},
1390+ {"longer hue", UnitType::LONGER_HUE},
1391+ {"increasing hue", UnitType::INCREASING_HUE},
1392+ {"decreasing hue", UnitType::DECREASING_HUE},
1393+ {"dotted", UnitType::DOTTED},
1394+ {"dashed", UnitType::DASHED},
1395+ {"solid", UnitType::SOLID},
1396+ {"double", UnitType::DOUBLE},
1397+ {"groove", UnitType::GROOVE},
1398+ {"ridge", UnitType::RIDGE},
1399+ {"inset", UnitType::INSET},
1400+ {"outset", UnitType::OUTSET},
1401+ {"baseline", UnitType::FIRST},
1402+ {"first baseline", UnitType::FIRST},
1403+ {"last baseline", UnitType::LAST},
1404+ {"safe", UnitType::SAFE},
1405+ {"unsafe", UnitType::UNSAFE},
1406+ {"visible", UnitType::VISIBLE},
1407+ {"clip", UnitType::CLIP},
1408+ {"scroll", UnitType::SCROLL},
1409+ {"inherit", UnitType::INHERIT},
1410+ {"initial", UnitType::INITIAL},
1411+ {"revert", UnitType::REVERT},
1412+ {"revert-layer", UnitType::REVERT_LAYER},
1413+ {"unset", UnitType::UNSET},
1414 };
1415
1416-/*
1417- Note to self:
1418- make a kMap object that will map values that have conflicts like none
1419- In another function use the key to find the type
1420-
1421- overflow: hidden
1422-
1423- today work on fixing the double alloc and map with prop keys
1424-
1425- what to do about strings
1426-*/
1427-
1428 static const std::unordered_map<std::string_view, UnitType> kFunc{
1429 {"calc", UnitType::CALC},
1430 {"min", UnitType::MIN},
1431@@ -767,8 +1229,8 @@ static const std::unordered_map<std::string_view, float> kAbsSize{
1432 {"large",1.2f}, {"x-large",1.5f}, {"xx-large",2.0f}, {"xxx-large",3.0f}
1433 };
1434
1435-std::vector<Unit> getUnit(std::string key, std::string value) {
1436- std::vector<Unit> units;
1437+std::vector<Unit> getUnit(std::string value) {
1438+ std::vector<Unit> units;
1439
1440 std::string buffer = "";
1441 int parenDepth = 0;
1442@@ -847,12 +1309,12 @@ std::vector<Unit> getUnit(std::string key, std::string value) {
1443 unit.type = it->second;
1444 // the value is not used here
1445 found = true;
1446- } else if (auto it = kColor.find(buffer); it != kColor.end()) {
1447+ } else if (auto it = kColors.find(buffer); it != kColors.end()) {
1448 /*
1449 Color Matching
1450 */
1451 unit.type = UnitType::HEX;
1452- unit.value.ENUM = it->second;
1453+ unit.value.UINT = it->second;
1454 found = true;
1455 } else {
1456 for (const auto& [suffix, type, trim] : table) {
1457@@ -890,6 +1352,9 @@ std::vector<Unit> getUnit(std::string key, std::string value) {
1458 found = false;
1459 }
1460 }
1461+ /*
1462+ need to handle strings
1463+ */
1464 }
1465
1466 if (found) {
1467@@ -916,12 +1381,15 @@ std::vector<Unit> getUnit(std::string key, std::string value) {
1468 return units;
1469 }
1470
1471-void StyleHandler::parseStream(std::istream& inputStream) {
1472+Style parseCSS(std::istream& inputStream) {
1473 // nowhitespace: value(can have whitespace); = property
1474 // a selector name is anything before a { up to a ; or a }
1475- Sheet* root = &window->CSS.root;
1476-
1477- Sheet* current = root;
1478+ std::vector<Style*> stack;
1479+
1480+ // change to a stack based tree
1481+
1482+ Style current{};
1483+ stack.push_back(¤t);
1484 // how to handle @import
1485
1486 std::string buffer;
1487@@ -956,7 +1424,7 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1488 // Parse the selector into its parts
1489 std::vector<std::vector<std::string>> parts = parseSelectorParts(buffer);
1490
1491- if (current->selector.size() > 0) {
1492+ if (current.selector.size() > 0) {
1493 // To be able to handle a substitution with a parent that has h1, h2
1494 // we need to rebuild the selector so we can add new copies
1495 std::vector<std::vector<std::string>> subd;
1496@@ -978,11 +1446,11 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1497 // Child: [[& .class, &, &]]
1498 // Result: [[h1 .class, h1, h1]]
1499 // [[h2 .class, h2, h2]]
1500- for (size_t e = 0; e < current->selector.size(); e++) {
1501+ for (size_t e = 0; e < current.selector.size(); e++) {
1502 std::vector<std::string> temp;
1503 for (size_t f = 0; f < parts[i].size(); f++) {
1504 if (parts[i][f] == "&") {
1505- for (auto p : current->selector[e]) {
1506+ for (auto p : current.selector[e]) {
1507 temp.push_back(p);
1508 }
1509 } else {
1510@@ -1001,18 +1469,17 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1511 }
1512
1513 // Find who the parent is
1514- Sheet newSheet;
1515- newSheet.parent = current;
1516+ Style newSheet{};
1517 newSheet.selector = parts;
1518- current->children.push_back(newSheet);
1519+ current.addChild(newSheet);
1520
1521- current = ¤t->children.back();
1522+ current = current.children.back();
1523
1524 // here we need to take the selector (buffer)
1525 // and find out what type it is. Also need to manage the nesting
1526 if (parts[0][0][0] == '@') {
1527 if (parts[0][0] == "@container") {
1528- current->type = SheetType::CONTAINER;
1529+ current.type = StyleType::CONTAINER;
1530 bool hasName = false;
1531 if (parts[0].size() >= 3) {
1532 // @container not (width < 400px)
1533@@ -1020,7 +1487,7 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1534 // @container (width > 400px) or|and (height > 400px)
1535 if (parts[0].size() >= 5) {
1536 if (parts[0][5] != "and" || parts[0][5] != "or") {
1537- current->name = parts[0][2];
1538+ current.name = parts[0][2];
1539 hasName = true;
1540 }
1541 }
1542@@ -1029,79 +1496,69 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1543 // If a name is present then remove the name and tag from the selector
1544 // else just remove the @container
1545 if (hasName) {
1546- current->selector[0] = std::vector<std::string>(current->selector[0].begin() + 3, current->selector[0].end());
1547+ current.selector[0] = std::vector<std::string>(current.selector[0].begin() + 3, current.selector[0].end());
1548 } else {
1549- current->selector[0] = std::vector<std::string>(current->selector[0].begin() + 1, current->selector[0].end());
1550+ current.selector[0] = std::vector<std::string>(current.selector[0].begin() + 1, current.selector[0].end());
1551 }
1552 } else if (parts[0][0] == "@counter-style") {
1553- current->name = parts[0][2];
1554- current->type = SheetType::COUNTER;
1555+ current.name = parts[0][2];
1556+ current.type = StyleType::COUNTER;
1557 } else if (parts[0][0] == "@font-face") {
1558- current->type = SheetType::FONTFACE;
1559+ current.type = StyleType::FONTFACE;
1560 } else if (parts[0][0] == "@font-feature") {
1561- current->type = SheetType::FONTFEATURE;
1562+ current.type = StyleType::FONTFEATURE;
1563 } else if (parts[0][0] == "@swash") {
1564- current->type = SheetType::SWASH;
1565+ current.type = StyleType::SWASH;
1566 } else if (parts[0][0] == "@annotation") {
1567- current->type = SheetType::ANNOTATION;
1568+ current.type = StyleType::ANNOTATION;
1569 } else if (parts[0][0] == "@ornaments") {
1570- current->type = SheetType::ORNAMENTS;
1571+ current.type = StyleType::ORNAMENTS;
1572 } else if (parts[0][0] == "@stylistic") {
1573- current->type = SheetType::STYLISTIC;
1574+ current.type = StyleType::STYLISTIC;
1575 } else if (parts[0][0] == "@styleset") {
1576- current->type = SheetType::STYLESET;
1577+ current.type = StyleType::STYLESET;
1578 } else if (parts[0][0] == "@character-varient") {
1579- current->type = SheetType::CHARACTERVARIANT;
1580+ current.type = StyleType::CHARACTERVARIANT;
1581 } else if (parts[0][0] == "@font-palette-values") {
1582- current->type = SheetType::FONTPALETTEVALUES;
1583- current->name = parts[0][2];
1584+ current.type = StyleType::FONTPALETTEVALUES;
1585+ current.name = parts[0][2];
1586 } else if (parts[0][0] == "@keyframes") {
1587- current->type = SheetType::KEYFRAMES;
1588- current->name = parts[0][2];
1589+ current.type = StyleType::KEYFRAMES;
1590+ current.name = parts[0][2];
1591 } else if (parts[0][0] == "@layer") {
1592- current->type = SheetType::LAYER;
1593+ current.type = StyleType::LAYER;
1594 } else if (parts[0][0] == "@media") {
1595- current->type = SheetType::MEDIA;
1596+ current.type = StyleType::MEDIA;
1597 } else if (parts[0][0] == "@property") {
1598- current->type = SheetType::PROPERTY;
1599- current->name = parts[0][2];
1600+ current.type = StyleType::PROPERTY;
1601+ current.name = parts[0][2];
1602 } else if (parts[0][0] == "@starting-style") {
1603- current->type = SheetType::STARTINGSTYLE;
1604+ current.type = StyleType::STARTINGSTYLE;
1605 }
1606 } else {
1607- current->type = SheetType::STYLE;
1608+ current.type = StyleType::STYLE;
1609 }
1610
1611
1612 buffer.clear();
1613 } else if (ch == '}') {
1614- // Calculate the basemap (more info in grim.h)
1615- std::vector<std::string> targetParts = current->selector[current->selector.size()-1];
1616- for (auto p : targetParts) {
1617- if (current->parent->basemap.find(p) != current->parent->basemap.end()) {
1618- current->parent->basemap[p].push_back(window->CSS.index);
1619- } else {
1620- std::vector<size_t> bm = {window->CSS.index};
1621- current->parent->basemap[p] = bm;
1622- }
1623- }
1624-
1625- window->CSS.index++;
1626+
1627
1628- if (current->parent != nullptr) {
1629- current = current->parent;
1630+ if (stack.size() > 0) {
1631+ current = *stack.back();
1632+ stack.pop_back();
1633 }
1634
1635 buffer.clear();
1636 } else if (ch == ';') {
1637 if (buffer[0] == '@') {
1638 // Single line at-rule
1639- Sheet inlineRule;
1640+ Style inlineRule;
1641 std::vector<std::vector<std::string>> parts = parseSelectorParts(buffer);
1642 inlineRule.selector = parts;
1643
1644 if (parts[0][0] == "@import") {
1645- inlineRule.path = parts[0][2];
1646+ inlineRule.selector = parts;
1647
1648 if (parts[0].size() > 3) {
1649 // See if the last word ends in )
1650@@ -1116,7 +1573,7 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1651
1652 }
1653
1654- current->children.push_back(inlineRule);
1655+ current.children.push_back(inlineRule);
1656
1657 } else {
1658 // end of a style property
1659@@ -1142,9 +1599,16 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1660 }
1661
1662 if (key.length() > 2 && key[0] == '-' && key[1] == '-') {
1663- current->variables[key] = value;
1664+ current.variables[key] = getUnit(value);
1665 } else {
1666- current->properties[key] = getUnit(key,value);
1667+ KeyType keyENUM;
1668+
1669+ if (auto it = keySearch.find(key); it != keySearch.end()) {
1670+ keyENUM = it->second;
1671+ } else {
1672+ std::cout << "Invalid property name: " << key << std::endl;
1673+ }
1674+ current.properties[keyENUM] = getUnit(value);
1675 }
1676 }
1677 buffer.clear();
1678@@ -1154,8 +1618,8 @@ void StyleHandler::parseStream(std::istream& inputStream) {
1679 }
1680 }
1681
1682-std::unordered_map<std::string, std::string> parseCSSInline(std::string inlineStyles) {
1683- std::unordered_map<std::string, std::string> props;
1684+std::unordered_map<KeyType, std::vector<Unit>> parseCSSInline(std::string inlineStyles) {
1685+ std::unordered_map<KeyType, std::vector<Unit>> props;
1686
1687 std::string buffer;
1688
1689@@ -1186,7 +1650,14 @@ std::unordered_map<std::string, std::string> parseCSSInline(std::string inlineSt
1690 }
1691 }
1692
1693- props[key] = value;
1694+ KeyType keyENUM;
1695+
1696+ if (auto it = keySearch.find(key); it != keySearch.end()) {
1697+ keyENUM = it->second;
1698+ } else {
1699+ std::cout << "Invalid property name: " << key << std::endl;
1700+ }
1701+ props[keyENUM] = getUnit(value);
1702
1703 buffer.clear();
1704 } else {
1705diff --git a/tests/css_parser.cc b/tests/css_parser.cc
1706index 5bd32c1..9150bc3 100755
1707--- a/tests/css_parser.cc
1708+++ b/tests/css_parser.cc
1709@@ -15,77 +15,47 @@ std::string printSelector(std::vector<std::vector<std::string>> selector) {
1710 return out;
1711 }
1712
1713-void trimSpace2(std::string& str) {
1714- if (str.empty()) {
1715- return;
1716- }
1717-
1718- // Find first non-space
1719- size_t first_non_space = 0;
1720- while (first_non_space < str.length() && std::isspace(str[first_non_space])) {
1721- first_non_space++;
1722- }
1723-
1724- // If all spaces or empty
1725- if (first_non_space == str.length()) {
1726- str.clear(); // Set to empty string
1727- return;
1728- }
1729-
1730- // Find last non-space
1731- size_t last_non_space = str.length() - 1;
1732- while (last_non_space >= first_non_space && std::isspace(str[last_non_space])) {
1733- last_non_space--;
1734- }
1735-
1736- // Erase trailing spaces
1737- if (last_non_space < str.length() - 1) {
1738- str.erase(last_non_space + 1);
1739- }
1740-
1741- // Erase leading spaces
1742- if (first_non_space > 0) {
1743- str.erase(0, first_non_space);
1744- }
1745-}
1746-
1747-void compareStyle(std::string selector, std::unordered_map<std::string, std::string> props, Sheet sheet, SheetType type) {
1748+void compareStyle(std::string selector, std::unordered_map<KeyType, std::vector<Unit>> props, Style style, StyleType type) {
1749 std::vector<std::vector<std::string>> parts = parseSelectorParts(selector);
1750 INFO("Expected: \"" + selector+"\"");
1751- INFO("Parsed: \""+ printSelector(sheet.selector)+"\"");
1752- REQUIRE(parts.size() == sheet.selector.size());
1753- REQUIRE(type == sheet.type);
1754+ INFO("Parsed: \""+ printSelector(style.selector)+"\"");
1755+ REQUIRE(parts.size() == style.selector.size());
1756+ REQUIRE(type == style.type);
1757
1758 for (size_t a = 0; a < parts.size(); a++) {
1759- REQUIRE(parts[a].size() == sheet.selector[a].size());
1760+ REQUIRE(parts[a].size() == style.selector[a].size());
1761
1762 for (size_t b = 0; b < parts[a].size(); b++) {
1763- REQUIRE(parts[a][b] == sheet.selector[a][b]);
1764+ REQUIRE(parts[a][b] == style.selector[a][b]);
1765 }
1766 }
1767
1768 for (auto p : props) {
1769- std::string f = p.second;
1770- std::string s = sheet.properties[p.first];
1771- trimSpace2(f);
1772- trimSpace2(s);
1773+ std::vector<Unit> f = p.second;
1774+ std::vector<Unit> s = style.properties[p.first];
1775+
1776+ REQUIRE(f.size() == s.size());
1777
1778- REQUIRE(f == s);
1779+ for (size_t i = 0; i < f.size(); i++) {
1780+ REQUIRE(f[i].type == s[i].type);
1781+ }
1782 }
1783 }
1784
1785-void compareInlineStyles(std::string style, std::unordered_map<std::string, std::string> targetProps) {
1786- std::unordered_map<std::string, std::string> props = parseCSSInline(style);
1787+void compareInlineStyles(std::string style, std::unordered_map<KeyType, std::vector<Unit>> targetProps) {
1788+ std::unordered_map<KeyType, std::vector<Unit>> props = parseCSSInline(style);
1789
1790 REQUIRE(props.size() == targetProps.size());
1791
1792 for (auto p : props) {
1793- std::string f = p.second;
1794- std::string s = targetProps[p.first];
1795- trimSpace2(f);
1796- trimSpace2(s);
1797+ std::vector<Unit> f = p.second;
1798+ std::vector<Unit> s = targetProps[p.first];
1799+
1800+ REQUIRE(f.size() == s.size());
1801
1802- REQUIRE(f == s);
1803+ for (size_t i = 0; i < f.size(); i++) {
1804+ REQUIRE(f[i].type == s[i].type);
1805+ }
1806 }
1807 }
1808
1809@@ -151,10 +121,7 @@ html#nested {
1810
1811 std::istringstream inputFile(cssContent);
1812
1813- Window window;
1814- window.CSS.parseStream(inputFile);
1815-
1816- StyleHandler handler = window.CSS;
1817+ Style style = parseCSS(inputFile);
1818
1819 SECTION("parseCSS can parse simple CSS rules") {
1820 compareStyle("h1", {
1821diff --git a/tests/css_unit.cc b/tests/css_unit.cc
1822old mode 100644
1823new mode 100755
1824diff --git a/tests/query_select.cc b/tests/query_select.cc
1825old mode 100644
1826new mode 100755