Skip to content

Commit

Permalink
Navigation from experimental feature to the related page (#3595)
Browse files Browse the repository at this point in the history
  • Loading branch information
davidegiacometti authored Aug 22, 2024
1 parent 85ccc49 commit 1fbadf0
Show file tree
Hide file tree
Showing 9 changed files with 103 additions and 11 deletions.
19 changes: 18 additions & 1 deletion common/Models/ExperimentalFeature.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,11 @@
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using DevHome.Common.Contracts;
using DevHome.Common.Extensions;
using DevHome.Common.Services;
using DevHome.Common.TelemetryEvents;
using DevHome.Telemetry;
using Microsoft.UI.Xaml;

namespace DevHome.Common.Models;

Expand All @@ -21,6 +23,10 @@ public partial class ExperimentalFeature : ObservableObject

public string Id { get; init; }

public string OpenPageKey { get; init; }

public string OpenPageParameter { get; init; }

public bool NeedsFeaturePresenceCheck { get; init; }

public bool IsVisible { get; init; }
Expand All @@ -29,9 +35,11 @@ public partial class ExperimentalFeature : ObservableObject

public static IQuickstartSetupService? QuickstartSetupService { get; set; }

public ExperimentalFeature(string id, bool enabledByDefault, bool needsFeaturePresenceCheck, bool visible = true)
public ExperimentalFeature(string id, bool enabledByDefault, bool needsFeaturePresenceCheck, string openPageKey, string openPageParameter, bool visible = true)
{
Id = id;
OpenPageKey = openPageKey;
OpenPageParameter = openPageParameter;
_isEnabledByDefault = enabledByDefault;
NeedsFeaturePresenceCheck = needsFeaturePresenceCheck;
IsVisible = visible;
Expand Down Expand Up @@ -88,4 +96,13 @@ public async Task OnToggledAsync()
}
}
}

[RelayCommand]
public void Open()
{
if (OpenPageKey != null)
{
Application.Current.GetService<INavigationService>().NavigateTo(OpenPageKey, OpenPageParameter);
}
}
}
23 changes: 21 additions & 2 deletions settings/DevHome.Settings/Views/ExperimentalFeaturesPage.xaml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
xmlns:views="using:DevHome.Common.Views"
xmlns:models="using:DevHome.Common.Models"
xmlns:behaviors="using:DevHome.Common.Behaviors"
xmlns:ui="using:CommunityToolkit.WinUI"
behaviors:NavigationViewHeaderBehavior.HeaderTemplate="{StaticResource BreadcrumbBarDataTemplate}"
behaviors:NavigationViewHeaderBehavior.HeaderContext="{x:Bind ViewModel}">

Expand All @@ -27,12 +28,30 @@
Header="{x:Bind Name, Mode=OneWay}"
Description="{x:Bind Description, Mode=OneWay}"
Margin="{ThemeResource SettingsCardMargin}"
Visibility="{x:Bind IsVisible, Mode=OneWay}">
<ToggleSwitch IsOn="{x:Bind IsEnabled, Mode=OneWay}" Grid.Column="1">
Visibility="{x:Bind IsVisible, Mode=OneWay}"
IsClickEnabled="{x:Bind IsEnabled, Mode=OneWay}"
Command="{x:Bind OpenCommand}">
<ToggleSwitch
IsOn="{x:Bind IsEnabled, Mode=OneWay}"
Grid.Column="1">
<i:Interaction.Behaviors>
<ic:EventTriggerBehavior EventName="Toggled">
<ic:InvokeCommandAction Command="{x:Bind ToggledCommand}" />
</ic:EventTriggerBehavior>
<ic:DataTriggerBehavior
Binding="{x:Bind IsEnabled, Mode=OneWay}"
Value="False">
<ic:ChangePropertyAction
PropertyName="Margin"
Value="0,0,27,0" />
</ic:DataTriggerBehavior>
<ic:DataTriggerBehavior
Binding="{x:Bind IsEnabled, Mode=OneWay}"
Value="True">
<ic:ChangePropertyAction
PropertyName="Margin"
Value="0" />
</ic:DataTriggerBehavior>
</i:Interaction.Behaviors>
</ToggleSwitch>
</ctControls:SettingsCard>
Expand Down
12 changes: 12 additions & 0 deletions src/Helpers/NavConfig.cs
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,9 @@ internal sealed class ExperimentalFeatures

[JsonPropertyName("buildTypeOverrides")]
public BuildTypeOverrides[] BuildTypeOverrides { get; set; }

[JsonPropertyName("openPage")]
public OpenPage OpenPage { get; set; }
}

internal sealed class BuildTypeOverrides
Expand All @@ -82,6 +85,15 @@ internal sealed class BuildTypeOverrides
public bool Visible { get; set; }
}

internal sealed class OpenPage
{
[JsonPropertyName("key")]
public string Key { get; set; }

[JsonPropertyName("parameter")]
public string Parameter { get; set; }
}

// Uses .NET's JSON source generator support for serializing / deserializing NavConfig to get some perf gains at startup.
[JsonSourceGenerationOptions(WriteIndented = true)]
[JsonSerializable(typeof(NavConfig))]
Expand Down
22 changes: 18 additions & 4 deletions src/NavConfig.jsonc
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,10 @@
"enabledByDefault": false,
"visible": true
}
]
],
"openPage": {
"key": "DevHome.Customization.ViewModels.MainPageViewModel"
}
},
{
"identity": "FileExplorerSourceControlIntegration",
Expand All @@ -87,7 +90,11 @@
"enabledByDefault": false,
"visible": false
}
]
],
"openPage": {
"key": "DevHome.Customization.ViewModels.MainPageViewModel",
"parameter": "ShowFileExplorer"
}
},
{
"identity": "QuickstartPlayground",
Expand All @@ -108,7 +115,11 @@
"enabledByDefault": false,
"visible": true
}
]
],
"openPage": {
"key": "DevHome.SetupFlow.ViewModels.SetupFlowViewModel",
"parameter": "StartQuickstartPlayground"
}
},
{
"identity": "ProjectIronsidesExperiment",
Expand All @@ -129,7 +140,10 @@
"enabledByDefault": false,
"visible": true
}
]
],
"openPage": {
"key": "DevHome.Utilities.ViewModels.UtilitiesMainPageViewModel"
}
}
]
}
4 changes: 3 additions & 1 deletion src/Services/PageService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,8 @@ where assembly.GetName().Name == tool.Assembly
{
var enabledByDefault = experimentalFeature.EnabledByDefault;
var needsFeaturePresenceCheck = experimentalFeature.NeedsFeaturePresenceCheck;
var openPageKey = experimentalFeature.OpenPage.Key;
var openPageParameter = experimentalFeature.OpenPage.Parameter;
var isVisible = true;
foreach (var buildTypeOverride in experimentalFeature.BuildTypeOverrides ?? Array.Empty<DevHome.Helpers.BuildTypeOverrides>())
{
Expand All @@ -68,7 +70,7 @@ where assembly.GetName().Name == tool.Assembly
}
}

experimentationService.AddExperimentalFeature(new ExperimentalFeature(experimentalFeature.Identity, enabledByDefault, needsFeaturePresenceCheck, isVisible));
experimentationService.AddExperimentalFeature(new ExperimentalFeature(experimentalFeature.Identity, enabledByDefault, needsFeaturePresenceCheck, openPageKey, openPageParameter, isVisible));
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ private async Task LaunchWindowsDeveloperSettings()
}

[RelayCommand]
private void NavigateToFileExplorerPage()
public void NavigateToFileExplorerPage()
{
_navigationService.NavigateTo(typeof(FileExplorerViewModel).FullName!);
}
Expand Down
17 changes: 17 additions & 0 deletions tools/Customization/DevHome.Customization/Views/MainPage.xaml.cs
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

using System;
using DevHome.Common.Extensions;
using DevHome.Common.Views;
using DevHome.Customization.ViewModels;
using Microsoft.UI.Dispatching;
using Microsoft.UI.Xaml;
using Microsoft.UI.Xaml.Navigation;

namespace DevHome.Customization.Views;

Expand All @@ -20,4 +23,18 @@ public MainPage()
ViewModel = Application.Current.GetService<MainPageViewModel>();
InitializeComponent();
}

protected override void OnNavigatedTo(NavigationEventArgs e)
{
base.OnNavigatedTo(e);

if (e.NavigationMode != NavigationMode.Back)
{
var parameter = e.Parameter?.ToString();
if (parameter != null && parameter.Equals("ShowFileExplorer", StringComparison.OrdinalIgnoreCase))
{
Application.Current.GetService<DispatcherQueue>().TryEnqueue(ViewModel.NavigateToFileExplorerPage);
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -278,7 +278,7 @@ private void StartRepoConfig(string flowTitle)
}

[RelayCommand]
private void StartQuickstart(string flowTitle)
public void StartQuickstart(string flowTitle)
{
_log.Information("Starting flow for developer quickstart playground");
StartSetupFlowForTaskGroups(flowTitle, "DeveloperQuickstartPlayground", _host.GetService<DeveloperQuickstartTaskGroup>());
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,23 +25,26 @@ public partial class SetupFlowViewModel : ObservableObject
{
private readonly ILogger _log = Log.ForContext("SourceContext", nameof(SetupFlowViewModel));
private readonly IHost _host;
private readonly ISetupFlowStringResource _stringResource;
private readonly MainPageViewModel _mainPageViewModel;
private readonly PackageProvider _packageProvider;

private readonly string _creationFlowNavigationParameter = "StartCreationFlow";

private readonly string _configurationFlowNavigationParameter = "StartConfigurationFlow";
private readonly string _quickstartNavigationParameter = "StartQuickstartPlayground";

public SetupFlowOrchestrator Orchestrator { get; }

public event EventHandler EndSetupFlow = (s, e) => { };

public SetupFlowViewModel(
IHost host,
ISetupFlowStringResource stringResource,
SetupFlowOrchestrator orchestrator,
PackageProvider packageProvider)
{
_host = host;
_stringResource = stringResource;
Orchestrator = orchestrator;
_packageProvider = packageProvider;

Expand Down Expand Up @@ -158,6 +161,14 @@ public void OnNavigatedTo(NavigationEventArgs args)
Cancel();
StartCreationFlow(originPage: parameters[1]);
}
else if ((!string.IsNullOrEmpty(parameter)) &&
parameter.Contains(_quickstartNavigationParameter, StringComparison.OrdinalIgnoreCase))
{
Cancel();
Orchestrator.FlowPages = [_mainPageViewModel];
var flowTitle = _stringResource.GetLocalized("MainPage_QuickstartPlayground/Header");
_mainPageViewModel.StartQuickstart(flowTitle);
}
else if (args.Parameter is object[] configObjs && configObjs.Length == 3)
{
if (configObjs[0] is string configObj && configObj.Equals(_configurationFlowNavigationParameter, StringComparison.OrdinalIgnoreCase))
Expand Down

0 comments on commit 1fbadf0

Please sign in to comment.