// This Source Code Form is subject to the terms of the MIT License.
// If a copy of the MIT was not distributed with this file, You can obtain one at https://opensource.org/licenses/MIT.
// Copyright (C) Leszek Pomianowski and WPF UI Contributors.
// All Rights Reserved.
using System.Runtime;
using System.Windows.Controls;
namespace WPFluent.Gallery.Controls;
public class PageControlDocumentation : Control
{
public static readonly DependencyProperty ShowProperty = DependencyProperty.RegisterAttached(
"Show",
typeof(bool),
typeof(PageControlDocumentation),
new FrameworkPropertyMetadata(true, FrameworkPropertyMetadataOptions.AffectsRender)
);
public static readonly DependencyProperty DocumentationTypeProperty = DependencyProperty.RegisterAttached(
"DocumentationType",
typeof(Type),
typeof(PageControlDocumentation),
new FrameworkPropertyMetadata(null)
);
/// Helper for getting from .
/// to read from.
/// Show property value.
[AttachedPropertyBrowsableForType(typeof(FrameworkElement))]
public static bool GetShow(FrameworkElement target) => (bool)target.GetValue(ShowProperty);
/// Helper for setting on .
/// to set on.
/// Show property value.
public static void SetShow(FrameworkElement target, bool show) => target.SetValue(ShowProperty, show);
/// Helper for getting from .
/// to read from.
/// DocumentationType property value.
[AttachedPropertyBrowsableForType(typeof(FrameworkElement))]
public static Type? GetDocumentationType(FrameworkElement target) =>
(Type?)target.GetValue(DocumentationTypeProperty);
/// Helper for setting on .
/// to set on.
/// DocumentationType property value.
public static void SetDocumentationType(FrameworkElement target, Type? type) =>
target.SetValue(DocumentationTypeProperty, type);
/// Identifies the dependency property.
public static readonly DependencyProperty NavigationViewProperty = DependencyProperty.Register(
nameof(NavigationView),
typeof(INavigationView),
typeof(PageControlDocumentation),
new FrameworkPropertyMetadata(null)
);
/// Identifies the dependency property.
public static readonly DependencyProperty IsDocumentationLinkVisibleProperty =
DependencyProperty.Register(
nameof(IsDocumentationLinkVisible),
typeof(Visibility),
typeof(PageControlDocumentation),
new FrameworkPropertyMetadata(Visibility.Collapsed)
);
/// Identifies the dependency property.
public static readonly DependencyProperty TemplateButtonCommandProperty = DependencyProperty.Register(
nameof(TemplateButtonCommand),
typeof(ICommand),
typeof(PageControlDocumentation),
new PropertyMetadata(null)
);
public INavigationView? NavigationView
{
get => (INavigationView?)GetValue(NavigationViewProperty);
set => SetValue(NavigationViewProperty, value);
}
public Visibility IsDocumentationLinkVisible
{
get => (Visibility)GetValue(IsDocumentationLinkVisibleProperty);
set => SetValue(IsDocumentationLinkVisibleProperty, value);
}
public ICommand TemplateButtonCommand => (ICommand)GetValue(TemplateButtonCommandProperty);
public PageControlDocumentation()
{
Loaded += static (sender, _) => ((PageControlDocumentation)sender).OnLoaded();
Unloaded += static (sender, _) => ((PageControlDocumentation)sender).OnUnloaded();
SetValue(
TemplateButtonCommandProperty,
new CommunityToolkit.Mvvm.Input.RelayCommand(OnClick)
);
}
private FrameworkElement? _page;
private void OnLoaded()
{
if (NavigationView is null)
{
throw new ArgumentNullException(nameof(NavigationView));
}
NavigationView.Navigated += NavigationViewOnNavigated;
}
private void OnUnloaded()
{
NavigationView!.Navigated -= NavigationViewOnNavigated;
_page = null;
}
private void NavigationViewOnNavigated(NavigationView sender, NavigatedEventArgs args)
{
SetCurrentValue(IsDocumentationLinkVisibleProperty, Visibility.Collapsed);
if (args.Page is not FrameworkElement page || !GetShow(page))
{
SetCurrentValue(VisibilityProperty, Visibility.Collapsed);
return;
}
_page = page;
SetCurrentValue(VisibilityProperty, Visibility.Visible);
if (GetDocumentationType(page) is not null)
{
SetCurrentValue(IsDocumentationLinkVisibleProperty, Visibility.Visible);
}
}
private void OnClick(string? param)
{
if (string.IsNullOrWhiteSpace(param) || _page is null)
{
return;
}
// TODO: Refactor switch
if (param == "theme")
{
SwitchThemes();
return;
}
string navigationUrl = param switch
{
"doc" when GetDocumentationType(_page) is { } documentationType => CreateUrlForDocumentation(
documentationType
),
//"xaml" => CreateUrlForGithub(_page.GetType(), ".xaml"),
//"c#" => CreateUrlForGithub(_page.GetType(), ".xaml.cs"),
_ => string.Empty,
};
if (string.IsNullOrEmpty(navigationUrl))
{
return;
}
try
{
ProcessStartInfo sInfo = new(navigationUrl) { UseShellExecute = true };
_ = Process.Start(sInfo);
}
catch (Exception e)
{
Debug.WriteLine(e);
}
}
//private static string CreateUrlForGithub(Type pageType, System.ReadOnlySpan fileExtension)
//{
// const string baseUrl = "https://github.com/lepoco/wpfui/tree/main/src/WPFluent.Gallery/";
// const string baseNamespace = "WPFluent.Gallery";
// ReadOnlySpan pageFullNameWithoutBaseNamespace = pageType.FullName.AsSpan()[
// (baseNamespace.Length + 1)..
// ];
// Span pageUrl = stackalloc char[pageFullNameWithoutBaseNamespace.Length];
// pageFullNameWithoutBaseNamespace.CopyTo(pageUrl);
// for (int i = 0; i < pageUrl.Length; i++)
// {
// if (pageUrl[i] == '.')
// {
// pageUrl[i] = '/';
// }
// }
// return string.Concat(baseUrl, pageUrl, fileExtension);
//}
private static string CreateUrlForDocumentation(Type type)
{
const string baseUrl = "https://wpfui.lepo.co/api/";
return string.Concat(baseUrl, type.FullName, ".html");
}
private static void SwitchThemes()
{
Appearance.ApplicationTheme currentTheme = WPFluent.Appearance.ApplicationThemeManager.GetAppTheme();
WPFluent.Appearance.ApplicationThemeManager.Apply(
currentTheme == WPFluent.Appearance.ApplicationTheme.Light
? WPFluent.Appearance.ApplicationTheme.Dark
: WPFluent.Appearance.ApplicationTheme.Light
);
}
}