diff --git a/src/Controls/src/Core/Compatibility/iOS/Extensions/ToolbarItemExtensions.cs b/src/Controls/src/Core/Compatibility/iOS/Extensions/ToolbarItemExtensions.cs index da86a6f9ca9a..2ad07699ed1c 100644 --- a/src/Controls/src/Core/Compatibility/iOS/Extensions/ToolbarItemExtensions.cs +++ b/src/Controls/src/Core/Compatibility/iOS/Extensions/ToolbarItemExtensions.cs @@ -4,6 +4,7 @@ using CoreGraphics; using Foundation; using Microsoft.Maui.Graphics; +using Microsoft.Maui.Graphics.Platform; using Microsoft.Maui.Platform; using ObjCRuntime; using UIKit; @@ -57,6 +58,35 @@ internal static SecondarySubToolbarItem ToSecondarySubToolbarItem(this ToolbarIt return new SecondarySubToolbarItem(item, action); } + static UIImage ScaleImageToSystemDefaults(ImageSource imageSource, UIImage uIImage) + { + var icon = uIImage; + + var originalImageSize = icon?.Size ?? CGSize.Empty; + + // The largest height you can use for navigation bar icons in iOS. + // Per Apple's Human Interface Guidelines, the navigation bar height is 44 points, + // so using the full height ensures maximum visual clarity and maintains consistency + // with iOS design standards. This allows icons to utilize the entire available + // vertical space within the navigation bar container. + var defaultIconHeight = 44f; + var buffer = 0.1; + // We only check height because the navigation bar constrains vertical space (44pt height), + // but allows horizontal flexibility. Width can vary based on icon design and content, + // while height must fit within the fixed navigation bar bounds to avoid clipping. + + // if the image is bigger than the default available size, resize it + if (icon is not null && originalImageSize.Height - defaultIconHeight > buffer) + { + if (imageSource is not FontImageSource fontImageSource || !fontImageSource.IsSet(FontImageSource.SizeProperty)) + { + icon = icon.ResizeImageSource(originalImageSize.Width, defaultIconHeight, originalImageSize); + } + } + + return icon; + } + sealed class PrimaryToolbarItem : UIBarButtonItem { readonly bool _forceName; @@ -302,11 +332,11 @@ void OnPropertyChanged(object sender, PropertyChangedEventArgs e) void UpdateIcon(ToolbarItem item) { - if (item.IconImageSource != null && !item.IconImageSource.IsEmpty) + if (item.IconImageSource is not null && !item.IconImageSource.IsEmpty) { item.IconImageSource.LoadImage(item.FindMauiContext(), result => { - ((SecondaryToolbarItemContent)CustomView).Image = result?.Value; + ((SecondaryToolbarItemContent)CustomView).Image = ScaleImageToSystemDefaults(item.IconImageSource, result?.Value); }); } else diff --git a/src/Controls/tests/TestCases.Mac.Tests/snapshots/mac/ToolbarItemShouldBeCorrectlyRendered.png b/src/Controls/tests/TestCases.Mac.Tests/snapshots/mac/ToolbarItemShouldBeCorrectlyRendered.png new file mode 100644 index 000000000000..a9c0fad7e922 Binary files /dev/null and b/src/Controls/tests/TestCases.Mac.Tests/snapshots/mac/ToolbarItemShouldBeCorrectlyRendered.png differ diff --git a/src/Controls/tests/TestCases.iOS.Tests/snapshots/ios/ToolbarItemShouldBeCorrectlyRendered.png b/src/Controls/tests/TestCases.iOS.Tests/snapshots/ios/ToolbarItemShouldBeCorrectlyRendered.png new file mode 100644 index 000000000000..6de58d097162 Binary files /dev/null and b/src/Controls/tests/TestCases.iOS.Tests/snapshots/ios/ToolbarItemShouldBeCorrectlyRendered.png differ