Skip to content

Commit

Permalink
Refactor IconsPage ItemsRepeater to ItemsView (microsoft#1376)
Browse files Browse the repository at this point in the history
<!--- Provide a general summary of your changes in the Title above -->

## Description
<!--- Describe your changes in detail -->
The ItemsRepeater for IconsPage has too many accessibility issues
including lack of keyboard navigation and narrator announcement.
Refactored to ItemsView that has all of it built in.

Also added Narrator announcement when filtered items have changed.

## Motivation and Context
<!--- Why is this change required? What problem does it solve? -->
<!--- If it fixes an open issue, please link to the issue here. -->
[Bug
44661633](https://microsoft.visualstudio.com/DefaultCollection/OS/_workitems/edit/44661633):
[WinUI Accessibility: Design guidance -> Icons]: Unable to navigate and
access the Icons present under “Fluent Icons Library” using keyboard.

[Bug
44661471](https://microsoft.visualstudio.com/DefaultCollection/OS/_workitems/edit/44661471):
[WinUI Accessibility: Design guidance -> Icons]: Screen reader fails to
announce regarding the available suggestions.

## How Has This Been Tested?
<!--- Please describe in detail how you tested your changes. -->
<!--- Include details of your testing environment, and the tests you ran
to -->
<!--- see how your change affects other areas of the code, etc. -->
Manual verification

## Screenshots (if appropriate):

## Types of changes
<!--- What types of changes does your code introduce? Put an `x` in all
the boxes that apply: -->
- [x] Bug fix (non-breaking change which fixes an issue)
- [ ] New feature (non-breaking change which adds functionality)
- [ ] Breaking change (fix or feature that would cause existing
functionality to change)
  • Loading branch information
karkarl committed Oct 17, 2023
1 parent 85d3945 commit 09424a9
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 70 deletions.
61 changes: 20 additions & 41 deletions WinUIGallery/ControlPages/DesignGuidance/IconsPage.xaml
Original file line number Diff line number Diff line change
Expand Up @@ -41,37 +41,15 @@
</Style>

<DataTemplate x:Key="IconTemplate">
<UserControl PointerPressed="Icons_TemplatePointerPressed">
<Grid
x:Name="IconTemplateRoot"
Width="96"
Height="96"
Margin="4"
HorizontalAlignment="Stretch"
x:DefaultBindMode="OneWay"
Background="{ThemeResource CardBackgroundFillColorDefaultBrush}"
BorderBrush="{ThemeResource CardStrokeColorDefaultBrush}"
BorderThickness="1"
CornerRadius="4"
ToolTipService.ToolTip="{Binding Name}">
<Grid.RowDefinitions>
<RowDefinition Height="*" />
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>

<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="SelectionState">
<VisualState x:Name="Default" />
<VisualState x:Name="Selected">
<VisualState.Setters>
<Setter Target="IconTemplateRoot.Background" Value="{ThemeResource AccentFillColorDefaultBrush}" />
<Setter Target="IconGlyph.Foreground" Value="{ThemeResource TextOnAccentFillColorPrimaryBrush}" />
<Setter Target="IconName.Foreground" Value="{ThemeResource TextOnAccentFillColorPrimaryBrush}" />
</VisualState.Setters>
</VisualState>
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<ItemContainer
AutomationProperties.Name="{Binding Name}"
ToolTipService.ToolTip="{Binding Name}"
Background="{ThemeResource CardBackgroundFillColorDefaultBrush}"
BorderBrush="{ThemeResource CardStrokeColorDefaultBrush}"
Width="96"
Height="96"
Margin="4">
<Grid>
<!-- Icon -->
<Viewbox
Grid.Row="1"
Expand All @@ -98,7 +76,7 @@
TextTrimming="CharacterEllipsis"
TextWrapping="NoWrap" />
</Grid>
</UserControl>
</ItemContainer>
</DataTemplate>
</Page.Resources>

Expand Down Expand Up @@ -168,7 +146,8 @@
<controls1:SampleThemeListener
Grid.Row="3"
MaxHeight="600"
VerticalAlignment="Top">
VerticalAlignment="Top"
IsTabStop="True">
<Grid
Background="{ThemeResource ControlExampleDisplayBrush}"
BorderBrush="{ThemeResource CardStrokeColorDefaultBrush}"
Expand All @@ -183,18 +162,18 @@
HorizontalAlignment="Stretch"
VerticalAlignment="Stretch"
AutomationProperties.Name="Icons">
<ItemsRepeater
x:Name="IconsRepeater"
<ItemsView
x:Name="IconsItemsView"
MinWidth="100"
Margin="0,0,0,36"
HorizontalAlignment="Stretch"
ElementIndexChanged="IconsRepeater_ElementIndexChanged"
ElementPrepared="IconsRepeater_ElementPrepared"
ItemTemplate="{StaticResource IconTemplate}">
<ItemsRepeater.Layout>
SelectionChanged="IconsItemsView_SelectionChanged"
ItemTemplate="{StaticResource IconTemplate}"
TabFocusNavigation="Once">
<ItemsView.Layout>
<UniformGridLayout Orientation="Horizontal" />
</ItemsRepeater.Layout>
</ItemsRepeater>
</ItemsView.Layout>
</ItemsView>
</ScrollViewer>

<Grid
Expand Down
36 changes: 7 additions & 29 deletions WinUIGallery/ControlPages/DesignGuidance/IconsPage.xaml.cs
Original file line number Diff line number Diff line change
Expand Up @@ -49,18 +49,18 @@ public IconsPage()
// Fill filtered items
IconsDataSource.Icons.ForEach(item => FilteredItems.Add(item));
this.InitializeComponent();
IconsRepeater.Loaded += ItemsGridView_Loaded;
IconsItemsView.Loaded += IconsItemsView_Loaded;
}

private void ItemsGridView_Loaded(object sender, RoutedEventArgs e)
private void IconsItemsView_Loaded(object sender, RoutedEventArgs e)
{
// Delegate loading of icons, so we have smooth navigating to this page
// and not unnecessarily block UI Thread
Task.Run(delegate ()
{
_ = DispatcherQueue.TryEnqueue(Microsoft.UI.Dispatching.DispatcherQueuePriority.High, () =>
{
IconsRepeater.ItemsSource = FilteredItems;
IconsItemsView.ItemsSource = FilteredItems;
SelectedItem = FilteredItems[0];
SetSampleCodePresenterCode(FilteredItems[0]);
});
Expand Down Expand Up @@ -111,35 +111,13 @@ public void Filter(string search)
UIHelper.AnnounceActionForAccessibility(IconsAutoSuggestBox, outputString, "AutoSuggestBoxNumberIconsFoundId");
}

private void Icons_TemplatePointerPressed(object sender, PointerRoutedEventArgs e)
private void IconsItemsView_SelectionChanged(ItemsView sender, ItemsViewSelectionChangedEventArgs args)
{
var oldIndex = FilteredItems.IndexOf(SelectedItem);
var previousItem = IconsRepeater.TryGetElement(oldIndex);
if(previousItem != null)
if (IconsItemsView.CurrentItemIndex != -1)
{
MoveToSelectionState(previousItem, false);
SelectedItem = FilteredItems[IconsItemsView.CurrentItemIndex];
}

var itemIndex = IconsRepeater.GetElementIndex(sender as UIElement);
SelectedItem = FilteredItems[itemIndex != -1 ? itemIndex : 0];
MoveToSelectionState(sender as UIElement, true);
}

private static void MoveToSelectionState(UIElement previousItem, bool isSelected)
{
VisualStateManager.GoToState(previousItem as Control, isSelected ? "Selected" : "Default", false);
}

private void IconsRepeater_ElementIndexChanged(ItemsRepeater sender, ItemsRepeaterElementIndexChangedEventArgs args)
{
var newItem = FilteredItems[args.NewIndex];
MoveToSelectionState(args.Element, newItem == SelectedItem);
}

private void IconsRepeater_ElementPrepared(ItemsRepeater sender, ItemsRepeaterElementPreparedEventArgs args)
{
var newItem = FilteredItems[args.Index];
MoveToSelectionState(args.Element, newItem == SelectedItem);

}
}
}

0 comments on commit 09424a9

Please sign in to comment.