Skip to content

Commit

Permalink
Introduce FontSizeMode for different behavior
Browse files Browse the repository at this point in the history
  • Loading branch information
GeertvanHorrik committed Oct 16, 2024
1 parent afcf8ee commit f8b3e91
Show file tree
Hide file tree
Showing 6 changed files with 122 additions and 19 deletions.
9 changes: 6 additions & 3 deletions src/Orc.Theming.Example/Views/MainWindow.xaml
Original file line number Diff line number Diff line change
Expand Up @@ -16,10 +16,13 @@

<StackPanel Grid.Row="0"
Orientation="Horizontal">
<orctheming:BaseColorSchemeSwitcherView />
<StackPanel>
<orctheming:AccentColorSwitcherView />
<orctheming:FontSizeSwitcherView />
<orctheming:BaseColorSchemeSwitcherView />
</StackPanel>

<orctheming:BaseColorSchemeSwitcherWithIconView />
<orctheming:AccentColorSwitcherView />
<orctheming:FontSizeSwitcherView />
</StackPanel>

<TabControl x:Name="TabControl" Grid.Row="1">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -147,6 +147,8 @@ namespace Orc.Theming
public FontSize() { }
[System.Windows.Markup.ConstructorArgument("delta")]
public double? Delta { get; set; }
[System.Windows.Markup.ConstructorArgument("mode")]
public Orc.Theming.FontSizeMode Mode { get; set; }
[System.Windows.Markup.ConstructorArgument("scale")]
public double? Scale { get; set; }
[System.Windows.Markup.ConstructorArgument("subscribeToEvents")]
Expand All @@ -155,6 +157,14 @@ namespace Orc.Theming
protected override void OnTargetObjectUnloaded() { }
protected override object? ProvideDynamicValue(System.IServiceProvider? serviceProvider) { }
}
public enum FontSizeMode
{
Default = 1,
TextBlockMetadata = 1,
Service = 2,
Parent = 3,
Resource = 4,
}
public class FontSizeService : Orc.Theming.IFontSizeService
{
public FontSizeService() { }
Expand Down
91 changes: 75 additions & 16 deletions src/Orc.Theming/Markup/FontSize.cs
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ public FontSize()
{
Scale = 1.0d;
SubscribeToEvents = false;
Mode = FontSizeMode.Default;
}

/// <summary>
Expand All @@ -45,6 +46,12 @@ public FontSize()
[ConstructorArgument("delta")]
public double? Delta { get; set; }

/// <summary>
/// Gets or sets the mode
/// </summary>
[ConstructorArgument("mode")]
public FontSizeMode Mode { get; set; }

/// <summary>
/// Gets or sets whether this markup extension should subscribe to events to be responsive.
/// <para />
Expand All @@ -58,13 +65,26 @@ public FontSize()
{
var defaultFontSize = 12d;

if (TargetObject is DependencyObject dependencyObject)
switch (Mode)
{
var parentControl = dependencyObject.GetLogicalParent()?.FindLogicalAncestorByType<Control>();
if (parentControl is not null)
{
defaultFontSize = (double)parentControl.GetValue(Control.FontSizeProperty);
}
case FontSizeMode.TextBlockMetadata:
defaultFontSize = GetFontSizeFromTextBlockMetadata();
break;

case FontSizeMode.Parent:
defaultFontSize = GetFontSizeFromParent();
break;

case FontSizeMode.Service:
defaultFontSize = GetFontSizeFromService();
break;

case FontSizeMode.Resource:
defaultFontSize = GetFontSizeFromResource();
break;

default:
throw Log.ErrorAndCreateException<NotSupportedException>($"Mode '{Mode}' is not supported");
}

var finalFontSize = defaultFontSize;
Expand All @@ -82,22 +102,50 @@ public FontSize()
return finalFontSize;
}

protected override void OnTargetObjectLoaded()
private double GetFontSizeFromTextBlockMetadata()
{
base.OnTargetObjectLoaded();
var defaultValue = (double)TextBlock.FontSizeProperty.GetMetadata(typeof(TextBlock)).DefaultValue;
return defaultValue;
}

if (SubscribeToEvents)
private double GetFontSizeFromParent()
{
var defaultFontSize = 12d;

if (TargetObject is DependencyObject dependencyObject)
{
var fontSizeService = _fontSizeService;
if (fontSizeService is null)
var parentControl = dependencyObject.GetLogicalParent()?.FindLogicalAncestorByType<Control>();
if (parentControl is not null)
{
_fontSizeService = fontSizeService = ServiceLocator.Default.ResolveType<IFontSizeService>();
defaultFontSize = (double)parentControl.GetValue(Control.FontSizeProperty);
}
}

if (fontSizeService is not null)
{
fontSizeService.FontSizeChanged += OnFontSizeServiceFontSizeChanged;
}
return defaultFontSize;
}

private double GetFontSizeFromService()
{
var service = GetFontSizeService();
return service.GetFontSize();
}

private double GetFontSizeFromResource()
{
// TODO: Based on discussion and performance, we consider
// resolving "fixed resources" based on the properties (e.g. Delta=4 resolves to Heading2)

throw Log.ErrorAndCreateException<NotImplementedException>("Reserved for future usage");
}

protected override void OnTargetObjectLoaded()
{
base.OnTargetObjectLoaded();

if (SubscribeToEvents)
{
var fontSizeService = GetFontSizeService();
fontSizeService.FontSizeChanged += OnFontSizeServiceFontSizeChanged;
}
}

Expand All @@ -112,6 +160,17 @@ protected override void OnTargetObjectUnloaded()
base.OnTargetObjectUnloaded();
}

private IFontSizeService GetFontSizeService()
{
var fontSizeService = _fontSizeService;
if (fontSizeService is null)
{
_fontSizeService = fontSizeService = ServiceLocator.Default.ResolveRequiredType<IFontSizeService>();
}

return fontSizeService;
}

private void OnFontSizeServiceFontSizeChanged(object? sender, EventArgs e)
{
UpdateValue();
Expand Down
15 changes: 15 additions & 0 deletions src/Orc.Theming/Markup/FontSizeMode.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
namespace Orc.Theming
{
public enum FontSizeMode
{
Default = TextBlockMetadata,

TextBlockMetadata = 1,

Service = 2,

Parent = 3,

Resource = 4
}
}
11 changes: 11 additions & 0 deletions src/Orc.Theming/Services/FontSizeService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
using System;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using Catel.Logging;

public class FontSizeService : IFontSizeService
Expand Down Expand Up @@ -44,6 +45,16 @@ public virtual bool SetFontSize(double fontSize)
TextBlock.SetFontSize(mainWindow, fontSize);
}

try
{
TextElement.FontSizeProperty.OverrideMetadata(typeof(TextElement), new FrameworkPropertyMetadata(fontSize));
TextBlock.FontSizeProperty.OverrideMetadata(typeof(TextBlock), new FrameworkPropertyMetadata(fontSize));
}
catch (Exception ex)
{
Log.Error(ex, "Failed to apply font size");
}

RaiseFontSizeChanged();

return true;
Expand Down
5 changes: 5 additions & 0 deletions src/Orc.Theming/ViewModels/FontSizeSwitcherViewModel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,11 @@ private void OnFontSizeServiceFontSizeChanged(object? sender, EventArgs e)

private void OnSelectedFontSizeChanged()
{
if (!IsInitialized)
{
return;
}

_fontSizeService.SetFontSize(SelectedFontSize);
}
}

0 comments on commit f8b3e91

Please sign in to comment.