Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Windows] Improve performance in accessibility extensions #22698

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
#nullable disable
using Microsoft.UI.Xaml;
using Microsoft.UI.Xaml.Automation.Peers;
using NativeAutomationProperties = Microsoft.UI.Xaml.Automation.AutomationProperties;
Expand All @@ -7,112 +6,153 @@ namespace Microsoft.Maui.Controls.Platform
{
public static class AccessibilityExtensions
{
public static void SetAutomationPropertiesAutomationId(this FrameworkElement Control, string id)
public static void SetAutomationPropertiesAutomationId(this FrameworkElement Control, string? id)
{
Control.SetValue(NativeAutomationProperties.AutomationIdProperty, id);
}

public static string SetAutomationPropertiesName(this FrameworkElement Control, Element Element, string _defaultAutomationPropertiesName = null)
public static string? SetAutomationPropertiesName(this FrameworkElement Control, Element? Element, string? _defaultAutomationPropertiesName = null)
{
if (Element == null)
if (Element is null)
{
return _defaultAutomationPropertiesName;
}

string? currentValue = null;

if (_defaultAutomationPropertiesName == null)
_defaultAutomationPropertiesName = (string)Control.GetValue(NativeAutomationProperties.NameProperty);
if (_defaultAutomationPropertiesName is null)
{
_defaultAutomationPropertiesName = currentValue = (string)Control.GetValue(NativeAutomationProperties.NameProperty);
}

#pragma warning disable CS0618 // Type or member is obsolete
var elemValue = (string)Element.GetValue(AutomationProperties.NameProperty);
#pragma warning restore CS0618 // Type or member is obsolete

if (!string.IsNullOrWhiteSpace(elemValue))
Control.SetValue(NativeAutomationProperties.NameProperty, elemValue);
else
string newValue = !string.IsNullOrWhiteSpace(elemValue) ? elemValue : _defaultAutomationPropertiesName;

if (currentValue is null || currentValue != newValue)
{
Control.SetValue(NativeAutomationProperties.NameProperty, _defaultAutomationPropertiesName);
}

return _defaultAutomationPropertiesName;
}

public static AccessibilityView? SetAutomationPropertiesAccessibilityView(this FrameworkElement Control, Element Element, AccessibilityView? _defaultAutomationPropertiesAccessibilityView = null)
public static AccessibilityView? SetAutomationPropertiesAccessibilityView(this FrameworkElement Control, Element? Element, AccessibilityView? _defaultAutomationPropertiesAccessibilityView = null)
{
if (Element == null)
if (Element is null)
{
return _defaultAutomationPropertiesAccessibilityView;
}

AccessibilityView? currentValue = null;

if (!_defaultAutomationPropertiesAccessibilityView.HasValue)
_defaultAutomationPropertiesAccessibilityView = (AccessibilityView)Control.GetValue(NativeAutomationProperties.AccessibilityViewProperty);
{
_defaultAutomationPropertiesAccessibilityView = currentValue = (AccessibilityView)Control.GetValue(NativeAutomationProperties.AccessibilityViewProperty);
}

var newValue = _defaultAutomationPropertiesAccessibilityView;

var elemValue = (bool?)Element.GetValue(AutomationProperties.IsInAccessibleTreeProperty);

if (elemValue == true)
{
newValue = AccessibilityView.Content;
}
else if (elemValue == false)
{
newValue = AccessibilityView.Raw;
}

Control.SetValue(NativeAutomationProperties.AccessibilityViewProperty, newValue);
if (currentValue is null || currentValue != newValue)
{
Control.SetValue(NativeAutomationProperties.AccessibilityViewProperty, newValue);
}

return _defaultAutomationPropertiesAccessibilityView;

}
public static string SetAutomationPropertiesHelpText(this FrameworkElement Control, Element Element, string _defaultAutomationPropertiesHelpText = null)
public static string? SetAutomationPropertiesHelpText(this FrameworkElement Control, Element? Element, string? _defaultAutomationPropertiesHelpText = null)
{
if (Element == null)
{
return _defaultAutomationPropertiesHelpText;
}

if (_defaultAutomationPropertiesHelpText == null)
_defaultAutomationPropertiesHelpText = (string)Control.GetValue(NativeAutomationProperties.HelpTextProperty);
string? currentValue = null;

if (_defaultAutomationPropertiesHelpText is null)
{
_defaultAutomationPropertiesHelpText = currentValue = (string)Control.GetValue(NativeAutomationProperties.HelpTextProperty);
}

#pragma warning disable CS0618 // Type or member is obsolete
var elemValue = (string)Element.GetValue(AutomationProperties.HelpTextProperty);
#pragma warning restore CS0618 // Type or member is obsolete
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If I get it right, this line should be changed to:

var elemValue = SemanticProperties.GetHint(Element);

to fix the "obsolete" warning. Is that right? Should it be done now?


if (!string.IsNullOrWhiteSpace(elemValue))
Control.SetValue(NativeAutomationProperties.HelpTextProperty, elemValue);
else
string newValue = !string.IsNullOrWhiteSpace(elemValue) ? elemValue : _defaultAutomationPropertiesHelpText;

if (currentValue is null || newValue != currentValue)
{
Control.SetValue(NativeAutomationProperties.HelpTextProperty, _defaultAutomationPropertiesHelpText);
}

return _defaultAutomationPropertiesHelpText;
}

public static UIElement SetAutomationPropertiesLabeledBy(
public static UIElement? SetAutomationPropertiesLabeledBy(
this FrameworkElement Control,
Element Element,
IMauiContext mauiContext,
UIElement _defaultAutomationPropertiesLabeledBy = null)
Element? Element,
IMauiContext? mauiContext,
UIElement? _defaultAutomationPropertiesLabeledBy = null)
{
if (Element == null)
if (Element is null)
{
return _defaultAutomationPropertiesLabeledBy;
}

// TODO Maui: this is a bit of a hack because Elements
// currently don't implement IView but they should
mauiContext ??= (Element as IView)?.Handler?.MauiContext;

if (_defaultAutomationPropertiesLabeledBy == null)
_defaultAutomationPropertiesLabeledBy = (UIElement)Control.GetValue(NativeAutomationProperties.LabeledByProperty);
UIElement? currentValue = null;

if (_defaultAutomationPropertiesLabeledBy is null)
{
_defaultAutomationPropertiesLabeledBy = currentValue = (UIElement)Control.GetValue(NativeAutomationProperties.LabeledByProperty);
}
#pragma warning disable CS0618 // Type or member is obsolete
var elemValue = (VisualElement)Element.GetValue(AutomationProperties.LabeledByProperty);
#pragma warning restore CS0618 // Type or member is obsolete
FrameworkElement nativeElement = null;
FrameworkElement? nativeElement = null;

if (mauiContext != null)
{
nativeElement = (elemValue as IView)?.ToHandler(mauiContext)?.PlatformView as FrameworkElement;
}

UIElement? newValue = nativeElement is not null ? nativeElement : _defaultAutomationPropertiesLabeledBy;

if (nativeElement != null)
if (currentValue is null || newValue != currentValue)
{
#pragma warning disable CS0618 // Type or member is obsolete
Control.SetValue(AutomationProperties.LabeledByProperty, nativeElement);
Control.SetValue(AutomationProperties.LabeledByProperty, newValue);
#pragma warning restore CS0618 // Type or member is obsolete
else
Control.SetValue(NativeAutomationProperties.LabeledByProperty, _defaultAutomationPropertiesLabeledBy);
}

return _defaultAutomationPropertiesLabeledBy;
}

// TODO MAUI: This is not having any effect on anything I've tested yet. See if we need it
// after we test the FP and NP w/ back button explicitly enabled.
public static void SetBackButtonTitle(this PageControl Control, Element Element)
public static void SetBackButtonTitle(this PageControl Control, Element? Element)
{
if (Element == null)
if (Element is null)
{
return;
}

var elemValue = ConcatenateNameAndHint(Element);

Expand All @@ -130,21 +170,23 @@ static string ConcatenateNameAndHint(Element Element)
#pragma warning restore CS0618 // Type or member is obsolete

if (string.IsNullOrWhiteSpace(name) || string.IsNullOrWhiteSpace(hint))
{
separator = "";

}
else
{
separator = ". ";

}

return string.Join(separator, name, hint);

}

public static void SetAutomationProperties(
this FrameworkElement frameworkElement,
Element element,
IMauiContext mauiContext,
string defaultName = null)
Element? element,
IMauiContext? mauiContext,
string? defaultName = null)
{
frameworkElement.SetAutomationPropertiesAutomationId(element?.AutomationId);
frameworkElement.SetAutomationPropertiesName(element, defaultName);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2534,13 +2534,6 @@
~static Microsoft.Maui.Controls.OnPlatform<T>.implicit operator T(Microsoft.Maui.Controls.OnPlatform<T> onPlatform) -> T
~static Microsoft.Maui.Controls.PanGestureRecognizer.CurrentId.get -> Microsoft.Maui.Controls.Internals.AutoId
~static Microsoft.Maui.Controls.Picker.ControlsPickerMapper -> Microsoft.Maui.IPropertyMapper<Microsoft.Maui.IPicker, Microsoft.Maui.Handlers.PickerHandler>
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationProperties(this Microsoft.UI.Xaml.FrameworkElement frameworkElement, Microsoft.Maui.Controls.Element element, Microsoft.Maui.IMauiContext mauiContext, string defaultName = null) -> void
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesAccessibilityView(this Microsoft.UI.Xaml.FrameworkElement Control, Microsoft.Maui.Controls.Element Element, Microsoft.UI.Xaml.Automation.Peers.AccessibilityView? _defaultAutomationPropertiesAccessibilityView = null) -> Microsoft.UI.Xaml.Automation.Peers.AccessibilityView?
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesAutomationId(this Microsoft.UI.Xaml.FrameworkElement Control, string id) -> void
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesHelpText(this Microsoft.UI.Xaml.FrameworkElement Control, Microsoft.Maui.Controls.Element Element, string _defaultAutomationPropertiesHelpText = null) -> string
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesLabeledBy(this Microsoft.UI.Xaml.FrameworkElement Control, Microsoft.Maui.Controls.Element Element, Microsoft.Maui.IMauiContext mauiContext, Microsoft.UI.Xaml.UIElement _defaultAutomationPropertiesLabeledBy = null) -> Microsoft.UI.Xaml.UIElement
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesName(this Microsoft.UI.Xaml.FrameworkElement Control, Microsoft.Maui.Controls.Element Element, string _defaultAutomationPropertiesName = null) -> string
~static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetBackButtonTitle(this Microsoft.Maui.Controls.Platform.PageControl Control, Microsoft.Maui.Controls.Element Element) -> void
~static Microsoft.Maui.Controls.Platform.AccessKeyHelper.UpdateAccessKey(Microsoft.UI.Xaml.FrameworkElement control, Microsoft.Maui.Controls.VisualElement element) -> void
~static Microsoft.Maui.Controls.Platform.BrushExtensions.ToBrush(this Microsoft.Maui.Controls.Brush brush) -> Microsoft.UI.Xaml.Media.Brush
~static Microsoft.Maui.Controls.Platform.FontExtensions.ApplyFont(this Microsoft.UI.Xaml.Controls.Control self, Microsoft.Maui.Font font, Microsoft.Maui.IFontManager fontManager) -> void
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,13 @@ Microsoft.Maui.Controls.PointerGestureRecognizer.PointerReleasedCommand.get -> S
Microsoft.Maui.Controls.PointerGestureRecognizer.PointerReleasedCommand.set -> void
Microsoft.Maui.Controls.PointerGestureRecognizer.PointerReleasedCommandParameter.get -> object!
Microsoft.Maui.Controls.PointerGestureRecognizer.PointerReleasedCommandParameter.set -> void
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationProperties(this Microsoft.UI.Xaml.FrameworkElement! frameworkElement, Microsoft.Maui.Controls.Element? element, Microsoft.Maui.IMauiContext? mauiContext, string? defaultName = null) -> void
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesAccessibilityView(this Microsoft.UI.Xaml.FrameworkElement! Control, Microsoft.Maui.Controls.Element? Element, Microsoft.UI.Xaml.Automation.Peers.AccessibilityView? _defaultAutomationPropertiesAccessibilityView = null) -> Microsoft.UI.Xaml.Automation.Peers.AccessibilityView?
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesAutomationId(this Microsoft.UI.Xaml.FrameworkElement! Control, string? id) -> void
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesHelpText(this Microsoft.UI.Xaml.FrameworkElement! Control, Microsoft.Maui.Controls.Element? Element, string? _defaultAutomationPropertiesHelpText = null) -> string?
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesLabeledBy(this Microsoft.UI.Xaml.FrameworkElement! Control, Microsoft.Maui.Controls.Element? Element, Microsoft.Maui.IMauiContext? mauiContext, Microsoft.UI.Xaml.UIElement? _defaultAutomationPropertiesLabeledBy = null) -> Microsoft.UI.Xaml.UIElement?
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetAutomationPropertiesName(this Microsoft.UI.Xaml.FrameworkElement! Control, Microsoft.Maui.Controls.Element? Element, string? _defaultAutomationPropertiesName = null) -> string?
static Microsoft.Maui.Controls.Platform.AccessibilityExtensions.SetBackButtonTitle(this Microsoft.Maui.Controls.Platform.PageControl! Control, Microsoft.Maui.Controls.Element? Element) -> void
static readonly Microsoft.Maui.Controls.KeyboardAccelerator.KeyProperty -> Microsoft.Maui.Controls.BindableProperty!
static readonly Microsoft.Maui.Controls.KeyboardAccelerator.ModifiersProperty -> Microsoft.Maui.Controls.BindableProperty!
static readonly Microsoft.Maui.Controls.DragGestureRecognizer.CanDragProperty -> Microsoft.Maui.Controls.BindableProperty!
Expand Down
Loading