Skip to content

Commit 2ebb917

Browse files
committed
Init
1 parent 415c6ba commit 2ebb917

21 files changed

+478
-566
lines changed

src/Files.App.CsWin32/NativeMethods.txt

+4
Original file line numberDiff line numberDiff line change
@@ -156,3 +156,7 @@ IApplicationDestinations
156156
ApplicationDestinations
157157
IApplicationDocumentLists
158158
ApplicationDocumentLists
159+
BHID_EnumItems
160+
BHID_SFUIObject
161+
IContextMenu
162+
CMF_OPTIMIZEFORINVOKE

src/Files.App.CsWin32/Windows.Win32.ComPtr.cs

+3-2
Original file line numberDiff line numberDiff line change
@@ -39,10 +39,11 @@ public ComPtr(T* ptr)
3939
}
4040

4141
[MethodImpl(MethodImplOptions.AggressiveInlining)]
42-
public readonly ComPtr<U> As<U>(Guid riid) where U : unmanaged
42+
public readonly ComPtr<U> As<U>() where U : unmanaged
4343
{
4444
ComPtr<U> pNewPtr = default;
45-
((IUnknown*)_ptr)->QueryInterface(&riid, (void**)pNewPtr.GetAddressOf());
45+
Guid uuid = typeof(U).GUID;
46+
((IUnknown*)_ptr)->QueryInterface(&uuid, (void**)pNewPtr.GetAddressOf());
4647
return pNewPtr;
4748
}
4849

src/Files.App/Actions/Sidebar/PinFolderToSidebarAction.cs

+14-19
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
// Copyright (c) 2024 Files Community
22
// Licensed under the MIT License. See the LICENSE.
33

4-
using Windows.Storage;
4+
using System.Collections.Specialized;
55

66
namespace Files.App.Actions
77
{
88
internal sealed class PinFolderToSidebarAction : ObservableObject, IAction
99
{
10-
private readonly IContentPageContext context;
11-
private readonly IQuickAccessService service;
10+
private readonly IContentPageContext context = Ioc.Default.GetRequiredService<IContentPageContext>();
11+
private readonly IQuickAccessService service = Ioc.Default.GetRequiredService<IQuickAccessService>();
1212

1313
public string Label
1414
=> "PinFolderToSidebar".GetLocalizedResource();
@@ -24,30 +24,25 @@ public bool IsExecutable
2424

2525
public PinFolderToSidebarAction()
2626
{
27-
context = Ioc.Default.GetRequiredService<IContentPageContext>();
28-
service = Ioc.Default.GetRequiredService<IQuickAccessService>();
29-
3027
context.PropertyChanged += Context_PropertyChanged;
31-
App.QuickAccessManager.UpdateQuickAccessWidget += QuickAccessManager_DataChanged;
28+
service.PinnedFoldersChanged += QuickAccessService_CollectionChanged;
3229
}
3330

3431
public async Task ExecuteAsync(object? parameter = null)
3532
{
36-
if (context.HasSelection)
37-
{
38-
var items = context.SelectedItems.Select(x => x.ItemPath).ToArray();
33+
var items = context.HasSelection
34+
? context.SelectedItems.Select(x => x.ItemPath).ToArray()
35+
: context.Folder is not null
36+
? [context.Folder.ItemPath]
37+
: null;
3938

40-
await service.PinToSidebarAsync(items);
41-
}
42-
else if (context.Folder is not null)
43-
{
44-
await service.PinToSidebarAsync(context.Folder.ItemPath);
45-
}
39+
if (items is not null)
40+
await service.PinFolderAsync(items);
4641
}
4742

4843
private bool GetIsExecutable()
4944
{
50-
string[] pinnedFolders = [.. App.QuickAccessManager.Model.PinnedFolders];
45+
string[] pinnedFolders = [.. service.PinnedFolders.Select(x => x.Path)];
5146

5247
return context.HasSelection
5348
? context.SelectedItems.All(IsPinnable)
@@ -56,7 +51,7 @@ private bool GetIsExecutable()
5651
bool IsPinnable(ListedItem item)
5752
{
5853
return
59-
item.PrimaryItemAttribute is StorageItemTypes.Folder &&
54+
item.PrimaryItemAttribute is Windows.Storage.StorageItemTypes.Folder &&
6055
!pinnedFolders.Contains(item.ItemPath);
6156
}
6257
}
@@ -72,7 +67,7 @@ private void Context_PropertyChanged(object? sender, PropertyChangedEventArgs e)
7267
}
7368
}
7469

75-
private void QuickAccessManager_DataChanged(object? sender, ModifyQuickAccessEventArgs e)
70+
private void QuickAccessService_CollectionChanged(object? sender, NotifyCollectionChangedEventArgs e)
7671
{
7772
OnPropertyChanged(nameof(IsExecutable));
7873
}

src/Files.App/Actions/Sidebar/UnpinFolderToSidebarAction.cs

+15-17
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,14 @@
11
// Copyright (c) 2024 Files Community
22
// Licensed under the MIT License. See the LICENSE.
33

4+
using System.Collections.Specialized;
5+
46
namespace Files.App.Actions
57
{
68
internal sealed class UnpinFolderFromSidebarAction : ObservableObject, IAction
79
{
8-
private readonly IContentPageContext context;
9-
private readonly IQuickAccessService service;
10+
private readonly IContentPageContext context = Ioc.Default.GetRequiredService<IContentPageContext>();
11+
private readonly IQuickAccessService service = Ioc.Default.GetRequiredService<IQuickAccessService>();
1012

1113
public string Label
1214
=> "UnpinFolderFromSidebar".GetLocalizedResource();
@@ -22,29 +24,25 @@ public bool IsExecutable
2224

2325
public UnpinFolderFromSidebarAction()
2426
{
25-
context = Ioc.Default.GetRequiredService<IContentPageContext>();
26-
service = Ioc.Default.GetRequiredService<IQuickAccessService>();
27-
2827
context.PropertyChanged += Context_PropertyChanged;
29-
App.QuickAccessManager.UpdateQuickAccessWidget += QuickAccessManager_DataChanged;
28+
service.PinnedFoldersChanged += QuickAccessService_CollectionChanged;
3029
}
3130

3231
public async Task ExecuteAsync(object? parameter = null)
3332
{
34-
if (context.HasSelection)
35-
{
36-
var items = context.SelectedItems.Select(x => x.ItemPath).ToArray();
37-
await service.UnpinFromSidebarAsync(items);
38-
}
39-
else if (context.Folder is not null)
40-
{
41-
await service.UnpinFromSidebarAsync(context.Folder.ItemPath);
42-
}
33+
var items = context.HasSelection
34+
? context.SelectedItems.Select(x => x.ItemPath).ToArray()
35+
: context.Folder is not null
36+
? [context.Folder.ItemPath]
37+
: null;
38+
39+
if (items is not null)
40+
await service.UnpinFolderAsync(items);
4341
}
4442

4543
private bool GetIsExecutable()
4644
{
47-
string[] pinnedFolders = [.. App.QuickAccessManager.Model.PinnedFolders];
45+
string[] pinnedFolders = [.. service.PinnedFolders.Select(x => x.Path)];
4846

4947
return context.HasSelection
5048
? context.SelectedItems.All(IsPinned)
@@ -67,7 +65,7 @@ private void Context_PropertyChanged(object? sender, PropertyChangedEventArgs e)
6765
}
6866
}
6967

70-
private void QuickAccessManager_DataChanged(object? sender, ModifyQuickAccessEventArgs e)
68+
private void QuickAccessService_CollectionChanged(object? sender, NotifyCollectionChangedEventArgs e)
7169
{
7270
OnPropertyChanged(nameof(IsExecutable));
7371
}

src/Files.App/App.xaml.cs

-2
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,6 @@ public static CommandBarFlyout? LastOpenedFlyout
3636
}
3737

3838
// TODO: Replace with DI
39-
public static QuickAccessManager QuickAccessManager { get; private set; } = null!;
4039
public static StorageHistoryWrapper HistoryWrapper { get; private set; } = null!;
4140
public static FileTagsManager FileTagsManager { get; private set; } = null!;
4241
public static LibraryManager LibraryManager { get; private set; } = null!;
@@ -110,7 +109,6 @@ async Task ActivateAsync()
110109
}
111110

112111
// TODO: Replace with DI
113-
QuickAccessManager = Ioc.Default.GetRequiredService<QuickAccessManager>();
114112
HistoryWrapper = Ioc.Default.GetRequiredService<StorageHistoryWrapper>();
115113
FileTagsManager = Ioc.Default.GetRequiredService<FileTagsManager>();
116114
LibraryManager = Ioc.Default.GetRequiredService<LibraryManager>();

src/Files.App/Data/Contexts/SideBar/SideBarContext.cs

+2-8
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,7 @@ namespace Files.App.Data.Contexts
66
/// <inheritdoc cref="ISidebarContext"/>
77
internal sealed class SidebarContext : ObservableObject, ISidebarContext
88
{
9-
private readonly PinnedFoldersManager favoriteModel = App.QuickAccessManager.Model;
10-
11-
private int PinnedFolderItemIndex =>
12-
IsItemRightClicked
13-
? favoriteModel.IndexOfItem(_RightClickedItem!)
14-
: -1;
9+
private readonly IQuickAccessService WindowsQuickAccessService = Ioc.Default.GetRequiredService<IQuickAccessService>();
1510

1611
private INavigationControlItem? _RightClickedItem = null;
1712
public INavigationControlItem? RightClickedItem => _RightClickedItem;
@@ -22,7 +17,7 @@ internal sealed class SidebarContext : ObservableObject, ISidebarContext
2217
public bool IsPinnedFolderItem =>
2318
IsItemRightClicked &&
2419
_RightClickedItem!.Section is SectionType.Pinned &&
25-
PinnedFolderItemIndex is not -1;
20+
WindowsQuickAccessService.PinnedFolders.ToList().Contains(_RightClickedItem);
2621

2722
public DriveItem? OpenDriveItem
2823
=> _RightClickedItem as DriveItem;
@@ -37,7 +32,6 @@ public void SidebarControl_RightClickedItemChanged(object? sender, INavigationCo
3732
if (SetProperty(ref _RightClickedItem, e, nameof(RightClickedItem)))
3833
{
3934
OnPropertyChanged(nameof(IsItemRightClicked));
40-
OnPropertyChanged(nameof(PinnedFolderItemIndex));
4135
OnPropertyChanged(nameof(IsPinnedFolderItem));
4236
OnPropertyChanged(nameof(OpenDriveItem));
4337
}
Original file line numberDiff line numberDiff line change
@@ -1,56 +1,22 @@
11
// Copyright (c) 2024 Files Community
22
// Licensed under the MIT License. See the LICENSE.
33

4+
using System.Collections.Specialized;
5+
46
namespace Files.App.Data.Contracts
57
{
68
public interface IQuickAccessService
79
{
8-
/// <summary>
9-
/// Gets the list of quick access items
10-
/// </summary>
11-
/// <returns></returns>
12-
Task<IEnumerable<ShellFileItem>> GetPinnedFoldersAsync();
13-
14-
/// <summary>
15-
/// Pins a folder to the quick access list
16-
/// </summary>
17-
/// <param name="folderPath">The folder to pin</param>
18-
/// <returns></returns>
19-
Task PinToSidebarAsync(string folderPath);
10+
IReadOnlyList<INavigationControlItem> PinnedFolders { get; }
2011

21-
/// <summary>
22-
/// Pins folders to the quick access list
23-
/// </summary>
24-
/// <param name="folderPaths">The array of folders to pin</param>
25-
/// <returns></returns>
26-
Task PinToSidebarAsync(string[] folderPaths);
12+
event EventHandler<NotifyCollectionChangedEventArgs>? PinnedFoldersChanged;
2713

28-
/// <summary>
29-
/// Unpins a folder from the quick access list
30-
/// </summary>
31-
/// <param name="folderPath">The folder to unpin</param>
32-
/// <returns></returns>
33-
Task UnpinFromSidebarAsync(string folderPath);
14+
Task InitializeAsync();
3415

35-
/// <summary>
36-
/// Unpins folders from the quick access list
37-
/// </summary>
38-
/// <param name="folderPaths">The array of folders to unpin</param>
39-
/// <returns></returns>
40-
Task UnpinFromSidebarAsync(string[] folderPaths);
16+
Task<bool> UpdatePinnedFoldersAsync();
4117

42-
/// <summary>
43-
/// Checks if a folder is pinned to the quick access list
44-
/// </summary>
45-
/// <param name="folderPath">The path of the folder</param>
46-
/// <returns>true if the item is pinned</returns>
47-
bool IsItemPinned(string folderPath);
18+
Task<bool> PinFolderAsync(string[] paths);
4819

49-
/// <summary>
50-
/// Saves a state of pinned folder items in the sidebar
51-
/// </summary>
52-
/// <param name="items">The array of items to save</param>
53-
/// <returns></returns>
54-
Task SaveAsync(string[] items);
20+
Task<bool> UnpinFolderAsync(string[] paths);
5521
}
5622
}

src/Files.App/Data/Items/DriveItem.cs

+3-2
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@
22
// Licensed under the MIT License. See the LICENSE.
33

44
using Files.App.Controls;
5-
using Files.App.Storage.Storables;
65
using Microsoft.UI.Xaml;
76
using Microsoft.UI.Xaml.Controls;
87
using Microsoft.UI.Xaml.Media.Imaging;
@@ -14,6 +13,8 @@ namespace Files.App.Data.Items
1413
{
1514
public sealed class DriveItem : ObservableObject, INavigationControlItem, ILocatableFolder
1615
{
16+
private readonly IQuickAccessService QuickAccessService = Ioc.Default.GetRequiredService<IQuickAccessService>();
17+
1718
private BitmapImage icon;
1819
public BitmapImage Icon
1920
{
@@ -49,7 +50,7 @@ public bool IsNetwork
4950
=> Type == DriveType.Network;
5051

5152
public bool IsPinned
52-
=> App.QuickAccessManager.Model.PinnedFolders.Contains(path);
53+
=> QuickAccessService.PinnedFolders.ToList().FirstOrDefault(x => x.Path == path) is not null;
5354

5455
public string MaxSpaceText
5556
=> MaxSpace.ToSizeString();

src/Files.App/Data/Items/ListedItem.cs

+3-1
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,8 @@ public class ListedItem : ObservableObject, IGroupableItem
2525

2626
protected static readonly IDateTimeFormatter dateTimeFormatter = Ioc.Default.GetRequiredService<IDateTimeFormatter>();
2727

28+
protected readonly IQuickAccessService QuickAccessService = Ioc.Default.GetRequiredService<IQuickAccessService>();
29+
2830
public bool IsHiddenItem { get; set; } = false;
2931

3032
public StorageItemTypes PrimaryItemAttribute { get; set; }
@@ -414,7 +416,7 @@ public override string ToString()
414416
public bool IsGitItem => this is GitItem;
415417
public virtual bool IsExecutable => !IsFolder && FileExtensionHelpers.IsExecutableFile(ItemPath);
416418
public virtual bool IsScriptFile => FileExtensionHelpers.IsScriptFile(ItemPath);
417-
public bool IsPinned => App.QuickAccessManager.Model.PinnedFolders.Contains(itemPath);
419+
public bool IsPinned => QuickAccessService.PinnedFolders.ToList().FirstOrDefault(x => x.Path == itemPath) is not null;
418420
public bool IsDriveRoot => ItemPath == PathNormalization.GetPathRoot(ItemPath);
419421
public bool IsElevationRequired { get; set; }
420422

src/Files.App/Data/Items/LocationItem.cs

+3-1
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ namespace Files.App.Data.Items
1111
{
1212
public class LocationItem : ObservableObject, INavigationControlItem
1313
{
14+
protected readonly IQuickAccessService QuickAccessService = Ioc.Default.GetRequiredService<IQuickAccessService>();
15+
1416
public BitmapImage icon;
1517
public BitmapImage Icon
1618
{
@@ -80,7 +82,7 @@ public bool IsExpanded
8082

8183
public bool IsInvalid { get; set; } = false;
8284

83-
public bool IsPinned => App.QuickAccessManager.Model.PinnedFolders.Contains(path);
85+
public bool IsPinned => QuickAccessService.PinnedFolders.ToList().FirstOrDefault(x => x.Path == path) is not null;
8486

8587
public SectionType Section { get; set; }
8688

0 commit comments

Comments
 (0)