1
0

ViewboxTests.cs 8.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247
  1. using Avalonia.Controls.Shapes;
  2. using Avalonia.Data;
  3. using Avalonia.LogicalTree;
  4. using Avalonia.Media;
  5. using Avalonia.UnitTests;
  6. using Xunit;
  7. namespace Avalonia.Controls.UnitTests
  8. {
  9. public class ViewboxTests : ScopedTestBase
  10. {
  11. [Fact]
  12. public void Viewbox_Stretch_Uniform_Child()
  13. {
  14. using var app = UnitTestApplication.Start(TestServices.MockPlatformRenderInterface);
  15. var target = new Viewbox() { Child = new Rectangle() { Width = 100, Height = 50 } };
  16. target.Measure(new Size(200, 200));
  17. target.Arrange(new Rect(new Point(0, 0), target.DesiredSize));
  18. Assert.Equal(new Size(200, 100), target.DesiredSize);
  19. Assert.True(TryGetScale(target, out Vector scale));
  20. Assert.Equal(2.0, scale.X);
  21. Assert.Equal(2.0, scale.Y);
  22. }
  23. [Fact]
  24. public void Viewbox_Stretch_None_Child()
  25. {
  26. using var app = UnitTestApplication.Start(TestServices.MockPlatformRenderInterface);
  27. var target = new Viewbox() { Stretch = Stretch.None, Child = new Rectangle() { Width = 100, Height = 50 } };
  28. target.Measure(new Size(200, 200));
  29. target.Arrange(new Rect(new Point(0, 0), target.DesiredSize));
  30. Assert.Equal(new Size(100, 50), target.DesiredSize);
  31. Assert.True(TryGetScale(target, out Vector scale));
  32. Assert.Equal(1.0, scale.X);
  33. Assert.Equal(1.0, scale.Y);
  34. }
  35. [Fact]
  36. public void Viewbox_Stretch_Fill_Child()
  37. {
  38. using var app = UnitTestApplication.Start(TestServices.MockPlatformRenderInterface);
  39. var target = new Viewbox() { Stretch = Stretch.Fill, Child = new Rectangle() { Width = 100, Height = 50 } };
  40. target.Measure(new Size(200, 200));
  41. target.Arrange(new Rect(new Point(0, 0), target.DesiredSize));
  42. Assert.Equal(new Size(200, 200), target.DesiredSize);
  43. Assert.True(TryGetScale(target, out Vector scale));
  44. Assert.Equal(2.0, scale.X);
  45. Assert.Equal(4.0, scale.Y);
  46. }
  47. [Fact]
  48. public void Viewbox_Stretch_UniformToFill_Child()
  49. {
  50. using var app = UnitTestApplication.Start(TestServices.MockPlatformRenderInterface);
  51. var target = new Viewbox() { Stretch = Stretch.UniformToFill, Child = new Rectangle() { Width = 100, Height = 50 } };
  52. target.Measure(new Size(200, 200));
  53. target.Arrange(new Rect(new Point(0, 0), target.DesiredSize));
  54. Assert.Equal(new Size(200, 200), target.DesiredSize);
  55. Assert.True(TryGetScale(target, out Vector scale));
  56. Assert.Equal(4.0, scale.X);
  57. Assert.Equal(4.0, scale.Y);
  58. }
  59. [Fact]
  60. public void Viewbox_Stretch_Uniform_Child_With_Unrestricted_Width()
  61. {
  62. using var app = UnitTestApplication.Start(TestServices.MockPlatformRenderInterface);
  63. var target = new Viewbox() { Child = new Rectangle() { Width = 100, Height = 50 } };
  64. target.Measure(new Size(double.PositiveInfinity, 200));
  65. target.Arrange(new Rect(new Point(0, 0), target.DesiredSize));
  66. Assert.Equal(new Size(400, 200), target.DesiredSize);
  67. Assert.True(TryGetScale(target, out Vector scale));
  68. Assert.Equal(4.0, scale.X);
  69. Assert.Equal(4.0, scale.Y);
  70. }
  71. [Fact]
  72. public void Viewbox_Stretch_Uniform_Child_With_Unrestricted_Height()
  73. {
  74. using var app = UnitTestApplication.Start(TestServices.MockPlatformRenderInterface);
  75. var target = new Viewbox() { Child = new Rectangle() { Width = 100, Height = 50 } };
  76. target.Measure(new Size(200, double.PositiveInfinity));
  77. target.Arrange(new Rect(new Point(0, 0), target.DesiredSize));
  78. Assert.Equal(new Size(200, 100), target.DesiredSize);
  79. Assert.True(TryGetScale(target, out Vector scale));
  80. Assert.Equal(2.0, scale.X);
  81. Assert.Equal(2.0, scale.Y);
  82. }
  83. [Theory]
  84. [InlineData(50, 100, 50, 100, 50, 100, 1)]
  85. [InlineData(50, 100, 150, 150, 50, 100, 1)]
  86. [InlineData(50, 100, 25, 50, 25, 50, 0.5)]
  87. public void Viewbox_Should_Return_Correct_SizeAndScale_StretchDirection_DownOnly(
  88. double childWidth, double childHeight,
  89. double viewboxWidth, double viewboxHeight,
  90. double expectedWidth, double expectedHeight,
  91. double expectedScale)
  92. {
  93. var target = new Viewbox
  94. {
  95. Child = new Control { Width = childWidth, Height = childHeight },
  96. StretchDirection = StretchDirection.DownOnly
  97. };
  98. target.Measure(new Size(viewboxWidth, viewboxHeight));
  99. target.Arrange(new Rect(default, target.DesiredSize));
  100. Assert.Equal(new Size(expectedWidth, expectedHeight), target.DesiredSize);
  101. Assert.True(TryGetScale(target, out Vector scale));
  102. Assert.Equal(expectedScale, scale.X);
  103. Assert.Equal(expectedScale, scale.Y);
  104. }
  105. [Theory]
  106. [InlineData(50, 100, 50, 100, 50, 100, 1)]
  107. [InlineData(50, 100, 25, 50, 25, 50, 1)]
  108. [InlineData(50, 100, 150, 150, 75, 150, 1.5)]
  109. public void Viewbox_Should_Return_Correct_SizeAndScale_StretchDirection_UpOnly(
  110. double childWidth, double childHeight,
  111. double viewboxWidth, double viewboxHeight,
  112. double expectedWidth, double expectedHeight,
  113. double expectedScale)
  114. {
  115. var target = new Viewbox
  116. {
  117. Child = new Control { Width = childWidth, Height = childHeight },
  118. StretchDirection = StretchDirection.UpOnly
  119. };
  120. target.Measure(new Size(viewboxWidth, viewboxHeight));
  121. target.Arrange(new Rect(default, target.DesiredSize));
  122. Assert.Equal(new Size(expectedWidth, expectedHeight), target.DesiredSize);
  123. Assert.True(TryGetScale(target, out Vector scale));
  124. Assert.Equal(expectedScale, scale.X);
  125. Assert.Equal(expectedScale, scale.Y);
  126. }
  127. [Fact]
  128. public void Child_Should_Be_Logical_Child_Of_Viewbox()
  129. {
  130. var target = new Viewbox();
  131. Assert.Empty(target.GetLogicalChildren());
  132. var child = new Canvas();
  133. target.Child = child;
  134. Assert.Single(target.GetLogicalChildren(), child);
  135. Assert.Same(child.GetLogicalParent(), target);
  136. target.Child = null;
  137. Assert.Empty(target.GetLogicalChildren());
  138. Assert.Null(child.GetLogicalParent());
  139. }
  140. [Fact]
  141. public void Changing_Child_Should_Invalidate_Layout()
  142. {
  143. var target = new Viewbox();
  144. target.Child = new Canvas
  145. {
  146. Width = 100,
  147. Height = 100,
  148. };
  149. target.Measure(Size.Infinity);
  150. target.Arrange(new Rect(target.DesiredSize));
  151. Assert.Equal(new Size(100, 100), target.DesiredSize);
  152. target.Child = new Canvas
  153. {
  154. Width = 200,
  155. Height = 200,
  156. };
  157. target.Measure(Size.Infinity);
  158. target.Arrange(new Rect(target.DesiredSize));
  159. Assert.Equal(new Size(200, 200), target.DesiredSize);
  160. }
  161. [Fact]
  162. public void Child_DataContext_Binding_Works()
  163. {
  164. var data = new
  165. {
  166. Foo = "foo",
  167. };
  168. var target = new Viewbox()
  169. {
  170. DataContext = data,
  171. Child = new Canvas
  172. {
  173. [!Canvas.DataContextProperty] = new Binding("Foo"),
  174. },
  175. };
  176. Assert.Equal("foo", target.Child.DataContext);
  177. }
  178. private static bool TryGetScale(Viewbox viewbox, out Vector scale)
  179. {
  180. if (viewbox.InternalTransform is null)
  181. {
  182. scale = default;
  183. return false;
  184. }
  185. var matrix = viewbox.InternalTransform.Value;
  186. Matrix.TryDecomposeTransform(matrix, out var decomposed);
  187. scale = decomposed.Scale;
  188. return true;
  189. }
  190. }
  191. }