ContentPageCommandBarPage.xaml.cs 8.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. using System.Collections.Generic;
  2. using System.Linq;
  3. using System.Threading.Tasks;
  4. using Avalonia.Controls;
  5. using Avalonia.Interactivity;
  6. using Avalonia.Layout;
  7. using Avalonia.Media;
  8. namespace ControlCatalog.Pages
  9. {
  10. public partial class ContentPageCommandBarPage : UserControl
  11. {
  12. private static readonly (string Label, string PathData)[] IconPresets =
  13. {
  14. ("Add", "M19,13H13V19H11V13H5V11H11V5H13V11H19V13Z"),
  15. ("Save", "M15,9H5V5H15M12,19A3,3 0 0,1 9,16A3,3 0 0,1 12,13A3,3 0 0,1 15,16A3,3 0 0,1 12,19M17,3H5C3.89,3 3,3.9 3,5V19A2,2 0 0,0 5,21H19A2,2 0 0,0 21,19V7L17,3Z"),
  16. ("Share", "M18,16.08C17.24,16.08 16.56,16.38 16.04,16.85L8.91,12.7C8.96,12.47 9,12.24 9,12C9,11.76 8.96,11.53 8.91,11.3L15.96,7.19C16.5,7.69 17.21,8 18,8A3,3 0 0,0 21,5A3,3 0 0,0 18,2A3,3 0 0,0 15,5C15,5.24 15.04,5.47 15.09,5.7L8.04,9.81C7.5,9.31 6.79,9 6,9A3,3 0 0,0 3,12A3,3 0 0,0 6,15C6.79,15 7.5,14.69 8.04,14.19L15.16,18.34C15.11,18.55 15.08,18.77 15.08,19C15.08,20.61 16.39,21.91 18,21.91C19.61,21.91 20.92,20.61 20.92,19C20.92,17.39 19.61,16.08 18,16.08Z"),
  17. ("Favorite", "M12,21.35L10.55,20.03C5.4,15.36 2,12.27 2,8.5C2,5.41 4.42,3 7.5,3C9.24,3 10.91,3.81 12,5.08C13.09,3.81 14.76,3 16.5,3C19.58,3 22,5.41 22,8.5C22,12.27 18.6,15.36 13.45,20.03L12,21.35Z"),
  18. ("Delete", "M19,4H15.5L14.5,3H9.5L8.5,4H5V6H19M6,19A2,2 0 0,0 8,21H16A2,2 0 0,0 18,19V7H6V19Z"),
  19. };
  20. private int _itemCounter;
  21. private string _position = "Top";
  22. private readonly List<ICommandBarElement> _primaryItems = new();
  23. private readonly List<ICommandBarElement> _secondaryItems = new();
  24. public ContentPageCommandBarPage()
  25. {
  26. InitializeComponent();
  27. Loaded += OnLoaded;
  28. }
  29. private async void OnLoaded(object? sender, RoutedEventArgs e)
  30. {
  31. var rootPage = new ContentPage
  32. {
  33. Header = "CommandBar Demo",
  34. Background = new SolidColorBrush(Color.Parse("#E3F2FD")),
  35. Content = new StackPanel
  36. {
  37. HorizontalAlignment = HorizontalAlignment.Center,
  38. VerticalAlignment = VerticalAlignment.Center,
  39. Spacing = 12,
  40. Children =
  41. {
  42. new TextBlock
  43. {
  44. Text = "Root Page",
  45. FontSize = 24,
  46. FontWeight = FontWeight.Bold,
  47. HorizontalAlignment = HorizontalAlignment.Center,
  48. },
  49. new TextBlock
  50. {
  51. Text = "Add items using the panel on the right,\nthen change the position to Top or Bottom.",
  52. FontSize = 14,
  53. TextWrapping = TextWrapping.Wrap,
  54. HorizontalAlignment = HorizontalAlignment.Center,
  55. TextAlignment = TextAlignment.Center,
  56. Opacity = 0.7,
  57. }
  58. }
  59. },
  60. HorizontalContentAlignment = HorizontalAlignment.Stretch,
  61. VerticalContentAlignment = VerticalAlignment.Stretch
  62. };
  63. await DemoNav.PushAsync(rootPage);
  64. }
  65. private void OnPositionChanged(object? sender, SelectionChangedEventArgs e)
  66. {
  67. if (PositionCombo == null)
  68. return;
  69. _position = PositionCombo.SelectedIndex == 1 ? "Bottom" : "Top";
  70. RebuildCommandBar();
  71. }
  72. private void OnAddPrimary(object? sender, RoutedEventArgs e)
  73. {
  74. _itemCounter++;
  75. var btn = new CommandBarButton { Label = $"Action {_itemCounter}" };
  76. if (UseIconCheck.IsChecked == true)
  77. {
  78. var preset = IconPresets[(_itemCounter - 1) % IconPresets.Length];
  79. btn.Label = preset.Label;
  80. btn.Icon = new PathIcon { Data = StreamGeometry.Parse(preset.PathData) };
  81. btn.IsCompact = true;
  82. }
  83. _primaryItems.Add(btn);
  84. RebuildCommandBar();
  85. }
  86. private void OnAddSecondary(object? sender, RoutedEventArgs e)
  87. {
  88. _itemCounter++;
  89. _secondaryItems.Add(new CommandBarButton { Label = $"Item {_itemCounter}" });
  90. RebuildCommandBar();
  91. }
  92. private void OnAddSeparator(object? sender, RoutedEventArgs e)
  93. {
  94. _primaryItems.Add(new CommandBarSeparator());
  95. RebuildCommandBar();
  96. }
  97. private void OnClearAll(object? sender, RoutedEventArgs e)
  98. {
  99. _primaryItems.Clear();
  100. _secondaryItems.Clear();
  101. _itemCounter = 0;
  102. ClearCommandBarFromActivePage();
  103. StatusText.Text = "No items added";
  104. }
  105. private async void OnPush(object? sender, RoutedEventArgs e)
  106. {
  107. var next = DemoNav.StackDepth + 1;
  108. var page = new ContentPage
  109. {
  110. Header = $"Page {next}",
  111. Background = new SolidColorBrush(Color.Parse("#E8F5E9")),
  112. Content = new StackPanel
  113. {
  114. HorizontalAlignment = HorizontalAlignment.Center,
  115. VerticalAlignment = VerticalAlignment.Center,
  116. Spacing = 8,
  117. Children =
  118. {
  119. new TextBlock
  120. {
  121. Text = $"Page {next}",
  122. FontSize = 28,
  123. FontWeight = FontWeight.Bold,
  124. HorizontalAlignment = HorizontalAlignment.Center,
  125. },
  126. new TextBlock
  127. {
  128. Text = "New page: no CommandBar set",
  129. FontSize = 14,
  130. Opacity = 0.6,
  131. HorizontalAlignment = HorizontalAlignment.Center,
  132. }
  133. }
  134. },
  135. HorizontalContentAlignment = HorizontalAlignment.Stretch,
  136. VerticalContentAlignment = VerticalAlignment.Stretch
  137. };
  138. await DemoNav.PushAsync(page);
  139. }
  140. private async void OnPop(object? sender, RoutedEventArgs e) => await DemoNav.PopAsync();
  141. private void ClearCommandBarFromActivePage()
  142. {
  143. if (DemoNav.CurrentPage is Page activePage)
  144. {
  145. NavigationPage.SetTopCommandBar(activePage, null);
  146. NavigationPage.SetBottomCommandBar(activePage, null);
  147. }
  148. }
  149. private void RebuildCommandBar()
  150. {
  151. if (DemoNav == null || DemoNav.CurrentPage is not Page activePage)
  152. return;
  153. if (_primaryItems.Count == 0 && _secondaryItems.Count == 0)
  154. {
  155. ClearCommandBarFromActivePage();
  156. StatusText.Text = "No items added";
  157. return;
  158. }
  159. NavigationPage.SetTopCommandBar(activePage, null);
  160. NavigationPage.SetBottomCommandBar(activePage, null);
  161. var commandBar = new CommandBar { IsDynamicOverflowEnabled = true };
  162. foreach (var item in _primaryItems)
  163. {
  164. if (item is CommandBarButton btn)
  165. {
  166. PathIcon? icon = null;
  167. if (btn.Icon is PathIcon src)
  168. icon = new PathIcon { Data = src.Data };
  169. commandBar.PrimaryCommands.Add(new CommandBarButton
  170. {
  171. Label = btn.Label,
  172. Icon = icon,
  173. IsCompact = btn.IsCompact,
  174. });
  175. }
  176. else if (item is CommandBarSeparator)
  177. commandBar.PrimaryCommands.Add(new CommandBarSeparator());
  178. }
  179. foreach (var item in _secondaryItems)
  180. {
  181. if (item is CommandBarButton btn)
  182. commandBar.SecondaryCommands.Add(new CommandBarButton { Label = btn.Label });
  183. }
  184. if (_position == "Top")
  185. NavigationPage.SetTopCommandBar(activePage, commandBar);
  186. else
  187. NavigationPage.SetBottomCommandBar(activePage, commandBar);
  188. var primaryCount = _primaryItems.Count(i => i is CommandBarButton);
  189. var secondaryCount = _secondaryItems.Count;
  190. StatusText.Text = $"{primaryCount} primary, {secondaryCount} secondary ({_position})";
  191. }
  192. }
  193. }