Skip to content
28 changes: 22 additions & 6 deletions src/Files.App/Data/Items/NavigationBarSuggestionItem.cs
Original file line number Diff line number Diff line change
@@ -1,17 +1,22 @@
// Copyright (c) Files Community
// Licensed under the MIT License.

using Files.App.Controls;
using Microsoft.UI.Xaml;

namespace Files.App.Data.Items
{
[Obsolete("Remove once Omnibar goes out of experimental.")]
public sealed partial class NavigationBarSuggestionItem : ObservableObject
public sealed partial class NavigationBarSuggestionItem : ObservableObject, IOmnibarTextMemberPathProvider
{
private Style? _ThemedIconStyle;
public Style? ThemedIconStyle { get => _ThemedIconStyle; set => SetProperty(ref _ThemedIconStyle, value); }

private string? _Glyph;
public string? Glyph { get => _Glyph; set => SetProperty(ref _Glyph, value); }

private string? _Text;
public string? Text
{
get => _Text;
set => SetProperty(ref _Text, value);
}
public string? Text { get => _Text; set => SetProperty(ref _Text, value); }

private string? _PrimaryDisplay;
public string? PrimaryDisplay
Expand Down Expand Up @@ -88,5 +93,16 @@ private void UpdatePrimaryDisplay()
}
}
}

public string GetTextMemberPath(string textMemberPath)
{
return textMemberPath switch
{
nameof(Text) => Text,
nameof(PrimaryDisplay) => PrimaryDisplay,
nameof(SearchText) => SearchText,
_ => string.Empty
};
}
}
}
89 changes: 49 additions & 40 deletions src/Files.App/UserControls/NavigationToolbar.xaml
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
<!-- Copyright (c) Files Community. Licensed under the MIT License. -->
<UserControl
x:Class="Files.App.UserControls.NavigationToolbar"
Expand Down Expand Up @@ -27,6 +27,7 @@
<UserControl.Resources>
<ResourceDictionary>
<converters:NullToTrueConverter x:Key="NullToFalseConverter" Inverse="True" />
<converters:NullToVisibilityCollapsedConverter x:Key="NullToVisibilityCollapsedConverter" />
<converters1:BoolNegationConverter x:Key="BoolNegationConverter" />

<ResourceDictionary.MergedDictionaries>
Expand Down Expand Up @@ -367,42 +368,50 @@
IconOnActive="{controls:ThemedIconMarkup Style={StaticResource App.ThemedIcons.Omnibar.Commands}, IsFilled=True}"
IconOnInactive="{controls:ThemedIconMarkup Style={StaticResource App.ThemedIcons.Omnibar.Commands}, IconType=Outline}"
ModeName="{x:Bind Commands.OpenCommandPalette.LabelWithHotKey, Mode=OneWay}"
PlaceholderText="{helpers:ResourceString Name=OmnibarCommandPaletteModeTextPlaceholder}">
<!--<controls:OmnibarMode.SuggestionItemTemplate>
<DataTemplate x:DataType="data:OmnibarPaletteSuggestionItem">
<Grid Height="48" ColumnSpacing="12">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<controls:ThemedIcon
Width="20"
Height="20"
VerticalAlignment="Center"
Style="{StaticResource App.ThemedIcons.Actions.Copying}" />
<StackPanel Grid.Column="1" VerticalAlignment="Center">
<TextBlock
Style="{StaticResource BodyStrongTextBlockStyle}"
Text="{x:Bind Title}"
TextTrimming="CharacterEllipsis"
TextWrapping="NoWrap" />
<TextBlock
Foreground="{ThemeResource TextFillColorSecondaryBrush}"
Style="{StaticResource CaptionTextBlockStyle}"
Text="{x:Bind Description}"
TextTrimming="CharacterEllipsis"
TextWrapping="NoWrap" />
</StackPanel>
<StackPanel Grid.Column="2" VerticalAlignment="Center">
PlaceholderText="{helpers:ResourceString Name=OmnibarCommandPaletteModeTextPlaceholder}"
SuggestionItemsSource="{x:Bind ViewModel.OmnibarCommandPaletteModeSuggestionItems, Mode=OneWay}"
Text="{x:Bind ViewModel.OmnibarCommandPaletteModeText, Mode=TwoWay}"
TextMemberPath="Text"
UpdateTextOnSelect="False">
<controls:OmnibarMode.SuggestionItemTemplate>
<DataTemplate x:DataType="dataitems:NavigationBarSuggestionItem">
<Grid ColumnSpacing="12">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="16" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>

<Grid Grid.Column="0">
<Viewbox
Width="16"
Height="16"
Visibility="{x:Bind Glyph, Converter={StaticResource NullToVisibilityCollapsedConverter}}">
<FontIcon Foreground="{ThemeResource App.Theme.IconBaseBrush}" Glyph="{x:Bind Glyph}" />
</Viewbox>
<controls:ThemedIcon Style="{x:Bind ThemedIconStyle}" Visibility="{x:Bind ThemedIconStyle, Converter={StaticResource NullToVisibilityCollapsedConverter}}" />
</Grid>

<!-- Primary Title -->
<TextBlock
Text="{x:Bind HotKeys}"
x:Name="PrimaryDisplayBlock"
Grid.Column="1"
VerticalAlignment="Center"
Foreground="{ThemeResource TextFillColorPrimaryBrush}"
TextTrimming="CharacterEllipsis"
TextWrapping="NoWrap" />
</StackPanel>
</Grid>
</DataTemplate>
</controls:OmnibarMode.SuggestionItemTemplate>-->
TextWrapping="NoWrap">
<Run FontWeight="Normal" Text="{x:Bind PrimaryDisplayPreMatched, Mode=OneWay}" /><Run FontWeight="Bold" Text="{x:Bind PrimaryDisplayMatched, Mode=OneWay}" /><Run FontWeight="Normal" Text="{x:Bind PrimaryDisplayPostMatched, Mode=OneWay}" />
</TextBlock>

<!-- Keyboard Shortcuts -->
<keyboard:KeyboardShortcut
x:Name="RightAlignedKeyboardShortcut"
Grid.Column="2"
VerticalAlignment="Center"
HotKeys="{x:Bind HotKeys}" />
</Grid>
</DataTemplate>
</controls:OmnibarMode.SuggestionItemTemplate>
</controls:OmnibarMode>

<controls:OmnibarMode
Expand Down Expand Up @@ -467,12 +476,12 @@
<Grid Margin="-16">

<!-- Enable icon again if we add option to always display on the toolbar
<ThemedIcon
x:Name="StatusCenterIcon"
Width="16"
Height="16"
x:Load="{x:Bind OngoingTasksViewModel.HasAnyItemInProgress, Converter={StaticResource BoolNegationConverter}, Mode=OneWay}"
Style="{StaticResource App.ThemedIcons.StatusCenter}" />-->
<ThemedIcon
x:Name="StatusCenterIcon"
Width="16"
Height="16"
x:Load="{x:Bind OngoingTasksViewModel.HasAnyItemInProgress, Converter={StaticResource BoolNegationConverter}, Mode=OneWay}"
Style="{StaticResource App.ThemedIcons.StatusCenter}" />-->

<ProgressRing
x:Name="MedianOperationProgressRing"
Expand Down
52 changes: 47 additions & 5 deletions src/Files.App/UserControls/NavigationToolbar.xaml.cs
Original file line number Diff line number Diff line change
Expand Up @@ -256,19 +256,61 @@ private void ClickablePath_GettingFocus(UIElement sender, GettingFocusEventArgs

private async void Omnibar_QuerySubmitted(Omnibar sender, OmnibarQuerySubmittedEventArgs args)
{
await ViewModel.HandleItemNavigationAsync(args.Text);
if (Omnibar.CurrentSelectedMode == OmnibarPathMode)
{
await ViewModel.HandleItemNavigationAsync(args.Text);
}
else if (Omnibar.CurrentSelectedMode == OmnibarCommandPaletteMode)
{
}
else if (Omnibar.CurrentSelectedMode == OmnibarSearchMode)
{
}
}

private async void Omnibar_SuggestionChosen(Omnibar sender, OmnibarSuggestionChosenEventArgs args)
{
if (args.SelectedItem is OmnibarPathModeSuggestionModel item &&
!string.IsNullOrEmpty(item.Path))
await ViewModel.HandleItemNavigationAsync(item.Path);
if (Omnibar.CurrentSelectedMode == OmnibarPathMode)
{
if (args.SelectedItem is OmnibarPathModeSuggestionModel item &&
!string.IsNullOrEmpty(item.Path))
await ViewModel.HandleItemNavigationAsync(item.Path);
}
else if (Omnibar.CurrentSelectedMode == OmnibarCommandPaletteMode)
{
if (args.SelectedItem is not NavigationBarSuggestionItem item || item.Text is not { } commandText)
return;

var command = Commands[commandText];
if (command == Commands.None)
await DialogDisplayHelper.ShowDialogAsync(Strings.InvalidCommand.GetLocalizedResource(),
string.Format(Strings.InvalidCommandContent.GetLocalizedResource(), commandText));
else if (!command.IsExecutable)
await DialogDisplayHelper.ShowDialogAsync(Strings.CommandNotExecutable.GetLocalizedResource(),
string.Format(Strings.CommandNotExecutableContent.GetLocalizedResource(), command.Code));
else
await command.ExecuteAsync();

Omnibar.ChangeMode(OmnibarPathMode);
}
else if (Omnibar.CurrentSelectedMode == OmnibarSearchMode)
{
}
}

private async void Omnibar_TextChanged(Omnibar sender, OmnibarTextChangedEventArgs args)
{
await ViewModel.PopulateOmnibarSuggestionsForPathMode();
if (Omnibar.CurrentSelectedMode == OmnibarPathMode)
{
await ViewModel.PopulateOmnibarSuggestionsForPathMode();
}
else if (Omnibar.CurrentSelectedMode == OmnibarCommandPaletteMode)
{
ViewModel.PopulateOmnibarSuggestionsForCommandPaletteMode();
}
else if (Omnibar.CurrentSelectedMode == OmnibarSearchMode)
{
}
}

private async void BreadcrumbBar_ItemClicked(Controls.BreadcrumbBar sender, Controls.BreadcrumbBarItemClickedEventArgs args)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,8 @@ public sealed partial class NavigationToolbarViewModel : ObservableObject, IAddr

internal ObservableCollection<OmnibarPathModeSuggestionModel> PathModeSuggestionItems { get; } = [];

internal ObservableCollection<NavigationBarSuggestionItem> OmnibarCommandPaletteModeSuggestionItems { get; } = [];

public bool IsSingleItemOverride { get; set; }

public bool SearchHasFocus { get; private set; }
Expand Down Expand Up @@ -218,6 +220,8 @@ public string? PathText
}
}

private string? _OmnibarCommandPaletteModeText;
public string? OmnibarCommandPaletteModeText { get => _OmnibarCommandPaletteModeText; set => SetProperty(ref _OmnibarCommandPaletteModeText, value); }

private bool _IsOmnibarFocused;
public bool IsOmnibarFocused
Expand All @@ -239,6 +243,8 @@ public bool IsOmnibarFocused
_ = PopulateOmnibarSuggestionsForPathMode();
break;
case OmnibarPaletteModeName:
if (OmnibarCommandPaletteModeSuggestionItems.Count is 0)
PopulateOmnibarSuggestionsForCommandPaletteMode();
break;
case OmnibarSearchModeName:
break;
Expand Down Expand Up @@ -1126,6 +1132,30 @@ void AddNoResultsItem()
}
}

public void PopulateOmnibarSuggestionsForCommandPaletteMode()
{
OmnibarCommandPaletteModeText ??= string.Empty;
OmnibarCommandPaletteModeSuggestionItems.Clear();

var suggestionItems = Commands.Where(command =>
command.IsExecutable &&
command.IsAccessibleGlobally &&
(command.Description.Contains(OmnibarCommandPaletteModeText, StringComparison.OrdinalIgnoreCase) ||
command.Code.ToString().Contains(OmnibarCommandPaletteModeText, StringComparison.OrdinalIgnoreCase)))
.Select(command => new NavigationBarSuggestionItem()
{
ThemedIconStyle = command.Glyph.ToThemedIconStyle(),
Glyph = command.Glyph.BaseGlyph,
Text = command.Code.ToString(),
PrimaryDisplay = command.Description,
HotKeys = command.HotKeys,
SearchText = OmnibarCommandPaletteModeText,
});

foreach (var item in suggestionItems)
OmnibarCommandPaletteModeSuggestionItems.Add(item);
}

[Obsolete("Remove once Omnibar goes out of experimental.")]
public async Task SetAddressBarSuggestionsAsync(AutoSuggestBox sender, IShellPage shellpage)
{
Expand Down
Loading