SharedSizeScopeTests.cs 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279
  1. using System.Collections.Generic;
  2. using System.Linq;
  3. using Avalonia.Controls.Primitives;
  4. using Avalonia.Input;
  5. using Avalonia.Platform;
  6. using Avalonia.UnitTests;
  7. using Moq;
  8. using Xunit;
  9. namespace Avalonia.Controls.UnitTests
  10. {
  11. public class SharedSizeScopeTests
  12. {
  13. [Fact]
  14. public void All_Descendant_Grids_Are_Registered_When_Added_After_Setting_Scope()
  15. {
  16. var grids = new[] { new Grid(), new Grid(), new Grid() };
  17. var scope = new Panel();
  18. scope.Children.AddRange(grids);
  19. var root = new TestRoot();
  20. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  21. root.Child = scope;
  22. Assert.All(grids, g => Assert.True(g.HasSharedSizeScope()));
  23. }
  24. [Fact]
  25. public void All_Descendant_Grids_Are_Registered_When_Setting_Scope()
  26. {
  27. var grids = new[] { new Grid(), new Grid(), new Grid() };
  28. var scope = new Panel();
  29. scope.Children.AddRange(grids);
  30. var root = new TestRoot();
  31. root.Child = scope;
  32. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  33. Assert.All(grids, g => Assert.True(g.HasSharedSizeScope()));
  34. }
  35. [Fact]
  36. public void All_Descendant_Grids_Are_Unregistered_When_Resetting_Scope()
  37. {
  38. var grids = new[] { new Grid(), new Grid(), new Grid() };
  39. var scope = new Panel();
  40. scope.Children.AddRange(grids);
  41. var root = new TestRoot();
  42. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  43. root.Child = scope;
  44. Assert.All(grids, g => Assert.True(g.HasSharedSizeScope()));
  45. root.SetValue(Grid.IsSharedSizeScopeProperty, false);
  46. Assert.All(grids, g => Assert.False(g.HasSharedSizeScope()));
  47. Assert.Equal(null, root.GetValue(Grid.PrivateSharedSizeScopeProperty));
  48. }
  49. [Fact]
  50. public void Size_Is_Propagated_Between_Grids()
  51. {
  52. var grids = new[] { CreateGrid("A", null), CreateGrid(("A", new GridLength(30)), (null, new GridLength())) };
  53. var scope = new Panel();
  54. scope.Children.AddRange(grids);
  55. var root = new TestRoot();
  56. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  57. root.Child = scope;
  58. root.Measure(new Size(50, 50));
  59. root.Arrange(new Rect(new Point(), new Point(50, 50)));
  60. Assert.Equal(30, grids[0].ColumnDefinitions[0].ActualWidth);
  61. }
  62. [Fact]
  63. public void Size_Propagation_Is_Constrained_To_Innermost_Scope()
  64. {
  65. var grids = new[] { CreateGrid("A", null), CreateGrid(("A", new GridLength(30)), (null, new GridLength())) };
  66. var innerScope = new Panel();
  67. innerScope.Children.AddRange(grids);
  68. innerScope.SetValue(Grid.IsSharedSizeScopeProperty, true);
  69. var outerGrid = CreateGrid(("A", new GridLength(0)));
  70. var outerScope = new Panel();
  71. outerScope.Children.AddRange(new[] { outerGrid, innerScope });
  72. var root = new TestRoot();
  73. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  74. root.Child = outerScope;
  75. root.Measure(new Size(50, 50));
  76. root.Arrange(new Rect(new Point(), new Point(50, 50)));
  77. Assert.Equal(0, outerGrid.ColumnDefinitions[0].ActualWidth);
  78. }
  79. [Fact]
  80. public void Size_Is_Propagated_Between_Rows_And_Columns()
  81. {
  82. var grid = new Grid
  83. {
  84. ColumnDefinitions = new ColumnDefinitions("*,30"),
  85. RowDefinitions = new RowDefinitions("*,10")
  86. };
  87. grid.ColumnDefinitions[1].SharedSizeGroup = "A";
  88. grid.RowDefinitions[1].SharedSizeGroup = "A";
  89. var root = new TestRoot();
  90. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  91. root.Child = grid;
  92. root.Measure(new Size(50, 50));
  93. root.Arrange(new Rect(new Point(), new Point(50, 50)));
  94. Assert.Equal(30, grid.RowDefinitions[1].ActualHeight);
  95. }
  96. [Fact]
  97. public void Size_Group_Changes_Are_Tracked()
  98. {
  99. var grids = new[] {
  100. CreateGrid((null, new GridLength(0, GridUnitType.Auto)), (null, new GridLength())),
  101. CreateGrid(("A", new GridLength(30)), (null, new GridLength())) };
  102. var scope = new Panel();
  103. scope.Children.AddRange(grids);
  104. var root = new TestRoot();
  105. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  106. root.Child = scope;
  107. root.Measure(new Size(50, 50));
  108. root.Arrange(new Rect(new Point(), new Point(50, 50)));
  109. Assert.Equal(0, grids[0].ColumnDefinitions[0].ActualWidth);
  110. grids[0].ColumnDefinitions[0].SharedSizeGroup = "A";
  111. root.Measure(new Size(51, 51));
  112. root.Arrange(new Rect(new Point(), new Point(51, 51)));
  113. Assert.Equal(30, grids[0].ColumnDefinitions[0].ActualWidth);
  114. grids[0].ColumnDefinitions[0].SharedSizeGroup = null;
  115. root.Measure(new Size(52, 52));
  116. root.Arrange(new Rect(new Point(), new Point(52, 52)));
  117. Assert.Equal(0, grids[0].ColumnDefinitions[0].ActualWidth);
  118. }
  119. [Fact]
  120. public void Collection_Changes_Are_Tracked()
  121. {
  122. var grid = CreateGrid(
  123. ("A", new GridLength(20)),
  124. ("A", new GridLength(30)),
  125. ("A", new GridLength(40)),
  126. (null, new GridLength()));
  127. var scope = new Panel();
  128. scope.Children.Add(grid);
  129. var root = new TestRoot();
  130. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  131. root.Child = scope;
  132. grid.Measure(new Size(200, 200));
  133. grid.Arrange(new Rect(new Point(), new Point(200, 200)));
  134. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(40, cd.ActualWidth));
  135. grid.ColumnDefinitions.RemoveAt(2);
  136. grid.Measure(new Size(200, 200));
  137. grid.Arrange(new Rect(new Point(), new Point(200, 200)));
  138. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(30, cd.ActualWidth));
  139. grid.ColumnDefinitions.Insert(1, new ColumnDefinition { Width = new GridLength(35), SharedSizeGroup = "A" });
  140. grid.Measure(new Size(200, 200));
  141. grid.Arrange(new Rect(new Point(), new Point(200, 200)));
  142. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(35, cd.ActualWidth));
  143. grid.ColumnDefinitions[1] = new ColumnDefinition { Width = new GridLength(10), SharedSizeGroup = "A" };
  144. grid.Measure(new Size(200, 200));
  145. grid.Arrange(new Rect(new Point(), new Point(200, 200)));
  146. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(30, cd.ActualWidth));
  147. grid.ColumnDefinitions[1] = new ColumnDefinition { Width = new GridLength(50), SharedSizeGroup = "A" };
  148. grid.Measure(new Size(200, 200));
  149. grid.Arrange(new Rect(new Point(), new Point(200, 200)));
  150. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(50, cd.ActualWidth));
  151. }
  152. [Fact]
  153. public void Size_Priorities_Are_Maintained()
  154. {
  155. var sizers = new List<Control>();
  156. var grid = CreateGrid(
  157. ("A", new GridLength(20)),
  158. ("A", new GridLength(20, GridUnitType.Auto)),
  159. ("A", new GridLength(1, GridUnitType.Star)),
  160. ("A", new GridLength(1, GridUnitType.Star)),
  161. (null, new GridLength()));
  162. for (int i = 0; i < 3; i++)
  163. sizers.Add(AddSizer(grid, i, 6 + i * 6));
  164. var scope = new Panel();
  165. scope.Children.Add(grid);
  166. var root = new TestRoot();
  167. root.SetValue(Grid.IsSharedSizeScopeProperty, true);
  168. root.Child = scope;
  169. grid.Measure(new Size(100, 100));
  170. grid.Arrange(new Rect(new Point(), new Point(100, 100)));
  171. // all in group are equal to the first fixed column
  172. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(20, cd.ActualWidth));
  173. grid.ColumnDefinitions[0].SharedSizeGroup = null;
  174. grid.Measure(new Size(100, 100));
  175. grid.Arrange(new Rect(new Point(), new Point(100, 100)));
  176. // all in group are equal to width (MinWidth) of the sizer in the second column
  177. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(6 + 1 * 6, cd.ActualWidth));
  178. grid.ColumnDefinitions[1].SharedSizeGroup = null;
  179. grid.Measure(new Size(double.PositiveInfinity, 100));
  180. grid.Arrange(new Rect(new Point(), new Point(100, 100)));
  181. // with no constraint star columns default to the MinWidth of the sizer in the column
  182. Assert.All(grid.ColumnDefinitions.Where(cd => cd.SharedSizeGroup == "A"), cd => Assert.Equal(6 + 2 * 6, cd.ActualWidth));
  183. }
  184. // grid creators
  185. private Grid CreateGrid(params string[] columnGroups)
  186. {
  187. return CreateGrid(columnGroups.Select(s => (s, ColumnDefinition.WidthProperty.GetDefaultValue(typeof(ColumnDefinition)))).ToArray());
  188. }
  189. private Grid CreateGrid(params (string name, GridLength width)[] columns)
  190. {
  191. return CreateGrid(columns.Select(c =>
  192. (c.name, c.width, ColumnDefinition.MinWidthProperty.GetDefaultValue(typeof(ColumnDefinition)))).ToArray());
  193. }
  194. private Grid CreateGrid(params (string name, GridLength width, double minWidth)[] columns)
  195. {
  196. return CreateGrid(columns.Select(c =>
  197. (c.name, c.width, c.minWidth, ColumnDefinition.MaxWidthProperty.GetDefaultValue(typeof(ColumnDefinition)))).ToArray());
  198. }
  199. private Grid CreateGrid(params (string name, GridLength width, double minWidth, double maxWidth)[] columns)
  200. {
  201. var columnDefinitions = new ColumnDefinitions();
  202. columnDefinitions.AddRange(
  203. columns.Select(c => new ColumnDefinition
  204. {
  205. SharedSizeGroup = c.name,
  206. Width = c.width,
  207. MinWidth = c.minWidth,
  208. MaxWidth = c.maxWidth
  209. })
  210. );
  211. var grid = new Grid
  212. {
  213. ColumnDefinitions = columnDefinitions
  214. };
  215. return grid;
  216. }
  217. private Control AddSizer(Grid grid, int column, double size = 30)
  218. {
  219. var ctrl = new Control { MinWidth = size, MinHeight = size };
  220. ctrl.SetValue(Grid.ColumnProperty, column);
  221. grid.Children.Add(ctrl);
  222. return ctrl;
  223. }
  224. }
  225. }