Skip to content

Commit 14474b3

Browse files
grid-auto-columns and grid-auto-rows
1 parent 33030ec commit 14474b3

File tree

5 files changed

+366
-14
lines changed

5 files changed

+366
-14
lines changed

tests/generated/YGGridTest.cpp

Lines changed: 244 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4869,3 +4869,247 @@ TEST(YogaTest, grid_gap_percentage_indefinite_size) {
48694869

48704870
YGConfigFree(config);
48714871
}
4872+
4873+
TEST(YogaTest, grid_auto_tracks) {
4874+
YGConfigRef config = YGConfigNew();
4875+
4876+
YGNodeRef root = YGNodeNewWithConfig(config);
4877+
YGNodeStyleSetPositionType(root, YGPositionTypeAbsolute);
4878+
YGNodeStyleSetDisplay(root, YGDisplayGrid);
4879+
std::vector<GridTrackSize> root_auto_columns = {
4880+
GridTrackSize::length(100.0f),
4881+
GridTrackSize::length(100.0f)
4882+
};
4883+
((Node*)root)->style().setGridAutoColumns(std::move(root_auto_columns));
4884+
std::vector<GridTrackSize> root_auto_rows = {
4885+
GridTrackSize::length(100.0f)
4886+
};
4887+
((Node*)root)->style().setGridAutoRows(std::move(root_auto_rows));
4888+
4889+
YGNodeRef root_child0 = YGNodeNewWithConfig(config);
4890+
YGNodeStyleSetGridColumnStart(root_child0, 1);
4891+
YGNodeStyleSetGridColumnEnd(root_child0, 2);
4892+
YGNodeInsertChild(root, root_child0, 0);
4893+
4894+
YGNodeRef root_child1 = YGNodeNewWithConfig(config);
4895+
YGNodeStyleSetGridColumnStart(root_child1, 2);
4896+
YGNodeStyleSetGridColumnEnd(root_child1, 3);
4897+
YGNodeInsertChild(root, root_child1, 1);
4898+
4899+
YGNodeRef root_child2 = YGNodeNewWithConfig(config);
4900+
YGNodeInsertChild(root, root_child2, 2);
4901+
4902+
YGNodeRef root_child3 = YGNodeNewWithConfig(config);
4903+
YGNodeInsertChild(root, root_child3, 3);
4904+
YGNodeCalculateLayout(root, YGUndefined, YGUndefined, YGDirectionLTR);
4905+
4906+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root));
4907+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root));
4908+
ASSERT_FLOAT_EQ(200, YGNodeLayoutGetWidth(root));
4909+
ASSERT_FLOAT_EQ(200, YGNodeLayoutGetHeight(root));
4910+
4911+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child0));
4912+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child0));
4913+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child0));
4914+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child0));
4915+
4916+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetLeft(root_child1));
4917+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child1));
4918+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child1));
4919+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child1));
4920+
4921+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child2));
4922+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetTop(root_child2));
4923+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child2));
4924+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child2));
4925+
4926+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetLeft(root_child3));
4927+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetTop(root_child3));
4928+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child3));
4929+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child3));
4930+
4931+
YGNodeCalculateLayout(root, YGUndefined, YGUndefined, YGDirectionRTL);
4932+
4933+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root));
4934+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root));
4935+
ASSERT_FLOAT_EQ(200, YGNodeLayoutGetWidth(root));
4936+
ASSERT_FLOAT_EQ(200, YGNodeLayoutGetHeight(root));
4937+
4938+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetLeft(root_child0));
4939+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child0));
4940+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child0));
4941+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child0));
4942+
4943+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child1));
4944+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child1));
4945+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child1));
4946+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child1));
4947+
4948+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetLeft(root_child2));
4949+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetTop(root_child2));
4950+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child2));
4951+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child2));
4952+
4953+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child3));
4954+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetTop(root_child3));
4955+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child3));
4956+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root_child3));
4957+
4958+
YGNodeFreeRecursive(root);
4959+
4960+
YGConfigFree(config);
4961+
}
4962+
4963+
TEST(YogaTest, grid_auto_tracks_with_implicit_tracks) {
4964+
YGConfigRef config = YGConfigNew();
4965+
4966+
YGNodeRef root = YGNodeNewWithConfig(config);
4967+
YGNodeStyleSetPositionType(root, YGPositionTypeAbsolute);
4968+
YGNodeStyleSetDisplay(root, YGDisplayGrid);
4969+
std::vector<GridTrackSize> root_auto_columns = {
4970+
GridTrackSize::length(100.0f)
4971+
};
4972+
((Node*)root)->style().setGridAutoColumns(std::move(root_auto_columns));
4973+
std::vector<GridTrackSize> root_auto_rows = {
4974+
GridTrackSize::length(50.0f)
4975+
};
4976+
((Node*)root)->style().setGridAutoRows(std::move(root_auto_rows));
4977+
4978+
YGNodeRef root_child0 = YGNodeNewWithConfig(config);
4979+
YGNodeStyleSetWidth(root_child0, 100);
4980+
YGNodeStyleSetHeight(root_child0, 50);
4981+
YGNodeStyleSetGridColumnStart(root_child0, -3);
4982+
YGNodeStyleSetGridColumnEnd(root_child0, -4);
4983+
YGNodeInsertChild(root, root_child0, 0);
4984+
4985+
YGNodeRef root_child1 = YGNodeNewWithConfig(config);
4986+
YGNodeStyleSetWidth(root_child1, 100);
4987+
YGNodeStyleSetHeight(root_child1, 50);
4988+
YGNodeStyleSetGridColumnStart(root_child1, 2);
4989+
YGNodeStyleSetGridColumnEnd(root_child1, 3);
4990+
YGNodeInsertChild(root, root_child1, 1);
4991+
4992+
YGNodeRef root_child2 = YGNodeNewWithConfig(config);
4993+
YGNodeInsertChild(root, root_child2, 2);
4994+
4995+
YGNodeRef root_child3 = YGNodeNewWithConfig(config);
4996+
YGNodeInsertChild(root, root_child3, 3);
4997+
YGNodeCalculateLayout(root, YGUndefined, YGUndefined, YGDirectionLTR);
4998+
4999+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root));
5000+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root));
5001+
ASSERT_FLOAT_EQ(500, YGNodeLayoutGetWidth(root));
5002+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root));
5003+
5004+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child0));
5005+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child0));
5006+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child0));
5007+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child0));
5008+
5009+
ASSERT_FLOAT_EQ(400, YGNodeLayoutGetLeft(root_child1));
5010+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child1));
5011+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child1));
5012+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child1));
5013+
5014+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child2));
5015+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetTop(root_child2));
5016+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child2));
5017+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child2));
5018+
5019+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetLeft(root_child3));
5020+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetTop(root_child3));
5021+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child3));
5022+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child3));
5023+
5024+
YGNodeCalculateLayout(root, YGUndefined, YGUndefined, YGDirectionRTL);
5025+
5026+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root));
5027+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root));
5028+
ASSERT_FLOAT_EQ(500, YGNodeLayoutGetWidth(root));
5029+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetHeight(root));
5030+
5031+
ASSERT_FLOAT_EQ(400, YGNodeLayoutGetLeft(root_child0));
5032+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child0));
5033+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child0));
5034+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child0));
5035+
5036+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child1));
5037+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child1));
5038+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child1));
5039+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child1));
5040+
5041+
ASSERT_FLOAT_EQ(400, YGNodeLayoutGetLeft(root_child2));
5042+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetTop(root_child2));
5043+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child2));
5044+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child2));
5045+
5046+
ASSERT_FLOAT_EQ(300, YGNodeLayoutGetLeft(root_child3));
5047+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetTop(root_child3));
5048+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child3));
5049+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child3));
5050+
5051+
YGNodeFreeRecursive(root);
5052+
5053+
YGConfigFree(config);
5054+
}
5055+
5056+
TEST(YogaTest, grid_with_percentage_tracks_indefinite_size) {
5057+
YGConfigRef config = YGConfigNew();
5058+
5059+
YGNodeRef root = YGNodeNewWithConfig(config);
5060+
YGNodeStyleSetPositionType(root, YGPositionTypeAbsolute);
5061+
YGNodeStyleSetDisplay(root, YGDisplayGrid);
5062+
std::vector<GridTrackSize> root_columns = {
5063+
GridTrackSize::length(100.0f),
5064+
GridTrackSize::percent(20.0f)
5065+
};
5066+
((Node*)root)->style().setGridTemplateColumns(std::move(root_columns));
5067+
std::vector<GridTrackSize> root_rows = {
5068+
GridTrackSize::length(50.0f),
5069+
GridTrackSize::percent(40.0f)
5070+
};
5071+
((Node*)root)->style().setGridTemplateRows(std::move(root_rows));
5072+
5073+
YGNodeRef root_child0 = YGNodeNewWithConfig(config);
5074+
YGNodeInsertChild(root, root_child0, 0);
5075+
5076+
YGNodeRef root_child1 = YGNodeNewWithConfig(config);
5077+
YGNodeInsertChild(root, root_child1, 1);
5078+
YGNodeCalculateLayout(root, YGUndefined, YGUndefined, YGDirectionLTR);
5079+
5080+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root));
5081+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root));
5082+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root));
5083+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root));
5084+
5085+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child0));
5086+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child0));
5087+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child0));
5088+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child0));
5089+
5090+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetLeft(root_child1));
5091+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child1));
5092+
ASSERT_FLOAT_EQ(20, YGNodeLayoutGetWidth(root_child1));
5093+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child1));
5094+
5095+
YGNodeCalculateLayout(root, YGUndefined, YGUndefined, YGDirectionRTL);
5096+
5097+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root));
5098+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root));
5099+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root));
5100+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root));
5101+
5102+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetLeft(root_child0));
5103+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child0));
5104+
ASSERT_FLOAT_EQ(100, YGNodeLayoutGetWidth(root_child0));
5105+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child0));
5106+
5107+
ASSERT_FLOAT_EQ(-20, YGNodeLayoutGetLeft(root_child1));
5108+
ASSERT_FLOAT_EQ(0, YGNodeLayoutGetTop(root_child1));
5109+
ASSERT_FLOAT_EQ(20, YGNodeLayoutGetWidth(root_child1));
5110+
ASSERT_FLOAT_EQ(50, YGNodeLayoutGetHeight(root_child1));
5111+
5112+
YGNodeFreeRecursive(root);
5113+
5114+
YGConfigFree(config);
5115+
}

tests/grid/CreateGridTrackTest.cpp

Lines changed: 89 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -178,3 +178,92 @@ TEST_F(GridCreateTracksTest, large_span_creating_many_implicit_tracks) {
178178
EXPECT_TRUE(track.minSizingFunction.isAuto());
179179
}
180180
}
181+
182+
TEST_F(GridCreateTracksTest, grid_auto_columns_pattern_repeats_backward) {
183+
std::vector<GridTrackSize> columns = {
184+
GridTrackSize::length(100.0f),
185+
GridTrackSize::length(150.0f)
186+
};
187+
gridContainer->style().setGridTemplateColumns(std::move(columns));
188+
189+
std::vector<GridTrackSize> autoColumns = {
190+
GridTrackSize::length(50.0f),
191+
GridTrackSize::fr(1.0f),
192+
GridTrackSize::length(75.0f)
193+
};
194+
gridContainer->style().setGridAutoColumns(std::move(autoColumns));
195+
196+
createGridItem(GridLine::fromInteger(-8), GridLine::fromInteger(-7));
197+
createGridItem(GridLine::fromInteger(3), GridLine::fromInteger(6));
198+
199+
auto autoPlacementResult = resolveGridItemPlacements(gridContainer);
200+
GridTracks tracks = createGridTracks(gridContainer, autoPlacementResult);
201+
202+
// 5 negative implicit + 2 explicit + 3 positive implicit = 10 tracks
203+
EXPECT_EQ(tracks.columnTracks.size(), 10);
204+
205+
// Implicit tracks before explicit grid
206+
EXPECT_TRUE(tracks.columnTracks[4].minSizingFunction.isPoints());
207+
EXPECT_EQ(tracks.columnTracks[4].minSizingFunction.resolve(0.0f).unwrap(), 75.0f);
208+
EXPECT_TRUE(tracks.columnTracks[3].maxSizingFunction.isStretch());
209+
EXPECT_TRUE(tracks.columnTracks[2].minSizingFunction.isPoints());
210+
EXPECT_EQ(tracks.columnTracks[2].minSizingFunction.resolve(0.0f).unwrap(), 50.0f);
211+
EXPECT_TRUE(tracks.columnTracks[1].minSizingFunction.isPoints());
212+
EXPECT_EQ(tracks.columnTracks[1].minSizingFunction.resolve(0.0f).unwrap(), 75.0f);
213+
EXPECT_TRUE(tracks.columnTracks[0].maxSizingFunction.isStretch());
214+
215+
// Explicit grid
216+
EXPECT_TRUE(tracks.columnTracks[5].minSizingFunction.isPoints());
217+
EXPECT_EQ(tracks.columnTracks[5].minSizingFunction.resolve(0.0f).unwrap(), 100.0f);
218+
EXPECT_TRUE(tracks.columnTracks[6].minSizingFunction.isPoints());
219+
EXPECT_EQ(tracks.columnTracks[6].minSizingFunction.resolve(0.0f).unwrap(), 150.0f);
220+
221+
// Implicit tracks after explicit grid
222+
EXPECT_TRUE(tracks.columnTracks[7].minSizingFunction.isPoints());
223+
EXPECT_EQ(tracks.columnTracks[7].minSizingFunction.resolve(0.0f).unwrap(), 50.0f);
224+
EXPECT_TRUE(tracks.columnTracks[8].maxSizingFunction.isStretch());
225+
EXPECT_TRUE(tracks.columnTracks[9].minSizingFunction.isPoints());
226+
EXPECT_EQ(tracks.columnTracks[9].minSizingFunction.resolve(0.0f).unwrap(), 75.0f);
227+
}
228+
229+
TEST_F(GridCreateTracksTest, grid_auto_rows_pattern_repeats_both_directions) {
230+
std::vector<GridTrackSize> rows = {
231+
GridTrackSize::length(200.0f)
232+
};
233+
gridContainer->style().setGridTemplateRows(std::move(rows));
234+
235+
std::vector<GridTrackSize> autoRows = {
236+
GridTrackSize::length(60.0f),
237+
GridTrackSize::length(80.0f)
238+
};
239+
gridContainer->style().setGridAutoRows(std::move(autoRows));
240+
241+
createGridItem(GridLine::auto_(), GridLine::auto_(),
242+
GridLine::fromInteger(-4), GridLine::fromInteger(-2));
243+
244+
createGridItem(GridLine::auto_(), GridLine::auto_(),
245+
GridLine::fromInteger(3), GridLine::fromInteger(5));
246+
247+
auto autoPlacementResult = resolveGridItemPlacements(gridContainer);
248+
GridTracks tracks = createGridTracks(gridContainer, autoPlacementResult);
249+
250+
// 2 implicit before + 1 explicit + 3 implicit after = 7 tracks
251+
EXPECT_EQ(tracks.rowTracks.size(), 6);
252+
253+
// Implicit tracks before explicit grid
254+
EXPECT_TRUE(tracks.rowTracks[1].minSizingFunction.isPoints());
255+
EXPECT_EQ(tracks.rowTracks[1].minSizingFunction.resolve(0.0f).unwrap(), 80.0f);
256+
EXPECT_TRUE(tracks.rowTracks[0].minSizingFunction.isPoints());
257+
EXPECT_EQ(tracks.rowTracks[0].minSizingFunction.resolve(0.0f).unwrap(), 60.0f);
258+
259+
// Explicit grid
260+
EXPECT_EQ(tracks.rowTracks[2].minSizingFunction.resolve(0.0f).unwrap(), 200.0f);
261+
262+
// Implicit tracks after explicit grid
263+
EXPECT_TRUE(tracks.rowTracks[3].minSizingFunction.isPoints());
264+
EXPECT_EQ(tracks.rowTracks[3].minSizingFunction.resolve(0.0f).unwrap(), 60.0f);
265+
EXPECT_TRUE(tracks.rowTracks[4].minSizingFunction.isPoints());
266+
EXPECT_EQ(tracks.rowTracks[4].minSizingFunction.resolve(0.0f).unwrap(), 80.0f);
267+
EXPECT_TRUE(tracks.rowTracks[5].minSizingFunction.isPoints());
268+
EXPECT_EQ(tracks.rowTracks[5].minSizingFunction.resolve(0.0f).unwrap(), 60.0f);
269+
}

0 commit comments

Comments
 (0)