Fix css rendering bug where nested styles would get eaten
This commit is contained in:
parent
97958b01a7
commit
d3620be4d8
22
src/css.rs
22
src/css.rs
@ -49,6 +49,8 @@ impl Toplevel {
|
|||||||
pub struct Css {
|
pub struct Css {
|
||||||
blocks: Vec<Toplevel>,
|
blocks: Vec<Toplevel>,
|
||||||
idx: usize,
|
idx: usize,
|
||||||
|
inner_rulesets: usize,
|
||||||
|
at_root: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Css {
|
impl Css {
|
||||||
@ -56,6 +58,8 @@ impl Css {
|
|||||||
Css {
|
Css {
|
||||||
blocks: Vec::new(),
|
blocks: Vec::new(),
|
||||||
idx: 0,
|
idx: 0,
|
||||||
|
inner_rulesets: 0,
|
||||||
|
at_root: true,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -65,12 +69,20 @@ impl Css {
|
|||||||
|
|
||||||
fn parse_stmt(&mut self, stmt: Stmt) {
|
fn parse_stmt(&mut self, stmt: Stmt) {
|
||||||
match stmt {
|
match stmt {
|
||||||
Stmt::Style(s) => self.blocks[self.idx - 1].push_style(s),
|
Stmt::Style(s) => {
|
||||||
|
assert!(self.idx >= 1);
|
||||||
|
if self.at_root {
|
||||||
|
self.blocks[self.idx - 1].push_style(s)
|
||||||
|
} else {
|
||||||
|
self.blocks[self.idx + self.inner_rulesets - 1].push_style(s)
|
||||||
|
}
|
||||||
|
},
|
||||||
Stmt::MultilineComment(s) => {
|
Stmt::MultilineComment(s) => {
|
||||||
|
assert!(self.idx >= 1);
|
||||||
if self.idx == 0 {
|
if self.idx == 0 {
|
||||||
self.blocks.push(Toplevel::MultilineComment(s));
|
self.blocks.push(Toplevel::MultilineComment(s));
|
||||||
} else {
|
} else {
|
||||||
self.blocks[self.idx - 1].push_comment(s)
|
self.blocks[self.idx + self.inner_rulesets - 1].push_comment(s)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Stmt::RuleSet(RuleSet {
|
Stmt::RuleSet(RuleSet {
|
||||||
@ -80,19 +92,25 @@ impl Css {
|
|||||||
}) => {
|
}) => {
|
||||||
if self.idx == 0 {
|
if self.idx == 0 {
|
||||||
self.idx = self.blocks.len() + 1;
|
self.idx = self.blocks.len() + 1;
|
||||||
|
self.inner_rulesets = 0;
|
||||||
self.blocks
|
self.blocks
|
||||||
.push(Toplevel::new_rule(super_selector.zip(selector)));
|
.push(Toplevel::new_rule(super_selector.zip(selector)));
|
||||||
for rule in rules {
|
for rule in rules {
|
||||||
|
self.at_root = true;
|
||||||
self.parse_stmt(rule);
|
self.parse_stmt(rule);
|
||||||
|
self.at_root = true;
|
||||||
}
|
}
|
||||||
self.idx = 0;
|
self.idx = 0;
|
||||||
} else {
|
} else {
|
||||||
self.idx += 1;
|
self.idx += 1;
|
||||||
|
self.at_root = false;
|
||||||
self.blocks
|
self.blocks
|
||||||
.push(Toplevel::new_rule(super_selector.zip(selector)));
|
.push(Toplevel::new_rule(super_selector.zip(selector)));
|
||||||
for rule in rules {
|
for rule in rules {
|
||||||
self.parse_stmt(rule);
|
self.parse_stmt(rule);
|
||||||
}
|
}
|
||||||
|
self.idx -= 1;
|
||||||
|
self.inner_rulesets += 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -464,7 +464,6 @@ mod test_css {
|
|||||||
"a, b {\n a, b {\n color: red\n}\n}\n",
|
"a, b {\n a, b {\n color: red\n}\n}\n",
|
||||||
"a a, a b, b a, b b {\n color: red;\n}\n"
|
"a a, a b, b a, b b {\n color: red;\n}\n"
|
||||||
);
|
);
|
||||||
|
|
||||||
test!(selector_element, "a {\n color: red;\n}\n");
|
test!(selector_element, "a {\n color: red;\n}\n");
|
||||||
test!(selector_id, "#id {\n color: red;\n}\n");
|
test!(selector_id, "#id {\n color: red;\n}\n");
|
||||||
test!(selector_class, ".class {\n color: red;\n}\n");
|
test!(selector_class, ".class {\n color: red;\n}\n");
|
||||||
@ -558,6 +557,11 @@ mod test_css {
|
|||||||
"a b {\n color: red;\n}\n"
|
"a b {\n color: red;\n}\n"
|
||||||
);
|
);
|
||||||
test!(removes_empty_styles, "a {}\n", "");
|
test!(removes_empty_styles, "a {}\n", "");
|
||||||
|
test!(
|
||||||
|
doesnt_eat_style_after_ruleset,
|
||||||
|
"a {\n b {\n color: red;\n}\n color: blue;\n}\n",
|
||||||
|
"a {\n color: blue;\n}\na b {\n color: red;\n}\n"
|
||||||
|
);
|
||||||
|
|
||||||
test!(
|
test!(
|
||||||
removes_inner_comments,
|
removes_inner_comments,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user