diff --git a/Tests/LibWeb/Layout/expected/grid/template-areas-1.txt b/Tests/LibWeb/Layout/expected/grid/template-areas-1.txt new file mode 100644 index 0000000000..fa1e19f2f2 --- /dev/null +++ b/Tests/LibWeb/Layout/expected/grid/template-areas-1.txt @@ -0,0 +1,23 @@ +Viewport <#document> at (0,0) content-size 800x600 children: not-inline + BlockContainer at (1,1) content-size 798x320 [BFC] children: not-inline + BlockContainer at (10,10) content-size 780x302 children: not-inline + Box at (11,11) content-size 778x300 [GFC] children: not-inline + BlockContainer at (12,12) content-size 298x198 [BFC] children: inline + line 0 width: 9.34375, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [12,12 9.34375x17.46875] + "a" + TextNode <#text> + BlockContainer at (12,212) content-size 298x98 [BFC] children: inline + line 0 width: 9.46875, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [12,212 9.46875x17.46875] + "b" + TextNode <#text> + +ViewportPaintable (Viewport<#document>) [0,0 800x600] + PaintableWithLines (BlockContainer) [0,0 800x322] + PaintableWithLines (BlockContainer) [9,9 782x304] + PaintableBox (Box
.grid) [10,10 780x302] + PaintableWithLines (BlockContainer
.a) [11,11 300x200] + TextPaintable (TextNode<#text>) + PaintableWithLines (BlockContainer
.b) [11,211 300x100] + TextPaintable (TextNode<#text>) diff --git a/Tests/LibWeb/Layout/expected/grid/template-areas-2.txt b/Tests/LibWeb/Layout/expected/grid/template-areas-2.txt new file mode 100644 index 0000000000..0762a2cb2c --- /dev/null +++ b/Tests/LibWeb/Layout/expected/grid/template-areas-2.txt @@ -0,0 +1,23 @@ +Viewport <#document> at (0,0) content-size 800x600 children: not-inline + BlockContainer at (1,1) content-size 798x320 [BFC] children: not-inline + BlockContainer at (10,10) content-size 780x302 children: not-inline + Box at (11,11) content-size 778x300 [GFC] children: not-inline + BlockContainer at (12,12) content-size 198x298 [BFC] children: inline + line 0 width: 9.34375, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [12,12 9.34375x17.46875] + "a" + TextNode <#text> + BlockContainer at (212,12) content-size 98x298 [BFC] children: inline + line 0 width: 9.46875, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [212,12 9.46875x17.46875] + "b" + TextNode <#text> + +ViewportPaintable (Viewport<#document>) [0,0 800x600] + PaintableWithLines (BlockContainer) [0,0 800x322] + PaintableWithLines (BlockContainer) [9,9 782x304] + PaintableBox (Box
.grid) [10,10 780x302] + PaintableWithLines (BlockContainer
.a) [11,11 200x300] + TextPaintable (TextNode<#text>) + PaintableWithLines (BlockContainer
.b) [211,11 100x300] + TextPaintable (TextNode<#text>) diff --git a/Tests/LibWeb/Layout/expected/grid/template-areas-3.txt b/Tests/LibWeb/Layout/expected/grid/template-areas-3.txt new file mode 100644 index 0000000000..23cd14b7f0 --- /dev/null +++ b/Tests/LibWeb/Layout/expected/grid/template-areas-3.txt @@ -0,0 +1,44 @@ +Viewport <#document> at (0,0) content-size 800x600 children: not-inline + BlockContainer at (1,1) content-size 798x692 [BFC] children: not-inline + BlockContainer at (10,10) content-size 780x674 children: not-inline + Box at (11,11) content-size 778x672 [GFC] children: not-inline + BlockContainer at (12,12) content-size 775.984375x334 [BFC] children: inline + line 0 width: 9.34375, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [12,12 9.34375x17.46875] + "a" + TextNode <#text> + BlockContainer at (12,348) content-size 257.328125x334 [BFC] children: inline + line 0 width: 9.46875, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [12,348 9.46875x17.46875] + "b" + TextNode <#text> + BlockContainer at (271.328125,348) content-size 257.328125x334 [BFC] children: inline + line 0 width: 8.890625, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [271.328125,348 8.890625x17.46875] + "c" + TextNode <#text> + BlockContainer at (530.65625,348) content-size 257.328125x166 [BFC] children: inline + line 0 width: 7.859375, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [530.65625,348 7.859375x17.46875] + "d" + TextNode <#text> + BlockContainer at (530.65625,516) content-size 257.328125x166 [BFC] children: inline + line 0 width: 8.71875, height: 17.46875, bottom: 17.46875, baseline: 13.53125 + frag 0 from TextNode start: 0, length: 1, rect: [530.65625,516 8.71875x17.46875] + "e" + TextNode <#text> + +ViewportPaintable (Viewport<#document>) [0,0 800x600] overflow: [0,0 800x694] + PaintableWithLines (BlockContainer) [0,0 800x694] + PaintableWithLines (BlockContainer) [9,9 782x676] + PaintableBox (Box
.grid) [10,10 780x674] + PaintableWithLines (BlockContainer
.a) [11,11 777.984375x336] + TextPaintable (TextNode<#text>) + PaintableWithLines (BlockContainer
.b) [11,347 259.328125x336] + TextPaintable (TextNode<#text>) + PaintableWithLines (BlockContainer
.c) [270.328125,347 259.328125x336] + TextPaintable (TextNode<#text>) + PaintableWithLines (BlockContainer
.d) [529.65625,347 259.328125x168] + TextPaintable (TextNode<#text>) + PaintableWithLines (BlockContainer
.e) [529.65625,515 259.328125x168] + TextPaintable (TextNode<#text>) diff --git a/Tests/LibWeb/Layout/input/grid/template-areas-1.html b/Tests/LibWeb/Layout/input/grid/template-areas-1.html new file mode 100644 index 0000000000..5c99a7336c --- /dev/null +++ b/Tests/LibWeb/Layout/input/grid/template-areas-1.html @@ -0,0 +1,22 @@ +
a
b
\ No newline at end of file diff --git a/Tests/LibWeb/Layout/input/grid/template-areas-2.html b/Tests/LibWeb/Layout/input/grid/template-areas-2.html new file mode 100644 index 0000000000..dcc0aafbb8 --- /dev/null +++ b/Tests/LibWeb/Layout/input/grid/template-areas-2.html @@ -0,0 +1,22 @@ +
a
b
\ No newline at end of file diff --git a/Tests/LibWeb/Layout/input/grid/template-areas-3.html b/Tests/LibWeb/Layout/input/grid/template-areas-3.html new file mode 100644 index 0000000000..8d1e81e6e3 --- /dev/null +++ b/Tests/LibWeb/Layout/input/grid/template-areas-3.html @@ -0,0 +1,33 @@ +
a
b
c
d
e
\ No newline at end of file diff --git a/Userland/Libraries/LibWeb/Layout/GridFormattingContext.cpp b/Userland/Libraries/LibWeb/Layout/GridFormattingContext.cpp index 9da529b99c..bd8d940c49 100644 --- a/Userland/Libraries/LibWeb/Layout/GridFormattingContext.cpp +++ b/Userland/Libraries/LibWeb/Layout/GridFormattingContext.cpp @@ -1323,33 +1323,35 @@ void GridFormattingContext::build_grid_areas() // https://www.w3.org/TR/css-grid-2/#grid-template-areas-property // If a named grid area spans multiple grid cells, but those cells do not form a single // filled-in rectangle, the declaration is invalid. - for (size_t y = 0; y < grid_container().computed_values().grid_template_areas().size(); y++) { - for (size_t x = 0; x < grid_container().computed_values().grid_template_areas()[y].size(); x++) { - auto grid_area_name = grid_container().computed_values().grid_template_areas()[y][x]; - auto maybe_grid_area = m_grid_areas.get(grid_area_name); - if (!maybe_grid_area.has_value()) { - m_grid_areas.set(grid_area_name, { grid_area_name, y, y + 1, x, x + 1 }); - } else { - auto& grid_area = maybe_grid_area.value(); - if (grid_area.row_start == y) { - if (grid_area.column_end == x) - grid_area.column_end = grid_area.column_end + 1; - else - return; - } else { - if (grid_area.row_end == y) { - if (grid_area.column_start != x) - return; - grid_area.row_end = grid_area.row_end + 1; - } else if (grid_area.row_end == y + 1) { - if (grid_area.column_end < x || grid_area.column_end > x + 1) - return; - } else { - return; - } + auto const& rows = grid_container().computed_values().grid_template_areas(); + + auto find_area_rectangle = [&](size_t x_start, size_t y_start, String const& name) { + bool invalid = false; + size_t x_end = x_start; + size_t y_end = y_start; + while (x_end < rows[y_start].size() && rows[y_start][x_end] == name) + x_end++; + while (y_end < rows.size() && rows[y_end][x_start] == name) + y_end++; + for (size_t y = y_start; y < y_end; y++) { + for (size_t x = x_start; x < x_end; x++) { + if (rows[y][x] != name) { + // If a named grid area spans multiple grid cells, but those cells do not form a single filled-in rectangle, the declaration is invalid. + invalid = true; + break; } } } + m_grid_areas.set(name, { name, y_start, y_end, x_start, x_end, invalid }); + }; + + for (size_t y = 0; y < rows.size(); y++) { + for (size_t x = 0; x < rows[y].size(); x++) { + auto name = rows[y][x]; + if (auto grid_area = m_grid_areas.get(name); grid_area.has_value()) + continue; + find_area_rectangle(x, y, name); + } } } diff --git a/Userland/Libraries/LibWeb/Layout/GridFormattingContext.h b/Userland/Libraries/LibWeb/Layout/GridFormattingContext.h index bf57e4ca03..3b67325e3d 100644 --- a/Userland/Libraries/LibWeb/Layout/GridFormattingContext.h +++ b/Userland/Libraries/LibWeb/Layout/GridFormattingContext.h @@ -142,6 +142,7 @@ private: size_t row_end { 1 }; size_t column_start { 0 }; size_t column_end { 1 }; + bool invalid { false }; /* FIXME: Ignore ignore invalid areas during layout */ }; HashMap m_grid_areas;