StyleTests.cs 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665
  1. using System.Collections.Generic;
  2. using System.Collections.ObjectModel;
  3. using System.Linq;
  4. using System.Xml;
  5. using Avalonia.Controls;
  6. using Avalonia.Markup.Xaml.Styling;
  7. using Avalonia.Markup.Xaml.Templates;
  8. using Avalonia.Media;
  9. using Avalonia.Styling;
  10. using Avalonia.UnitTests;
  11. using Xunit;
  12. namespace Avalonia.Markup.Xaml.UnitTests.Xaml
  13. {
  14. public class StyleTests : XamlTestBase
  15. {
  16. [Fact]
  17. public void Color_Can_Be_Added_To_Style_Resources()
  18. {
  19. using (UnitTestApplication.Start(TestServices.MockPlatformWrapper))
  20. {
  21. var xaml = @"
  22. <UserControl xmlns='https://github.com/avaloniaui'
  23. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  24. <UserControl.Styles>
  25. <Style>
  26. <Style.Resources>
  27. <Color x:Key='color'>#ff506070</Color>
  28. </Style.Resources>
  29. </Style>
  30. </UserControl.Styles>
  31. </UserControl>";
  32. var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
  33. var color = (Color)((Style)userControl.Styles[0]).Resources["color"];
  34. Assert.Equal(0xff506070, color.ToUint32());
  35. }
  36. }
  37. [Fact]
  38. public void DataTemplate_Can_Be_Added_To_Style_Resources()
  39. {
  40. using (UnitTestApplication.Start(TestServices.MockPlatformWrapper))
  41. {
  42. var xaml = @"
  43. <UserControl xmlns='https://github.com/avaloniaui'
  44. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  45. <UserControl.Styles>
  46. <Style>
  47. <Style.Resources>
  48. <DataTemplate x:Key='dataTemplate'><TextBlock/></DataTemplate>
  49. </Style.Resources>
  50. </Style>
  51. </UserControl.Styles>
  52. </UserControl>";
  53. var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
  54. var dataTemplate = (DataTemplate)((Style)userControl.Styles[0]).Resources["dataTemplate"];
  55. Assert.NotNull(dataTemplate);
  56. }
  57. }
  58. [Fact]
  59. public void ControlTemplate_Can_Be_Added_To_Style_Resources()
  60. {
  61. using (UnitTestApplication.Start(TestServices.MockPlatformWrapper))
  62. {
  63. var xaml = @"
  64. <UserControl xmlns='https://github.com/avaloniaui'
  65. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  66. <UserControl.Styles>
  67. <Style>
  68. <Style.Resources>
  69. <ControlTemplate x:Key='controlTemplate' TargetType='{x:Type Button}'>
  70. <ContentPresenter Content='{TemplateBinding Content}'/>
  71. </ControlTemplate>
  72. </Style.Resources>
  73. </Style>
  74. </UserControl.Styles>
  75. </UserControl>";
  76. var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
  77. var controlTemplate = (ControlTemplate)((Style)userControl.Styles[0]).Resources["controlTemplate"];
  78. Assert.NotNull(controlTemplate);
  79. Assert.Equal(typeof(Button), controlTemplate.TargetType);
  80. }
  81. }
  82. [Fact]
  83. public void SolidColorBrush_Can_Be_Added_To_Style_Resources()
  84. {
  85. using (UnitTestApplication.Start(TestServices.MockPlatformWrapper))
  86. {
  87. var xaml = @"
  88. <UserControl xmlns='https://github.com/avaloniaui'
  89. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  90. <UserControl.Styles>
  91. <Style>
  92. <Style.Resources>
  93. <SolidColorBrush x:Key='brush'>#ff506070</SolidColorBrush>
  94. </Style.Resources>
  95. </Style>
  96. </UserControl.Styles>
  97. </UserControl>";
  98. var userControl = (UserControl)AvaloniaRuntimeXamlLoader.Load(xaml);
  99. var brush = (ISolidColorBrush)((Style)userControl.Styles[0]).Resources["brush"];
  100. Assert.Equal(0xff506070, brush.Color.ToUint32());
  101. }
  102. }
  103. [Fact]
  104. public void StyleInclude_Is_Built()
  105. {
  106. using (UnitTestApplication.Start(TestServices.StyledWindow
  107. .With(theme: () => new Styles())))
  108. {
  109. var xaml = @"
  110. <ContentControl xmlns='https://github.com/avaloniaui'>
  111. <ContentControl.Styles>
  112. <StyleInclude Source='avares://Avalonia.Markup.Xaml.UnitTests/Xaml/Style1.xaml'/>
  113. </ContentControl.Styles>
  114. </ContentControl>";
  115. var window = AvaloniaRuntimeXamlLoader.Parse<ContentControl>(xaml);
  116. Assert.IsType<Style>(window.Styles[0]);
  117. }
  118. }
  119. [Fact]
  120. public void StyleInclude_Is_Built_Resources()
  121. {
  122. using (UnitTestApplication.Start(TestServices.StyledWindow
  123. .With(theme: () => new Styles())))
  124. {
  125. var xaml = @"
  126. <ContentControl xmlns='https://github.com/avaloniaui'
  127. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  128. <ContentControl.Resources>
  129. <StyleInclude x:Key='Include' Source='avares://Avalonia.Markup.Xaml.UnitTests/Xaml/Style1.xaml'/>
  130. </ContentControl.Resources>
  131. </ContentControl>";
  132. var window = AvaloniaRuntimeXamlLoader.Parse<ContentControl>(xaml);
  133. Assert.IsType<Style>(window.Resources["Include"]);
  134. }
  135. }
  136. [Fact]
  137. public void Setter_Can_Contain_Template()
  138. {
  139. using (UnitTestApplication.Start(TestServices.StyledWindow))
  140. {
  141. var xaml = @"
  142. <Window xmlns='https://github.com/avaloniaui'
  143. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  144. <Window.Styles>
  145. <Style Selector='ContentControl'>
  146. <Setter Property='Content'>
  147. <Template>
  148. <TextBlock>Hello World!</TextBlock>
  149. </Template>
  150. </Setter>
  151. </Style>
  152. </Window.Styles>
  153. <ContentControl Name='target'/>
  154. </Window>";
  155. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  156. var target = window.Find<ContentControl>("target");
  157. Assert.IsType<TextBlock>(target.Content);
  158. Assert.Equal("Hello World!", ((TextBlock)target.Content).Text);
  159. }
  160. }
  161. [Fact]
  162. public void Setter_Value_Is_Bound_Directly_If_The_Target_Type_Derives_From_ITemplate()
  163. {
  164. using (UnitTestApplication.Start(TestServices.StyledWindow))
  165. {
  166. var xaml = @"
  167. <Window xmlns='https://github.com/avaloniaui'
  168. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  169. <Window.Styles>
  170. <Style Selector=':is(Control)'>
  171. <Setter Property='FocusAdorner'>
  172. <FocusAdornerTemplate>
  173. <Rectangle Stroke='Black'
  174. StrokeThickness='1'
  175. StrokeDashArray='1,2'/>
  176. </FocusAdornerTemplate>
  177. </Setter>
  178. </Style>
  179. </Window.Styles>
  180. <TextBlock Name='target'/>
  181. </Window>";
  182. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  183. var target = window.Find<TextBlock>("target");
  184. Assert.NotNull(target.FocusAdorner);
  185. }
  186. }
  187. [Fact]
  188. public void Setter_Can_Set_Attached_Property()
  189. {
  190. using (UnitTestApplication.Start(TestServices.StyledWindow))
  191. {
  192. var xaml = @"
  193. <Window xmlns='https://github.com/avaloniaui'
  194. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'
  195. xmlns:local='clr-namespace:Avalonia.Markup.Xaml.UnitTests.Xaml;assembly=Avalonia.Markup.Xaml.UnitTests'>
  196. <Window.Styles>
  197. <Style Selector='TextBlock'>
  198. <Setter Property='DockPanel.Dock' Value='Right'/>
  199. </Style>
  200. </Window.Styles>
  201. <TextBlock/>
  202. </Window>";
  203. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  204. var textBlock = (TextBlock)window.Content;
  205. window.ApplyTemplate();
  206. Assert.Equal(Dock.Right, DockPanel.GetDock(textBlock));
  207. }
  208. }
  209. [Fact(Skip = "The animation system currently needs to be able to set any property on any object")]
  210. public void Disallows_Setting_Non_Registered_Property()
  211. {
  212. using (UnitTestApplication.Start(TestServices.StyledWindow))
  213. {
  214. var xaml = @"
  215. <Window xmlns='https://github.com/avaloniaui'
  216. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'
  217. xmlns:local='clr-namespace:Avalonia.Markup.Xaml.UnitTests.Xaml;assembly=Avalonia.Markup.Xaml.UnitTests'>
  218. <Window.Styles>
  219. <Style Selector='TextBlock'>
  220. <Setter Property='Button.IsDefault' Value='True'/>
  221. </Style>
  222. </Window.Styles>
  223. <TextBlock/>
  224. </Window>";
  225. var ex = Assert.Throws<XmlException>(() => AvaloniaRuntimeXamlLoader.Load(xaml));
  226. Assert.Equal(
  227. "Property 'Button.IsDefault' is not registered on 'Avalonia.Controls.TextBlock'.",
  228. ex.InnerException.Message);
  229. }
  230. }
  231. [Fact]
  232. public void Style_Can_Use_Not_Selector()
  233. {
  234. using (UnitTestApplication.Start(TestServices.StyledWindow))
  235. {
  236. var xaml = @"
  237. <Window xmlns='https://github.com/avaloniaui'
  238. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  239. <Window.Styles>
  240. <Style Selector='Border:not(.foo)'>
  241. <Setter Property='Background' Value='Red'/>
  242. </Style>
  243. </Window.Styles>
  244. <StackPanel>
  245. <Border Name='foo' Classes='foo bar'/>
  246. <Border Name='notFoo' Classes='bar'/>
  247. </StackPanel>
  248. </Window>";
  249. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  250. var foo = window.FindControl<Border>("foo");
  251. var notFoo = window.FindControl<Border>("notFoo");
  252. Assert.Null(foo.Background);
  253. Assert.Equal(Colors.Red, ((ISolidColorBrush)notFoo.Background).Color);
  254. }
  255. }
  256. [Fact]
  257. public void Style_Can_Use_NthChild_Selector()
  258. {
  259. using (UnitTestApplication.Start(TestServices.StyledWindow))
  260. {
  261. var xaml = @"
  262. <Window xmlns='https://github.com/avaloniaui'
  263. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  264. <Window.Styles>
  265. <Style Selector='Border.foo:nth-child(2n+1)'>
  266. <Setter Property='Background' Value='Red'/>
  267. </Style>
  268. </Window.Styles>
  269. <StackPanel>
  270. <Border x:Name='b1' Classes='foo'/>
  271. <Border x:Name='b2' />
  272. </StackPanel>
  273. </Window>";
  274. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  275. var b1 = window.FindControl<Border>("b1");
  276. var b2 = window.FindControl<Border>("b2");
  277. Assert.Equal(Brushes.Red, b1.Background);
  278. Assert.Null(b2.Background);
  279. }
  280. }
  281. [Fact]
  282. public void Style_Can_Use_NthChild_Selector_After_Reoder()
  283. {
  284. using (UnitTestApplication.Start(TestServices.StyledWindow))
  285. {
  286. var xaml = @"
  287. <Window xmlns='https://github.com/avaloniaui'
  288. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  289. <Window.Styles>
  290. <Style Selector='Border:nth-child(2n)'>
  291. <Setter Property='Background' Value='Red'/>
  292. </Style>
  293. </Window.Styles>
  294. <StackPanel x:Name='parent'>
  295. <Border x:Name='b1' />
  296. <Border x:Name='b2' />
  297. </StackPanel>
  298. </Window>";
  299. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  300. var parent = window.FindControl<StackPanel>("parent");
  301. var b1 = window.FindControl<Border>("b1");
  302. var b2 = window.FindControl<Border>("b2");
  303. Assert.Null(b1.Background);
  304. Assert.Equal(Brushes.Red, b2.Background);
  305. parent.Children.Remove(b1);
  306. Assert.Null(b1.Background);
  307. Assert.Null(b2.Background);
  308. parent.Children.Add(b1);
  309. Assert.Equal(Brushes.Red, b1.Background);
  310. Assert.Null(b2.Background);
  311. }
  312. }
  313. [Fact]
  314. public void Style_Can_Use_NthLastChild_Selector_After_Reoder()
  315. {
  316. using (UnitTestApplication.Start(TestServices.StyledWindow))
  317. {
  318. var xaml = @"
  319. <Window xmlns='https://github.com/avaloniaui'
  320. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  321. <Window.Styles>
  322. <Style Selector='Border:nth-last-child(2n)'>
  323. <Setter Property='Background' Value='Red'/>
  324. </Style>
  325. </Window.Styles>
  326. <StackPanel x:Name='parent'>
  327. <Border x:Name='b1' />
  328. <Border x:Name='b2' />
  329. </StackPanel>
  330. </Window>";
  331. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  332. var parent = window.FindControl<StackPanel>("parent");
  333. var b1 = window.FindControl<Border>("b1");
  334. var b2 = window.FindControl<Border>("b2");
  335. Assert.Equal(Brushes.Red, b1.Background);
  336. Assert.Null(b2.Background);
  337. parent.Children.Remove(b1);
  338. Assert.Null(b1.Background);
  339. Assert.Null(b2.Background);
  340. parent.Children.Add(b1);
  341. Assert.Null(b1.Background);
  342. Assert.Equal(Brushes.Red, b2.Background);
  343. }
  344. }
  345. [Fact]
  346. public void Style_Can_Use_NthChild_Selector_With_ListBox()
  347. {
  348. using (UnitTestApplication.Start(TestServices.StyledWindow))
  349. {
  350. var xaml = @"
  351. <Window xmlns='https://github.com/avaloniaui'
  352. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  353. <Window.Styles>
  354. <Style Selector='ListBoxItem:nth-child(2n)'>
  355. <Setter Property='Background' Value='{Binding}'/>
  356. </Style>
  357. </Window.Styles>
  358. <ListBox x:Name='list' />
  359. </Window>";
  360. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  361. var collection = new ObservableCollection<IBrush>()
  362. {
  363. Brushes.Red, Brushes.Green, Brushes.Blue
  364. };
  365. var list = window.FindControl<ListBox>("list");
  366. list.VirtualizationMode = ItemVirtualizationMode.Simple;
  367. list.Items = collection;
  368. window.Show();
  369. IEnumerable<IBrush> GetColors() => list.Presenter.Panel.Children.Cast<ListBoxItem>().Select(t => t.Background);
  370. Assert.Equal(new[] { Brushes.Transparent, Brushes.Green, Brushes.Transparent }, GetColors());
  371. collection.Remove(Brushes.Green);
  372. Assert.Equal(new[] { Brushes.Transparent, Brushes.Blue }, GetColors());
  373. collection.Add(Brushes.Violet);
  374. collection.Add(Brushes.Black);
  375. Assert.Equal(new[] { Brushes.Transparent, Brushes.Blue, Brushes.Transparent, Brushes.Black }, GetColors());
  376. }
  377. }
  378. [Fact]
  379. public void Style_Can_Use_NthChild_Selector_With_ItemsRepeater()
  380. {
  381. using (UnitTestApplication.Start(TestServices.StyledWindow))
  382. {
  383. var xaml = @"
  384. <Window xmlns='https://github.com/avaloniaui'
  385. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  386. <Window.Styles>
  387. <Style Selector='TextBlock'>
  388. <Setter Property='Foreground' Value='Transparent'/>
  389. </Style>
  390. <Style Selector='TextBlock:nth-child(2n)'>
  391. <Setter Property='Foreground' Value='{Binding}'/>
  392. </Style>
  393. </Window.Styles>
  394. <ItemsRepeater x:Name='list' />
  395. </Window>";
  396. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  397. var collection = new ObservableCollection<IBrush>()
  398. {
  399. Brushes.Red, Brushes.Green, Brushes.Blue
  400. };
  401. var list = window.FindControl<ItemsRepeater>("list");
  402. list.Items = collection;
  403. window.Show();
  404. IEnumerable<IBrush> GetColors() => Enumerable.Range(0, list.ItemsSourceView.Count)
  405. .Select(t => (list.GetOrCreateElement(t) as TextBlock)!.Foreground);
  406. Assert.Equal(new[] { Brushes.Transparent, Brushes.Green, Brushes.Transparent }, GetColors());
  407. collection.Remove(Brushes.Green);
  408. Assert.Equal(new[] { Brushes.Transparent, Brushes.Blue }, GetColors().ToList());
  409. collection.Add(Brushes.Violet);
  410. collection.Add(Brushes.Black);
  411. Assert.Equal(new[] { Brushes.Transparent, Brushes.Blue, Brushes.Transparent, Brushes.Black }, GetColors());
  412. }
  413. }
  414. [Fact]
  415. public void Style_Can_Use_Or_Selector_1()
  416. {
  417. using (UnitTestApplication.Start(TestServices.StyledWindow))
  418. {
  419. var xaml = @"
  420. <Window xmlns='https://github.com/avaloniaui'
  421. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  422. <Window.Styles>
  423. <Style Selector='Border.foo, Border.bar'>
  424. <Setter Property='Background' Value='Red'/>
  425. </Style>
  426. </Window.Styles>
  427. <StackPanel>
  428. <Border Name='foo' Classes='foo'/>
  429. <Border Name='bar' Classes='bar'/>
  430. <Border Name='baz' Classes='baz'/>
  431. </StackPanel>
  432. </Window>";
  433. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  434. var foo = window.FindControl<Border>("foo");
  435. var bar = window.FindControl<Border>("bar");
  436. var baz = window.FindControl<Border>("baz");
  437. Assert.Equal(Brushes.Red, foo.Background);
  438. Assert.Equal(Brushes.Red, bar.Background);
  439. Assert.Null(baz.Background);
  440. }
  441. }
  442. [Fact]
  443. public void Style_Can_Use_Or_Selector_2()
  444. {
  445. using (UnitTestApplication.Start(TestServices.StyledWindow))
  446. {
  447. var xaml = @"
  448. <Window xmlns='https://github.com/avaloniaui'
  449. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  450. <Window.Styles>
  451. <Style Selector='Button,Carousel,ListBox'>
  452. <Setter Property='Background' Value='Red'/>
  453. </Style>
  454. </Window.Styles>
  455. <StackPanel>
  456. <Button Name='button'/>
  457. <Carousel Name='carousel'/>
  458. <ListBox Name='listBox'/>
  459. </StackPanel>
  460. </Window>";
  461. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  462. var button = window.FindControl<Button>("button");
  463. var carousel = window.FindControl<Carousel>("carousel");
  464. var listBox = window.FindControl<ListBox>("listBox");
  465. Assert.Equal(Brushes.Red, button.Background);
  466. Assert.Equal(Brushes.Red, carousel.Background);
  467. Assert.Equal(Brushes.Red, listBox.Background);
  468. }
  469. }
  470. [Fact]
  471. public void Transitions_Can_Be_Styled()
  472. {
  473. using (UnitTestApplication.Start(TestServices.StyledWindow))
  474. {
  475. var xaml = @"
  476. <Window xmlns='https://github.com/avaloniaui'
  477. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  478. <Window.Styles>
  479. <Style Selector='Border'>
  480. <Setter Property='Transitions'>
  481. <Transitions>
  482. <DoubleTransition Property='Width' Duration='0:0:1'/>
  483. </Transitions>
  484. </Setter>
  485. </Style>
  486. <Style Selector='Border.foo'>
  487. <Setter Property='Transitions'>
  488. <Transitions>
  489. <DoubleTransition Property='Height' Duration='0:0:1'/>
  490. </Transitions>
  491. </Setter>
  492. </Style>
  493. </Window.Styles>
  494. <Border/>
  495. </Window>";
  496. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  497. var border = (Border)window.Content;
  498. Assert.Equal(1, border.Transitions.Count);
  499. Assert.Equal(Border.WidthProperty, border.Transitions[0].Property);
  500. border.Classes.Add("foo");
  501. Assert.Equal(1, border.Transitions.Count);
  502. Assert.Equal(Border.HeightProperty, border.Transitions[0].Property);
  503. border.Classes.Remove("foo");
  504. Assert.Equal(1, border.Transitions.Count);
  505. Assert.Equal(Border.WidthProperty, border.Transitions[0].Property);
  506. }
  507. }
  508. [Fact]
  509. public void Style_Can_Use_Class_Selector_With_Dash()
  510. {
  511. using (UnitTestApplication.Start(TestServices.StyledWindow))
  512. {
  513. var xaml = @"
  514. <Window xmlns='https://github.com/avaloniaui'
  515. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  516. <Window.Styles>
  517. <Style Selector='Border.foo-bar'>
  518. <Setter Property='Background' Value='Red'/>
  519. </Style>
  520. </Window.Styles>
  521. <StackPanel>
  522. <Border Name='foo' Classes='foo-bar'/>
  523. </StackPanel>
  524. </Window>";
  525. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  526. var foo = window.FindControl<Border>("foo");
  527. Assert.Equal(Colors.Red, ((ISolidColorBrush)foo.Background).Color);
  528. }
  529. }
  530. [Fact]
  531. public void Style_Can_Use_Pseudolass_Selector_With_Dash()
  532. {
  533. using (UnitTestApplication.Start(TestServices.StyledWindow))
  534. {
  535. var xaml = @"
  536. <Window xmlns='https://github.com/avaloniaui'
  537. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  538. <Window.Styles>
  539. <Style Selector='Border:foo-bar'>
  540. <Setter Property='Background' Value='Red'/>
  541. </Style>
  542. </Window.Styles>
  543. <StackPanel>
  544. <Border Name='foo'/>
  545. </StackPanel>
  546. </Window>";
  547. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  548. var foo = window.FindControl<Border>("foo");
  549. Assert.Null(foo.Background);
  550. ((IPseudoClasses)foo.Classes).Add(":foo-bar");
  551. Assert.Equal(Colors.Red, ((ISolidColorBrush)foo.Background).Color);
  552. }
  553. }
  554. [Fact]
  555. public void Can_Use_Nested_Styles()
  556. {
  557. using (UnitTestApplication.Start(TestServices.StyledWindow))
  558. {
  559. var xaml = @"
  560. <Window xmlns='https://github.com/avaloniaui'
  561. xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'>
  562. <Window.Styles>
  563. <Style Selector='Border'>
  564. <Style Selector='^.foo'>
  565. <Setter Property='Background' Value='Red'/>
  566. </Style>
  567. </Style>
  568. </Window.Styles>
  569. <StackPanel>
  570. <Border Name='foo'/>
  571. </StackPanel>
  572. </Window>";
  573. var window = (Window)AvaloniaRuntimeXamlLoader.Load(xaml);
  574. var foo = window.FindControl<Border>("foo");
  575. Assert.Null(foo.Background);
  576. foo.Classes.Add("foo");
  577. Assert.Equal(Colors.Red, ((ISolidColorBrush)foo.Background).Color);
  578. }
  579. }
  580. }
  581. }