css_ast/traits/declaration_metadata.rs
1use bitmask_enum::bitmask;
2
3use crate::CssAtomSet;
4
5/// The CSS specification/module that a property belongs to.
6#[bitmask(u64)]
7#[bitmask_config(vec_debug)]
8#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
9pub enum PropertyGroup {
10 Align,
11 AnchorPosition,
12 Animations,
13 Backgrounds,
14 Borders,
15 Box,
16 Break,
17 Cascade,
18 Color,
19 ColorAdjust,
20 ColorHdr,
21 Conditional,
22 Contain,
23 Content,
24 Display,
25 Exclusions,
26 Flexbox,
27 Fonts,
28 Forms,
29 Gaps,
30 Gcpm,
31 Grid,
32 Images,
33 Inline,
34 LineGrid,
35 LinkParams,
36 Lists,
37 Logical,
38 Multicol,
39 Nav,
40 Overflow,
41 Overscroll,
42 Page,
43 PageFloats,
44 Position,
45 Regions,
46 Rhythm,
47 RoundDisplay,
48 Ruby,
49 ScrollAnchoring,
50 ScrollSnap,
51 Scrollbars,
52 Shapes,
53 SizeAdjust,
54 Sizing,
55 Speech,
56 Tables,
57 Text,
58 TextDecor,
59 Transforms,
60 Transitions,
61 Ui,
62 Values,
63 Variables,
64 ViewTransitions,
65 Viewport,
66 WillChange,
67 WritingModes,
68}
69
70pub enum Inherits {
71 False,
72 True,
73 Unknown,
74}
75
76impl Inherits {
77 pub fn to_bool(self, unknown: bool) -> bool {
78 match self {
79 Self::False => false,
80 Self::True => true,
81 Self::Unknown => unknown,
82 }
83 }
84}
85
86pub enum Percentages {
87 /// This style value has no way of expressing values as a percentage.
88 None,
89 /// Any percentage expressed in this value pertains to the size of the containing block.
90 ContainingBlock,
91 /// Any percentage expressed in this value pertains to the size of the border box.
92 BorderBox,
93 /// Any percentage expressed in this value is a syntax affordance; a Number token would be the equivalent value.
94 Number,
95 /// Relative to the 1em Font-Size
96 FontSize,
97 /// Relative to the Font-Size of the parent element
98 ParentFontSize,
99 /// Relative to the scroll container's scrollport
100 Scrollport,
101 /// Relative to the content area dimension
102 ContentArea,
103 /// Relative to the border-edge side length
104 BorderEdge,
105 /// Relative to the background positioning area
106 BackgroundPositioningArea,
107 /// Relative to the reference box size
108 ReferenceBox,
109 /// Relative to the element's own dimensions
110 SelfSize,
111 /// Relative to the line box
112 LineBox,
113 /// Relative to the flex container
114 FlexContainer,
115 /// Relative to the border image area
116 BorderImageArea,
117 /// Map to a normalized range (e.g., `[0,1]`)
118 NormalizedRange,
119 /// Unknown or complex percentage resolution
120 Unknown,
121}
122
123/// The type of element or container this style value applies to.
124#[bitmask(u16)]
125#[bitmask_config(vec_debug)]
126#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
127pub enum AppliesTo {
128 /// Any element which is `display: block` or equivalent.
129 Block,
130 /// Any element which is `display: grid` or equivalent.
131 Grid,
132 /// Any element which is `display: flex` or equivalent.
133 Flex,
134 /// Any inline-level box.
135 Inline,
136 /// Any floated element.
137 Float,
138 /// Any Ruby container
139 Ruby,
140 /// Any absolutely positioned element.
141 AbsPos,
142 /// Any text node.
143 Text,
144 /// Any Pseudo Elements
145 PseudoElements,
146 /// Any Element
147 Elements,
148 /// What this applies to still needs to be established.
149 Unknown,
150}
151
152pub enum AnimationType {
153 /// This property is not animatable.
154 None,
155 /// This property animates between discrete values.
156 Discrete,
157 /// Animates by interpolating computed values
158 ByComputedValue,
159 /// Each item in a list animates independently
160 RepeatableList,
161 /// Animates as a transform list
162 TransformList,
163 /// Animates as a shadow list
164 ShadowList,
165 /// Animates as a length value
166 Length,
167 /// Animates as a number value
168 Number,
169 /// Unknown or complex animation behavior
170 Unknown,
171}
172
173/// How the computed value is calculated from the specified value
174pub enum ComputedValueType {
175 /// The computed value is the same as the specified value
176 AsSpecified,
177 /// Computed to an absolute length
178 AbsoluteLength,
179 /// Computed to an absolute length or percentage
180 AbsoluteLengthOrPercentage,
181 /// Computed to an absolute length or 'none'
182 AbsoluteLengthOrNone,
183 /// A specified keyword plus an absolute length
184 SpecifiedKeywordPlusAbsoluteLength,
185 /// Two absolute lengths (e.g., for background-position)
186 TwoAbsoluteLengths,
187 /// A list of absolute lengths
188 ListOfAbsoluteLengths,
189 /// Computed as specified, but with relative lengths converted to absolute
190 SpecifiedWithAbsoluteLengths,
191 /// Computed as specified, but with relative URLs converted to absolute
192 SpecifiedWithAbsoluteUrls,
193 /// Special computation rules - see spec
194 SeeIndividualProperties,
195 /// Computed value calculation is complex or spec-specific
196 Complex,
197 /// Not yet categorized
198 Unknown,
199}
200
201/// Which side(s) of the box a property applies to.
202/// This is a bitmask so properties can apply to multiple sides.
203#[bitmask(u8)]
204#[bitmask_config(vec_debug)]
205#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
206pub enum BoxSide {
207 /// Applies to the physical top side
208 Top,
209 /// Applies to the physical bottom side
210 Bottom,
211 /// Applies to the physical left side
212 Left,
213 /// Applies to the physical right side
214 Right,
215 /// Applies to the logical block-start side
216 BlockStart,
217 /// Applies to the logical block-end side
218 BlockEnd,
219 /// Applies to the logical inline-start side
220 InlineStart,
221 /// Applies to the logical inline-end side
222 InlineEnd,
223}
224
225/// Which portion(s) of the box model a property affects.
226/// This is a bitmask so properties can affect multiple portions.
227#[bitmask(u8)]
228#[bitmask_config(vec_debug)]
229#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
230pub enum BoxPortion {
231 /// Affects the content size (width/height)
232 Size,
233 /// Affects the margin area
234 Margin,
235 /// Affects the padding area
236 Padding,
237 /// Affects the border area
238 Border,
239 /// Affects the position/placement of the box
240 Position,
241}
242
243pub trait DeclarationMetadata: PartialEq + Sized + Clone {
244 /// Returns the initial value of this property, as a string
245 fn initial() -> &'static str;
246
247 /// Determines if this style value inherits from parent rules
248 fn inherits() -> Inherits {
249 // Most properties do not inherit, so this is a sensible default
250 Inherits::False
251 }
252
253 /// Determines what types of frames this rule applies to
254 fn applies_to() -> AppliesTo {
255 AppliesTo::none()
256 }
257
258 /// Determines how this style value resolves percentages, if they are allowed as values
259 fn percentages() -> Percentages {
260 Percentages::None
261 }
262
263 /// Returns how this style value animates
264 fn animation_type() -> AnimationType {
265 // Most properties do not animate, so this is a sensible default
266 AnimationType::None
267 }
268
269 /// Determines if this style value is a "shorthand" value, meaning it is comprised of other "longhand" style values.
270 fn is_shorthand() -> bool {
271 false
272 }
273
274 /// Determines if this style value is a "longhand" value, meaning a "shorthand" style value exists that could also
275 /// express this.
276 fn is_longhand() -> bool {
277 Self::shorthand_group() == CssAtomSet::_None
278 }
279
280 /// Returns the declaration ID of the shorthand that this property is part of.
281 /// If this is not a longhand then it will be `CssAtomSet::_None`.
282 fn shorthand_group() -> CssAtomSet {
283 CssAtomSet::_None
284 }
285
286 /// Returns which CSS specification(s) this property belongs to.
287 /// This allows tracking which CSS modules are used in a stylesheet.
288 fn property_group() -> PropertyGroup {
289 PropertyGroup::none()
290 }
291
292 /// Returns how the computed value is calculated from the specified value.
293 fn computed_value_type() -> ComputedValueType {
294 ComputedValueType::Unknown
295 }
296
297 /// Returns the canonical order for serialization (e.g., "per grammar", "unique").
298 /// Returns None if not specified or not applicable.
299 fn canonical_order() -> Option<&'static str> {
300 None
301 }
302
303 /// Returns the logical property group this property belongs to (e.g., "Margin", "Border").
304 /// This groups related logical/physical properties together.
305 /// Returns None if this is not part of a logical property group.
306 fn logical_property_group() -> Option<CssAtomSet> {
307 None
308 }
309
310 /// Returns which side(s) of the box this property applies to.
311 /// For example, `margin-top` returns BoxSide::Top, while `margin` returns all sides.
312 /// Returns BoxSide::none() if the property doesn't apply to a specific side.
313 fn box_side() -> BoxSide {
314 BoxSide::none()
315 }
316
317 /// Returns which portion(s) of the box model this property affects.
318 /// For example, `margin-top` returns BoxPortion::Margin, `border-width` returns BoxPortion::Border.
319 /// Returns BoxPortion::none() if the property doesn't affect the box model.
320 fn box_portion() -> BoxPortion {
321 BoxPortion::none()
322 }
323}