Skip to content

Commit

Permalink
Code Quality: Remove thumbnail cache to simplify logic and improve pe…
Browse files Browse the repository at this point in the history
…rformance (#14871)

Co-authored-by: hishitetsu <[email protected]>
  • Loading branch information
yaira2 and hishitetsu authored Mar 3, 2024
1 parent 6090141 commit 4f4cd89
Show file tree
Hide file tree
Showing 2 changed files with 38 additions and 150 deletions.
167 changes: 37 additions & 130 deletions src/Files.App/Data/Models/ItemViewModel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -900,29 +900,6 @@ public void UpdateGroupOptions()
FilesAndFolders.GetExtendedGroupHeaderInfo = groupInfoSelector.Item2;
}

public Dictionary<string, BitmapImage> DefaultIcons = new();

private uint currentDefaultIconSize = 0;

public async Task GetDefaultItemIconsAsync(uint size)
{
if (currentDefaultIconSize == size)
return;

DefaultIcons.Clear();

// TODO: Add more than just the folder icon
using StorageItemThumbnail icon = await FilesystemTasks.Wrap(() => StorageItemIconHelpers.GetIconForItemType(size, IconPersistenceOptions.Persist));
if (icon is not null)
{
var img = new BitmapImage();
await img.SetSourceAsync(icon);
DefaultIcons.Add(string.Empty, img);
}

currentDefaultIconSize = size;
}

private bool isLoadingItems = false;
public bool IsLoadingItems
{
Expand All @@ -937,117 +914,40 @@ private async Task<BitmapImage> GetShieldIcon()
return shieldIcon;
}

private async Task LoadItemThumbnailAsync(ListedItem item)
private async Task LoadThumbnailAsync(ListedItem item)
{
// Cancel if thumbnails aren't enabled
var thumbnailSize = folderSettings.GetRoundedIconSize();
var returnIconOnly = UserSettingsService.FoldersSettingsService.ShowThumbnails == false || thumbnailSize < 48;

if (item.IsLibrary || item.PrimaryItemAttribute == StorageItemTypes.File || item.IsArchive)
{
var getIconOnly = UserSettingsService.FoldersSettingsService.ShowThumbnails == false || thumbnailSize < 48;
var getThumbnailOnly = !item.IsExecutable && !getIconOnly;
var iconInfo = await FileThumbnailHelper.GetIconAsync(
// Get thumbnail
var icon = await FileThumbnailHelper.GetIconAsync(
item.ItemPath,
thumbnailSize,
item.IsFolder,
false,
getThumbnailOnly,
getIconOnly ? IconOptions.ReturnIconOnly : IconOptions.None);

if (!iconInfo.isIconCached)
{
// Assign a placeholder icon while trying to get a cached thumbnail
if (iconInfo.IconData is not null)
{
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
item.FileImage = await iconInfo.IconData.ToBitmapAsync();
}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}

// Loop until cached thumbnail is loaded or timeout is reached
var cancellationTokenSource = new CancellationTokenSource(3000);
while (!iconInfo.isIconCached)
{
iconInfo = await FileThumbnailHelper.GetIconAsync(
item.ItemPath,
thumbnailSize,
false,
getThumbnailOnly,
getIconOnly ? IconOptions.ReturnIconOnly : IconOptions.None);

if (cancellationTokenSource.Token.IsCancellationRequested)
break;

await Task.Delay(500);
}
}
returnIconOnly ? IconOptions.ReturnIconOnly : IconOptions.None);

if (iconInfo.IconData is not null)
{
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
// Assign the thumbnail/icon to the listed item
item.FileImage = await iconInfo.IconData.ToBitmapAsync();

// Add the file icon to the DefaultIcons list
if
(
!DefaultIcons.ContainsKey(item.FileExtension.ToLowerInvariant()) &&
!string.IsNullOrEmpty(item.FileExtension) &&
!item.IsShortcut &&
!item.IsExecutable
)
{
var fileIcon = await FileThumbnailHelper.GetIconAsync(
item.ItemPath,
thumbnailSize,
false,
false,
IconOptions.ReturnIconOnly);

var bitmapImage = await fileIcon.IconData.ToBitmapAsync();
DefaultIcons.TryAdd(item.FileExtension.ToLowerInvariant(), bitmapImage);
}

}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}

var iconOverlay = await FileThumbnailHelper.GetIconOverlayAsync(item.ItemPath, false);
if (iconOverlay is not null)
{
// Assign the icon overlay to the listed item
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
item.IconOverlay = await iconOverlay.ToBitmapAsync();
item.ShieldIcon = await GetShieldIcon();
}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}
}
else
if (icon.IconData is not null)
{
var getIconOnly = UserSettingsService.FoldersSettingsService.ShowThumbnails == false || thumbnailSize < 48;
var iconInfo = await FileThumbnailHelper.GetIconAsync(
item.ItemPath,
thumbnailSize,
true,
false, getIconOnly ? IconOptions.ReturnIconOnly : IconOptions.None);

if (iconInfo.IconData is not null)
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
item.FileImage = await iconInfo.IconData.ToBitmapAsync();
}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}
// Assign FileImage property
var image = await icon.IconData.ToBitmapAsync();
if (image is not null)
item.FileImage = image;
}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}

var iconOverlay = await FileThumbnailHelper.GetIconOverlayAsync(item.ItemPath, true);
if (iconOverlay is not null)
// Get icon overlay
var iconOverlay = await FileThumbnailHelper.GetIconOverlayAsync(item.ItemPath, true);
if (iconOverlay is not null)
{
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
await dispatcherQueue.EnqueueOrInvokeAsync(async () =>
{
item.IconOverlay = await iconOverlay.ToBitmapAsync();
item.ShieldIcon = await GetShieldIcon();
}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}
item.IconOverlay = await iconOverlay.ToBitmapAsync();
item.ShieldIcon = await GetShieldIcon();
}, Microsoft.UI.Dispatching.DispatcherQueuePriority.Low);
}
}

Expand Down Expand Up @@ -1092,7 +992,7 @@ await Task.Run(async () =>
}

cts.Token.ThrowIfCancellationRequested();
_ = LoadItemThumbnailAsync(item);
_ = LoadThumbnailAsync(item);

if (item.IsLibrary || item.PrimaryItemAttribute == StorageItemTypes.File || item.IsArchive)
{
Expand Down Expand Up @@ -1198,6 +1098,17 @@ await dispatcherQueue.EnqueueOrInvokeAsync(() =>
SetFileTag(item);
});
}
else
{
// Try loading thumbnail for cloud files in case they weren't cached the first time
if (item.SyncStatusUI.SyncStatus != CloudDriveSyncStatus.NotSynced && item.SyncStatusUI.SyncStatus != CloudDriveSyncStatus.Unknown)
{
_ = Task.Run(async () => {
await Task.Delay(500);
await LoadThumbnailAsync(item);
});
}
}

if (loadGroupHeaderInfo)
{
Expand Down Expand Up @@ -1473,8 +1384,6 @@ private async Task RapidAddItemsToCollectionAsync(string? path, LibraryItem? lib
break;
}

await GetDefaultItemIconsAsync(folderSettings.GetRoundedIconSize());

if (IsLoadingCancelled)
{
IsLoadingCancelled = false;
Expand Down Expand Up @@ -1693,7 +1602,7 @@ await Task.Run(async () =>
filesAndFolders.AddRange(intermediateList);
await OrderFilesAndFoldersAsync();
await ApplyFilesAndFoldersChangesAsync();
}, defaultIconPairs: DefaultIcons);
});

filesAndFolders.AddRange(fileList);

Expand Down Expand Up @@ -1741,8 +1650,7 @@ await Task.Run(async () =>

await OrderFilesAndFoldersAsync();
await ApplyFilesAndFoldersChangesAsync();
},
defaultIconPairs: DefaultIcons);
});

filesAndFolders.AddRange(finalList);

Expand Down Expand Up @@ -2481,7 +2389,6 @@ public void Dispose()
fileTagsSettingsService.OnSettingImportedEvent -= FileTagsSettingsService_OnSettingUpdated;
fileTagsSettingsService.OnTagsUpdated -= FileTagsSettingsService_OnSettingUpdated;
folderSizeProvider.SizeChanged -= FolderSizeProvider_SizeChanged;
DefaultIcons.Clear();
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,8 +26,7 @@ public static async Task<List<ListedItem>> ListEntries(
NativeFindStorageItemHelper.WIN32_FIND_DATA findData,
CancellationToken cancellationToken,
int countLimit,
Func<List<ListedItem>, Task> intermediateAction,
Dictionary<string, BitmapImage> defaultIconPairs = null
Func<List<ListedItem>, Task> intermediateAction
)
{
var sampler = new IntervalSampler(500);
Expand All @@ -54,18 +53,6 @@ public static async Task<List<ListedItem>> ListEntries(
var file = await GetFile(findData, path, isGitRepo, cancellationToken);
if (file is not null)
{
if (defaultIconPairs is not null)
{
if (!string.IsNullOrEmpty(file.FileExtension))
{
var lowercaseExtension = file.FileExtension.ToLowerInvariant();
if (defaultIconPairs.ContainsKey(lowercaseExtension))
{
file.FileImage = defaultIconPairs[lowercaseExtension];
}
}
}

tempList.Add(file);
++count;

Expand All @@ -82,12 +69,6 @@ public static async Task<List<ListedItem>> ListEntries(
var folder = await GetFolder(findData, path, isGitRepo, cancellationToken);
if (folder is not null)
{
if (defaultIconPairs?.ContainsKey(string.Empty) ?? false)
{
// Set folder icon (found by empty extension string)
folder.FileImage = defaultIconPairs[string.Empty];
}

tempList.Add(folder);
++count;

Expand Down

0 comments on commit 4f4cd89

Please sign in to comment.