diff --git a/samples/ControlCatalog.Android/MainActivity.cs b/samples/ControlCatalog.Android/MainActivity.cs
index f6fa07dbde..486d14661e 100644
--- a/samples/ControlCatalog.Android/MainActivity.cs
+++ b/samples/ControlCatalog.Android/MainActivity.cs
@@ -5,7 +5,7 @@ using Avalonia.Android;
namespace ControlCatalog.Android
{
- [Activity(Label = "ControlCatalog.Android", Theme = "@style/MyTheme.Main", Icon = "@drawable/icon", LaunchMode = LaunchMode.SingleTop, ConfigurationChanges = ConfigChanges.Orientation | ConfigChanges.ScreenSize)]
+ [Activity(Label = "ControlCatalog.Android", Theme = "@style/MyTheme.Main", Icon = "@drawable/icon", LaunchMode = LaunchMode.SingleTop, ConfigurationChanges = ConfigChanges.Orientation | ConfigChanges.ScreenSize | ConfigChanges.UiMode)]
public class MainActivity : AvaloniaMainActivity
{
}
diff --git a/samples/ControlCatalog.Android/Resources/values-night/colors.xml b/samples/ControlCatalog.Android/Resources/values-night/colors.xml
new file mode 100644
index 0000000000..3d47b6fc58
--- /dev/null
+++ b/samples/ControlCatalog.Android/Resources/values-night/colors.xml
@@ -0,0 +1,4 @@
+
+
+ #212121
+
diff --git a/src/Android/Avalonia.Android/AvaloniaMainActivity.cs b/src/Android/Avalonia.Android/AvaloniaMainActivity.cs
index eb4b6bf6a0..b2cd150933 100644
--- a/src/Android/Avalonia.Android/AvaloniaMainActivity.cs
+++ b/src/Android/Avalonia.Android/AvaloniaMainActivity.cs
@@ -32,10 +32,6 @@ namespace Avalonia.Android
{
lifetime.View = View;
}
-
- Window?.ClearFlags(WindowManagerFlags.TranslucentStatus);
- Window?.AddFlags(WindowManagerFlags.DrawsSystemBarBackgrounds);
-
base.OnCreate(savedInstanceState);
SetContentView(View);
diff --git a/src/Android/Avalonia.Android/Platform/AndroidInsetsManager.cs b/src/Android/Avalonia.Android/Platform/AndroidInsetsManager.cs
index 35d1b06e6a..549815a036 100644
--- a/src/Android/Avalonia.Android/Platform/AndroidInsetsManager.cs
+++ b/src/Android/Avalonia.Android/Platform/AndroidInsetsManager.cs
@@ -2,11 +2,10 @@
using System.Collections.Generic;
using Android.OS;
using Android.Views;
-using AndroidX.AppCompat.App;
using AndroidX.Core.View;
using Avalonia.Android.Platform.SkiaPlatform;
using Avalonia.Controls.Platform;
-using static Avalonia.Controls.Platform.IInsetsManager;
+using Avalonia.Media;
namespace Avalonia.Android.Platform
{
@@ -20,6 +19,7 @@ namespace Avalonia.Android.Platform
private bool? _systemUiVisibility;
private SystemBarTheme? _statusBarTheme;
private bool? _isDefaultSystemBarLightTheme;
+ private Color? _systemBarColor;
public event EventHandler SafeAreaChanged;
@@ -36,6 +36,16 @@ namespace Avalonia.Android.Platform
}
WindowCompat.SetDecorFitsSystemWindows(_activity.Window, !value);
+
+ if(value)
+ {
+ _activity.Window.AddFlags(WindowManagerFlags.TranslucentStatus);
+ _activity.Window.AddFlags(WindowManagerFlags.TranslucentNavigation);
+ }
+ else
+ {
+ SystemBarColor = _systemBarColor;
+ }
}
}
@@ -93,6 +103,7 @@ namespace Avalonia.Android.Platform
public WindowInsetsCompat OnApplyWindowInsets(View v, WindowInsetsCompat insets)
{
NotifySafeAreaChanged(SafeAreaPadding);
+ insets = ViewCompat.OnApplyWindowInsets(v, insets);
return insets;
}
@@ -146,8 +157,6 @@ namespace Avalonia.Android.Platform
compat.AppearanceLightStatusBars = value == Controls.Platform.SystemBarTheme.Light;
compat.AppearanceLightNavigationBars = value == Controls.Platform.SystemBarTheme.Light;
-
- AppCompatDelegate.DefaultNightMode = isDefault ? AppCompatDelegate.ModeNightFollowSystem : compat.AppearanceLightStatusBars ? AppCompatDelegate.ModeNightNo : AppCompatDelegate.ModeNightYes;
}
}
@@ -190,10 +199,36 @@ namespace Avalonia.Android.Platform
}
}
+ public Color? SystemBarColor
+ {
+ get => _systemBarColor;
+ set
+ {
+ _systemBarColor = value;
+
+ if (_systemBarColor is { } color && !_displayEdgeToEdge && _activity.Window != null)
+ {
+ _activity.Window.ClearFlags(WindowManagerFlags.TranslucentStatus);
+ _activity.Window.ClearFlags(WindowManagerFlags.TranslucentNavigation);
+ _activity.Window.AddFlags(WindowManagerFlags.DrawsSystemBarBackgrounds);
+
+ var androidColor = global::Android.Graphics.Color.Argb(color.A, color.R, color.G, color.B);
+ _activity.Window.SetStatusBarColor(androidColor);
+
+ if (Build.VERSION.SdkInt >= BuildVersionCodes.O)
+ {
+ // As we can only change the navigation bar's foreground api 26 and newer, we only change the background color if running on those versions
+ _activity.Window.SetNavigationBarColor(androidColor);
+ }
+ }
+ }
+ }
+
internal void ApplyStatusBarState()
{
IsSystemBarVisible = _systemUiVisibility;
SystemBarTheme = _statusBarTheme;
+ SystemBarColor = _systemBarColor;
}
private class InsetsAnimationCallback : WindowInsetsAnimationCompat.Callback
diff --git a/src/Android/Avalonia.Android/Platform/SkiaPlatform/TopLevelImpl.cs b/src/Android/Avalonia.Android/Platform/SkiaPlatform/TopLevelImpl.cs
index b8d80a50ff..4e783a0873 100644
--- a/src/Android/Avalonia.Android/Platform/SkiaPlatform/TopLevelImpl.cs
+++ b/src/Android/Avalonia.Android/Platform/SkiaPlatform/TopLevelImpl.cs
@@ -3,9 +3,13 @@ using System.Collections.Generic;
using Android.App;
using Android.Content;
using Android.Graphics;
+using Android.Graphics.Drawables;
+using Android.OS;
using Android.Runtime;
+using Android.Text;
using Android.Views;
using Android.Views.InputMethods;
+using AndroidX.AppCompat.App;
using Avalonia.Android.Platform.Specific;
using Avalonia.Android.Platform.Specific.Helpers;
using Avalonia.Android.Platform.Storage;
@@ -22,13 +26,6 @@ using Avalonia.Platform.Storage;
using Avalonia.Rendering;
using Avalonia.Rendering.Composition;
using Java.Lang;
-using Java.Util;
-using Math = System.Math;
-using AndroidRect = Android.Graphics.Rect;
-using Window = Android.Views.Window;
-using Android.Graphics.Drawables;
-using Android.OS;
-using Android.Text;
namespace Avalonia.Android.Platform.SkiaPlatform
{
@@ -286,6 +283,8 @@ namespace Avalonia.Android.Platform.SkiaPlatform
_ => null,
};
}
+
+ AppCompatDelegate.DefaultNightMode = themeVariant == PlatformThemeVariant.Light ? AppCompatDelegate.ModeNightNo : AppCompatDelegate.ModeNightYes;
}
public AcrylicPlatformCompensationLevels AcrylicCompensationLevels => new AcrylicPlatformCompensationLevels(1, 1, 1);
diff --git a/src/Avalonia.Controls/Platform/IInsetsManager.cs b/src/Avalonia.Controls/Platform/IInsetsManager.cs
index 072bace154..c604b89e5c 100644
--- a/src/Avalonia.Controls/Platform/IInsetsManager.cs
+++ b/src/Avalonia.Controls/Platform/IInsetsManager.cs
@@ -1,4 +1,5 @@
using System;
+using Avalonia.Media;
using Avalonia.Metadata;
#nullable enable
@@ -22,7 +23,12 @@ namespace Avalonia.Controls.Platform
/// Gets the current safe area padding.
///
Thickness SafeAreaPadding { get; }
-
+
+ ///
+ /// Gets or sets the color of the platform's system bars
+ ///
+ Color? SystemBarColor { get; set; }
+
///
/// Occurs when safe area for the current window changes.
///
diff --git a/src/Avalonia.Controls/TopLevel.cs b/src/Avalonia.Controls/TopLevel.cs
index bf0de1d79f..19ec9b9e0e 100644
--- a/src/Avalonia.Controls/TopLevel.cs
+++ b/src/Avalonia.Controls/TopLevel.cs
@@ -87,7 +87,15 @@ namespace Avalonia.Controls
///
public static readonly StyledProperty RequestedThemeVariantProperty =
ThemeVariantScope.RequestedThemeVariantProperty.AddOwner();
-
+
+ ///
+ /// Defines the SystemBarColor attached property.
+ ///
+ public static readonly AttachedProperty SystemBarColorProperty =
+ AvaloniaProperty.RegisterAttached(
+ "SystemBarColor",
+ inherits: true);
+
///
/// Defines the event.
///
@@ -124,6 +132,22 @@ namespace Avalonia.Controls
{
KeyboardNavigation.TabNavigationProperty.OverrideDefaultValue(KeyboardNavigationMode.Cycle);
AffectsMeasure(ClientSizeProperty);
+
+ SystemBarColorProperty.Changed.AddClassHandler((view, e) =>
+ {
+ if (e.NewValue is SolidColorBrush colorBrush)
+ {
+ if (view.Parent is TopLevel tl && tl.InsetsManager is { } insetsManager)
+ {
+ insetsManager.SystemBarColor = colorBrush.Color;
+ }
+
+ if (view is TopLevel topLevel && topLevel.InsetsManager is { } insets)
+ {
+ insets.SystemBarColor = colorBrush.Color;
+ }
+ }
+ });
}
///
@@ -379,6 +403,26 @@ namespace Avalonia.Controls
set { SetValue(AccessText.ShowAccessKeyProperty, value); }
}
+ ///
+ /// Helper for setting the color of the platform's system bars
+ ///
+ /// The main view attached to the toplevel, or the toplevel
+ /// The color to set
+ public static void SetSystemBarColor(Control control, SolidColorBrush? color)
+ {
+ control.SetValue(SystemBarColorProperty, color);
+ }
+
+ ///
+ /// Helper for getting the color of the platform's system bars
+ ///
+ /// The main view attached to the toplevel, or the toplevel
+ /// The current color of the platform's system bars
+ public static SolidColorBrush? GetSystemBarColor(Control control)
+ {
+ return control.GetValue(SystemBarColorProperty);
+ }
+
///
double ILayoutRoot.LayoutScaling => PlatformImpl?.RenderScaling ?? 1;
diff --git a/src/Avalonia.Themes.Fluent/Controls/EmbeddableControlRoot.xaml b/src/Avalonia.Themes.Fluent/Controls/EmbeddableControlRoot.xaml
index 6a2651e3f5..f60424a2dc 100644
--- a/src/Avalonia.Themes.Fluent/Controls/EmbeddableControlRoot.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/EmbeddableControlRoot.xaml
@@ -3,6 +3,7 @@
+
diff --git a/src/Avalonia.Themes.Fluent/Controls/Window.xaml b/src/Avalonia.Themes.Fluent/Controls/Window.xaml
index 35cc81663f..ff27cce800 100644
--- a/src/Avalonia.Themes.Fluent/Controls/Window.xaml
+++ b/src/Avalonia.Themes.Fluent/Controls/Window.xaml
@@ -3,6 +3,7 @@
+
diff --git a/src/Browser/Avalonia.Browser/BrowserInsetsManager.cs b/src/Browser/Avalonia.Browser/BrowserInsetsManager.cs
index 30f80ba27c..0f64003699 100644
--- a/src/Browser/Avalonia.Browser/BrowserInsetsManager.cs
+++ b/src/Browser/Avalonia.Browser/BrowserInsetsManager.cs
@@ -5,6 +5,7 @@ using System.Text;
using System.Threading.Tasks;
using Avalonia.Browser.Interop;
using Avalonia.Controls.Platform;
+using Avalonia.Media;
using static Avalonia.Controls.Platform.IInsetsManager;
namespace Avalonia.Browser
@@ -37,6 +38,8 @@ namespace Avalonia.Browser
}
}
+ public Color? SystemBarColor { get; set; }
+
public void NotifySafeAreaPaddingChanged()
{
SafeAreaChanged?.Invoke(this, new SafeAreaChangedArgs(SafeAreaPadding));
diff --git a/src/iOS/Avalonia.iOS/InsetsManager.cs b/src/iOS/Avalonia.iOS/InsetsManager.cs
index 62e560ddf9..bd6f989dbd 100644
--- a/src/iOS/Avalonia.iOS/InsetsManager.cs
+++ b/src/iOS/Avalonia.iOS/InsetsManager.cs
@@ -1,5 +1,6 @@
using System;
using Avalonia.Controls.Platform;
+using Avalonia.Media;
using UIKit;
namespace Avalonia.iOS;
@@ -80,4 +81,6 @@ internal class InsetsManager : IInsetsManager
}
public Thickness SafeAreaPadding => _controller?.SafeAreaPadding ?? default;
+
+ public Color? SystemBarColor { get; set; }
}