ContentControlTests.cs 8.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255
  1. // Copyright (c) The Perspex Project. All rights reserved.
  2. // Licensed under the MIT license. See licence.md file in the project root for full license information.
  3. using System.Collections.Specialized;
  4. using System.Linq;
  5. using Moq;
  6. using Perspex.Controls.Presenters;
  7. using Perspex.Controls.Templates;
  8. using Perspex.LogicalTree;
  9. using Perspex.Styling;
  10. using Perspex.VisualTree;
  11. using Xunit;
  12. namespace Perspex.Controls.UnitTests
  13. {
  14. public class ContentControlTests
  15. {
  16. [Fact]
  17. public void Template_Should_Be_Instantiated()
  18. {
  19. var target = new ContentControl();
  20. target.Content = "Foo";
  21. target.Template = GetTemplate();
  22. target.ApplyTemplate();
  23. ((ContentPresenter)target.Presenter).UpdateChild();
  24. var child = ((IVisual)target).VisualChildren.Single();
  25. Assert.IsType<Border>(child);
  26. child = child.VisualChildren.Single();
  27. Assert.IsType<ContentPresenter>(child);
  28. child = child.VisualChildren.Single();
  29. Assert.IsType<TextBlock>(child);
  30. }
  31. [Fact]
  32. public void Templated_Children_Should_Be_Styled()
  33. {
  34. var root = new TestRoot();
  35. var target = new ContentControl();
  36. var styler = new Mock<IStyler>();
  37. PerspexLocator.CurrentMutable.Bind<IStyler>().ToConstant(styler.Object);
  38. target.Content = "Foo";
  39. target.Template = GetTemplate();
  40. root.Child = target;
  41. target.ApplyTemplate();
  42. styler.Verify(x => x.ApplyStyles(It.IsAny<ContentControl>()), Times.Once());
  43. styler.Verify(x => x.ApplyStyles(It.IsAny<Border>()), Times.Once());
  44. styler.Verify(x => x.ApplyStyles(It.IsAny<ContentPresenter>()), Times.Once());
  45. styler.Verify(x => x.ApplyStyles(It.IsAny<TextBlock>()), Times.Once());
  46. }
  47. [Fact]
  48. public void ContentPresenter_Should_Have_TemplatedParent_Set()
  49. {
  50. var target = new ContentControl();
  51. var child = new Border();
  52. target.Template = GetTemplate();
  53. target.Content = child;
  54. target.ApplyTemplate();
  55. ((ContentPresenter)target.Presenter).UpdateChild();
  56. var contentPresenter = child.GetVisualParent<ContentPresenter>();
  57. Assert.Equal(target, contentPresenter.TemplatedParent);
  58. }
  59. [Fact]
  60. public void Content_Should_Have_TemplatedParent_Set_To_Null()
  61. {
  62. var target = new ContentControl();
  63. var child = new Border();
  64. target.Template = GetTemplate();
  65. target.Content = child;
  66. target.ApplyTemplate();
  67. ((ContentPresenter)target.Presenter).UpdateChild();
  68. Assert.Null(child.TemplatedParent);
  69. }
  70. [Fact]
  71. public void Control_Content_Should_Be_Logical_Child_Before_ApplyTemplate()
  72. {
  73. var target = new ContentControl
  74. {
  75. Template = GetTemplate(),
  76. };
  77. var child = new Control();
  78. target.Content = child;
  79. Assert.Equal(child.Parent, target);
  80. Assert.Equal(child.GetLogicalParent(), target);
  81. Assert.Equal(new[] { child }, target.GetLogicalChildren());
  82. }
  83. [Fact]
  84. public void DataTemplate_Created_Control_Should_Be_Logical_Child_After_ApplyTemplate()
  85. {
  86. var target = new ContentControl
  87. {
  88. Template = GetTemplate(),
  89. };
  90. target.Content = "Foo";
  91. target.ApplyTemplate();
  92. ((ContentPresenter)target.Presenter).UpdateChild();
  93. var child = target.Presenter.Child;
  94. Assert.NotNull(child);
  95. Assert.Equal(target, child.Parent);
  96. Assert.Equal(target, child.GetLogicalParent());
  97. Assert.Equal(new[] { child }, target.GetLogicalChildren());
  98. }
  99. [Fact]
  100. public void Clearing_Content_Should_Clear_Logical_Child()
  101. {
  102. var target = new ContentControl();
  103. var child = new Control();
  104. target.Content = child;
  105. Assert.Equal(new[] { child }, target.GetLogicalChildren());
  106. target.Content = null;
  107. Assert.Null(child.Parent);
  108. Assert.Null(child.GetLogicalParent());
  109. Assert.Empty(target.GetLogicalChildren());
  110. }
  111. [Fact]
  112. public void Setting_Content_Should_Fire_LogicalChildren_CollectionChanged()
  113. {
  114. var target = new ContentControl();
  115. var child = new Control();
  116. var called = false;
  117. ((ILogical)target).LogicalChildren.CollectionChanged += (s, e) =>
  118. called = e.Action == NotifyCollectionChangedAction.Add;
  119. target.Template = GetTemplate();
  120. target.Content = child;
  121. target.ApplyTemplate();
  122. ((ContentPresenter)target.Presenter).UpdateChild();
  123. Assert.True(called);
  124. }
  125. [Fact]
  126. public void Clearing_Content_Should_Fire_LogicalChildren_CollectionChanged()
  127. {
  128. var target = new ContentControl();
  129. var child = new Control();
  130. var called = false;
  131. target.Template = GetTemplate();
  132. target.Content = child;
  133. target.ApplyTemplate();
  134. ((ContentPresenter)target.Presenter).UpdateChild();
  135. ((ILogical)target).LogicalChildren.CollectionChanged += (s, e) => called = true;
  136. target.Content = null;
  137. ((ContentPresenter)target.Presenter).UpdateChild();
  138. Assert.True(called);
  139. }
  140. [Fact]
  141. public void Changing_Content_Should_Fire_LogicalChildren_CollectionChanged()
  142. {
  143. var target = new ContentControl();
  144. var child1 = new Control();
  145. var child2 = new Control();
  146. var called = false;
  147. target.Template = GetTemplate();
  148. target.Content = child1;
  149. target.ApplyTemplate();
  150. ((ContentPresenter)target.Presenter).UpdateChild();
  151. ((ILogical)target).LogicalChildren.CollectionChanged += (s, e) => called = true;
  152. target.Content = child2;
  153. target.Presenter.ApplyTemplate();
  154. Assert.True(called);
  155. }
  156. [Fact]
  157. public void Changing_Content_Should_Update_Presenter()
  158. {
  159. var target = new ContentControl();
  160. target.Template = GetTemplate();
  161. target.ApplyTemplate();
  162. ((ContentPresenter)target.Presenter).UpdateChild();
  163. target.Content = "Foo";
  164. ((ContentPresenter)target.Presenter).UpdateChild();
  165. Assert.Equal("Foo", ((TextBlock)target.Presenter.Child).Text);
  166. target.Content = "Bar";
  167. ((ContentPresenter)target.Presenter).UpdateChild();
  168. Assert.Equal("Bar", ((TextBlock)target.Presenter.Child).Text);
  169. }
  170. [Fact]
  171. public void DataContext_Should_Be_Set_For_DataTemplate_Created_Content()
  172. {
  173. var target = new ContentControl();
  174. target.Template = GetTemplate();
  175. target.Content = "Foo";
  176. target.ApplyTemplate();
  177. ((ContentPresenter)target.Presenter).UpdateChild();
  178. Assert.Equal("Foo", target.Presenter.Child.DataContext);
  179. }
  180. [Fact]
  181. public void DataContext_Should_Not_Be_Set_For_Control_Content()
  182. {
  183. var target = new ContentControl();
  184. target.Template = GetTemplate();
  185. target.Content = new TextBlock();
  186. target.ApplyTemplate();
  187. ((ContentPresenter)target.Presenter).UpdateChild();
  188. Assert.Null(target.Presenter.Child.DataContext);
  189. }
  190. private FuncControlTemplate GetTemplate()
  191. {
  192. return new FuncControlTemplate<ContentControl>(parent =>
  193. {
  194. return new Border
  195. {
  196. Background = new Media.SolidColorBrush(0xffffffff),
  197. Child = new ContentPresenter
  198. {
  199. Name = "PART_ContentPresenter",
  200. [~ContentPresenter.ContentProperty] = parent[~ContentControl.ContentProperty],
  201. }
  202. };
  203. });
  204. }
  205. }
  206. }