Use SourceCache, set SelectedItem and scroll to it
This commit is contained in:
@@ -47,6 +47,56 @@ public partial class BindedCollection<T> : IDisposable, INotifyPropertyChanged
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void Dispose()
|
||||||
|
{
|
||||||
|
_disposable?.Dispose();
|
||||||
|
_innerDisposable?.Dispose();
|
||||||
|
GC.SuppressFinalize(this);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public partial class BindedCollection<T, TKey> : IDisposable, INotifyPropertyChanged where TKey : notnull
|
||||||
|
{
|
||||||
|
private readonly IDisposable? _disposable;
|
||||||
|
private IDisposable? _innerDisposable;
|
||||||
|
|
||||||
|
[Notify] private ReadOnlyObservableCollection<T>? _collection;
|
||||||
|
|
||||||
|
public BindedCollection()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
public BindedCollection(IObservable<IChangeSet<T, TKey>> dynamicList)
|
||||||
|
{
|
||||||
|
_disposable = dynamicList
|
||||||
|
.Bind(out var collection)
|
||||||
|
.DisposeMany()
|
||||||
|
.Subscribe();
|
||||||
|
|
||||||
|
_collection = collection;
|
||||||
|
}
|
||||||
|
|
||||||
|
public BindedCollection(IObservable<IObservable<IChangeSet<T, TKey>>?> dynamicListSource)
|
||||||
|
{
|
||||||
|
_disposable = dynamicListSource.Subscribe(dynamicList =>
|
||||||
|
{
|
||||||
|
_innerDisposable?.Dispose();
|
||||||
|
if (dynamicList is not null)
|
||||||
|
{
|
||||||
|
_innerDisposable = dynamicList
|
||||||
|
.Bind(out var collection)
|
||||||
|
.DisposeMany()
|
||||||
|
.Subscribe();
|
||||||
|
|
||||||
|
Collection = collection;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Collection = null;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
public void Dispose()
|
public void Dispose()
|
||||||
{
|
{
|
||||||
_disposable?.Dispose();
|
_disposable?.Dispose();
|
||||||
|
|||||||
@@ -14,13 +14,13 @@ public interface ITabViewModel : IInitable<ITab, int>, IDisposable
|
|||||||
IObservable<bool> IsSelected { get; }
|
IObservable<bool> IsSelected { get; }
|
||||||
IObservable<IContainer?> CurrentLocation { get; }
|
IObservable<IContainer?> CurrentLocation { get; }
|
||||||
IObservable<IItemViewModel?> CurrentSelectedItem { get; }
|
IObservable<IItemViewModel?> CurrentSelectedItem { get; }
|
||||||
IObservable<IObservable<IChangeSet<IItemViewModel>>?> CurrentItems { get; }
|
IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> CurrentItems { get; }
|
||||||
IObservable<IChangeSet<FullName>> MarkedItems { get; }
|
IObservable<IChangeSet<FullName>> MarkedItems { get; }
|
||||||
IObservable<IObservable<IChangeSet<IItemViewModel>>?> SelectedsChildren { get; }
|
IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> SelectedsChildren { get; }
|
||||||
IObservable<IObservable<IChangeSet<IItemViewModel>>?> ParentsChildren { get; }
|
IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> ParentsChildren { get; }
|
||||||
BindedCollection<IItemViewModel>? CurrentItemsCollection { get; }
|
BindedCollection<IItemViewModel, string>? CurrentItemsCollection { get; }
|
||||||
BindedCollection<IItemViewModel>? SelectedsChildrenCollection { get; }
|
BindedCollection<IItemViewModel, string>? SelectedsChildrenCollection { get; }
|
||||||
BindedCollection<IItemViewModel>? ParentsChildrenCollection { get; }
|
BindedCollection<IItemViewModel, string>? ParentsChildrenCollection { get; }
|
||||||
IObservable<IReadOnlyCollection<IItemViewModel>?> CurrentItemsCollectionObservable { get; }
|
IObservable<IReadOnlyCollection<IItemViewModel>?> CurrentItemsCollectionObservable { get; }
|
||||||
IObservable<IReadOnlyCollection<IItemViewModel>?> ParentsChildrenCollectionObservable { get; }
|
IObservable<IReadOnlyCollection<IItemViewModel>?> ParentsChildrenCollectionObservable { get; }
|
||||||
IObservable<IReadOnlyCollection<IItemViewModel>?> SelectedsChildrenCollectionObservable { get; }
|
IObservable<IReadOnlyCollection<IItemViewModel>?> SelectedsChildrenCollectionObservable { get; }
|
||||||
|
|||||||
@@ -31,10 +31,10 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
|
|
||||||
public IObservable<IContainer?> CurrentLocation { get; private set; } = null!;
|
public IObservable<IContainer?> CurrentLocation { get; private set; } = null!;
|
||||||
public IObservable<IItemViewModel?> CurrentSelectedItem { get; private set; } = null!;
|
public IObservable<IItemViewModel?> CurrentSelectedItem { get; private set; } = null!;
|
||||||
public IObservable<IObservable<IChangeSet<IItemViewModel>>?> CurrentItems { get; private set; } = null!;
|
public IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> CurrentItems { get; private set; } = null!;
|
||||||
public IObservable<IChangeSet<FullName>> MarkedItems { get; }
|
public IObservable<IChangeSet<FullName>> MarkedItems { get; }
|
||||||
public IObservable<IObservable<IChangeSet<IItemViewModel>>?> SelectedsChildren { get; private set; } = null!;
|
public IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> SelectedsChildren { get; private set; } = null!;
|
||||||
public IObservable<IObservable<IChangeSet<IItemViewModel>>?> ParentsChildren { get; private set; } = null!;
|
public IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> ParentsChildren { get; private set; } = null!;
|
||||||
|
|
||||||
public IObservable<IReadOnlyCollection<IItemViewModel>?> CurrentItemsCollectionObservable { get; private set; } =
|
public IObservable<IReadOnlyCollection<IItemViewModel>?> CurrentItemsCollectionObservable { get; private set; } =
|
||||||
null!;
|
null!;
|
||||||
@@ -46,11 +46,11 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
SelectedsChildrenCollectionObservable
|
SelectedsChildrenCollectionObservable
|
||||||
{ get; private set; } = null!;
|
{ get; private set; } = null!;
|
||||||
|
|
||||||
[Property] private BindedCollection<IItemViewModel>? _currentItemsCollection;
|
[Property] private BindedCollection<IItemViewModel, string>? _currentItemsCollection;
|
||||||
|
|
||||||
[Property] private BindedCollection<IItemViewModel>? _parentsChildrenCollection;
|
[Property] private BindedCollection<IItemViewModel, string>? _parentsChildrenCollection;
|
||||||
|
|
||||||
[Property] private BindedCollection<IItemViewModel>? _selectedsChildrenCollection;
|
[Property] private BindedCollection<IItemViewModel, string>? _selectedsChildrenCollection;
|
||||||
|
|
||||||
public IContainer? CachedCurrentLocation { get; private set; }
|
public IContainer? CachedCurrentLocation { get; private set; }
|
||||||
|
|
||||||
@@ -81,12 +81,10 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
|
|
||||||
CurrentItems = tab.CurrentItems
|
CurrentItems = tab.CurrentItems
|
||||||
.Select(items => items?.Transform(i => MapItemToViewModel(i, ItemViewModelType.Main)))
|
.Select(items => items?.Transform(i => MapItemToViewModel(i, ItemViewModelType.Main)))
|
||||||
/*.ObserveOn(_rxSchedulerService.GetWorkerScheduler())
|
|
||||||
.SubscribeOn(_rxSchedulerService.GetUIScheduler())*/
|
|
||||||
.Publish(null)
|
.Publish(null)
|
||||||
.RefCount();
|
.RefCount();
|
||||||
|
|
||||||
CurrentSelectedItem =
|
/*CurrentSelectedItem =
|
||||||
Observable.CombineLatest(
|
Observable.CombineLatest(
|
||||||
CurrentItems,
|
CurrentItems,
|
||||||
tab.CurrentSelectedItem,
|
tab.CurrentSelectedItem,
|
||||||
@@ -96,18 +94,28 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
: currentItems
|
: currentItems
|
||||||
.ToCollection()
|
.ToCollection()
|
||||||
.Select(items =>
|
.Select(items =>
|
||||||
items.FirstOrDefault(i => i.BaseItem?.FullName == currentSelectedItemPath?.Path))
|
items.FirstOrDefault(i => i.BaseItem?.FullName?.Path == currentSelectedItemPath?.Path.Path))
|
||||||
)
|
)
|
||||||
.Switch()
|
.Switch()
|
||||||
|
.Publish(null)
|
||||||
|
.RefCount();*/
|
||||||
|
|
||||||
|
CurrentSelectedItem =
|
||||||
|
Observable.CombineLatest(
|
||||||
|
CurrentItems,
|
||||||
|
tab.CurrentSelectedItem,
|
||||||
|
(currentItems, currentSelectedItemPath) =>
|
||||||
|
CurrentItemsCollection?.Collection?.FirstOrDefault(i => i.BaseItem?.FullName?.Path == currentSelectedItemPath?.Path.Path)
|
||||||
|
)
|
||||||
.Publish(null)
|
.Publish(null)
|
||||||
.RefCount();
|
.RefCount();
|
||||||
|
|
||||||
SelectedsChildren = InitSelectedsChildren();
|
SelectedsChildren = InitSelectedsChildren();
|
||||||
ParentsChildren = InitParentsChildren();
|
ParentsChildren = InitParentsChildren();
|
||||||
|
|
||||||
CurrentItemsCollectionObservable = InitAsd(CurrentItems);
|
CurrentItemsCollectionObservable = InitCollection(CurrentItems);
|
||||||
SelectedsChildrenCollectionObservable = InitAsd(SelectedsChildren);
|
SelectedsChildrenCollectionObservable = InitCollection(SelectedsChildren);
|
||||||
ParentsChildrenCollectionObservable = InitAsd(ParentsChildren);
|
ParentsChildrenCollectionObservable = InitCollection(ParentsChildren);
|
||||||
|
|
||||||
CurrentItemsCollection = new(CurrentItems);
|
CurrentItemsCollection = new(CurrentItems);
|
||||||
ParentsChildrenCollection = new(ParentsChildren);
|
ParentsChildrenCollection = new(ParentsChildren);
|
||||||
@@ -115,7 +123,7 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
|
|
||||||
tab.CurrentLocation.Subscribe((_) => _markedItems.Clear()).AddToDisposables(_disposables);
|
tab.CurrentLocation.Subscribe((_) => _markedItems.Clear()).AddToDisposables(_disposables);
|
||||||
|
|
||||||
IObservable<IObservable<IChangeSet<IItemViewModel>>?> InitSelectedsChildren()
|
IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> InitSelectedsChildren()
|
||||||
{
|
{
|
||||||
var currentSelectedItemThrottled =
|
var currentSelectedItemThrottled =
|
||||||
CurrentSelectedItem.Throttle(TimeSpan.FromMilliseconds(250)).Publish(null).RefCount();
|
CurrentSelectedItem.Throttle(TimeSpan.FromMilliseconds(250)).Publish(null).RefCount();
|
||||||
@@ -131,7 +139,7 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
.Transform(i => MapItemToViewModel(i, ItemViewModelType.SelectedChild))),
|
.Transform(i => MapItemToViewModel(i, ItemViewModelType.SelectedChild))),
|
||||||
currentSelectedItemThrottled
|
currentSelectedItemThrottled
|
||||||
.Where(c => c is null or not IContainerViewModel)
|
.Where(c => c is null or not IContainerViewModel)
|
||||||
.Select(_ => (IObservable<IChangeSet<IItemViewModel>>?)null)
|
.Select(_ => (IObservable<IChangeSet<IItemViewModel, string>>?)null)
|
||||||
)
|
)
|
||||||
/*.ObserveOn(_rxSchedulerService.GetWorkerScheduler())
|
/*.ObserveOn(_rxSchedulerService.GetWorkerScheduler())
|
||||||
.SubscribeOn(_rxSchedulerService.GetUIScheduler())*/
|
.SubscribeOn(_rxSchedulerService.GetUIScheduler())*/
|
||||||
@@ -139,7 +147,7 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
.RefCount();
|
.RefCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
IObservable<IObservable<IChangeSet<IItemViewModel>>?> InitParentsChildren()
|
IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> InitParentsChildren()
|
||||||
{
|
{
|
||||||
var parentThrottled = CurrentLocation
|
var parentThrottled = CurrentLocation
|
||||||
.Select(l => l?.Parent)
|
.Select(l => l?.Parent)
|
||||||
@@ -159,7 +167,7 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
.Transform(i => MapItemToViewModel(i, ItemViewModelType.Parent))),
|
.Transform(i => MapItemToViewModel(i, ItemViewModelType.Parent))),
|
||||||
parentThrottled
|
parentThrottled
|
||||||
.Where(p => p is null)
|
.Where(p => p is null)
|
||||||
.Select(_ => (IObservable<IChangeSet<IItemViewModel>>?)null)
|
.Select(_ => (IObservable<IChangeSet<IItemViewModel, string>>?)null)
|
||||||
)
|
)
|
||||||
/*.ObserveOn(_rxSchedulerService.GetWorkerScheduler())
|
/*.ObserveOn(_rxSchedulerService.GetWorkerScheduler())
|
||||||
.SubscribeOn(_rxSchedulerService.GetUIScheduler())*/
|
.SubscribeOn(_rxSchedulerService.GetUIScheduler())*/
|
||||||
@@ -167,8 +175,8 @@ public partial class TabViewModel : ITabViewModel
|
|||||||
.RefCount();
|
.RefCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
IObservable<IReadOnlyCollection<IItemViewModel>?> InitAsd(
|
IObservable<IReadOnlyCollection<IItemViewModel>?> InitCollection(
|
||||||
IObservable<IObservable<IChangeSet<IItemViewModel>>?> source)
|
IObservable<IObservable<IChangeSet<IItemViewModel, string>>?> source)
|
||||||
{
|
{
|
||||||
return source
|
return source
|
||||||
.Select(c =>
|
.Select(c =>
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ public static class DynamicDataExtensions
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static async Task<IEnumerable<AbsolutePath>?> GetItemsAsync(
|
public static async Task<IEnumerable<AbsolutePath>?> GetItemsAsync(
|
||||||
this IObservable<IObservable<IChangeSet<AbsolutePath>>?> stream)
|
this IObservable<IObservable<IChangeSet<AbsolutePath, string>>?> stream)
|
||||||
=> await GetItemsAsync(stream
|
=> await GetItemsAsync(stream
|
||||||
.Select(s =>
|
.Select(s =>
|
||||||
s is null
|
s is null
|
||||||
@@ -50,7 +50,7 @@ public static class DynamicDataExtensions
|
|||||||
.Switch());
|
.Switch());
|
||||||
|
|
||||||
public static async Task<IEnumerable<AbsolutePath>?> GetItemsAsync(
|
public static async Task<IEnumerable<AbsolutePath>?> GetItemsAsync(
|
||||||
this IObservable<IChangeSet<AbsolutePath>> stream)
|
this IObservable<IChangeSet<AbsolutePath, string>> stream)
|
||||||
=> await GetItemsAsync(stream.ToCollection());
|
=> await GetItemsAsync(stream.ToCollection());
|
||||||
|
|
||||||
private static Task<IEnumerable<AbsolutePath>?> GetItemsAsync(
|
private static Task<IEnumerable<AbsolutePath>?> GetItemsAsync(
|
||||||
|
|||||||
@@ -4,6 +4,6 @@ namespace FileTime.Core.Models;
|
|||||||
|
|
||||||
public interface IContainer : IItem
|
public interface IContainer : IItem
|
||||||
{
|
{
|
||||||
IObservable<IObservable<IChangeSet<AbsolutePath>>?> Items { get; }
|
IObservable<IObservable<IChangeSet<AbsolutePath, string>>?> Items { get; }
|
||||||
IObservable<bool> IsLoading { get; }
|
IObservable<bool> IsLoading { get; }
|
||||||
}
|
}
|
||||||
@@ -8,7 +8,7 @@ public interface ITab : IInitable<IContainer>, IDisposable
|
|||||||
{
|
{
|
||||||
IObservable<IContainer?> CurrentLocation { get; }
|
IObservable<IContainer?> CurrentLocation { get; }
|
||||||
IObservable<AbsolutePath?> CurrentSelectedItem { get; }
|
IObservable<AbsolutePath?> CurrentSelectedItem { get; }
|
||||||
IObservable<IObservable<IChangeSet<IItem>>?> CurrentItems { get; }
|
IObservable<IObservable<IChangeSet<IItem, string>>?> CurrentItems { get; }
|
||||||
FullName? LastDeepestSelectedPath { get; }
|
FullName? LastDeepestSelectedPath { get; }
|
||||||
|
|
||||||
void SetCurrentLocation(IContainer newLocation);
|
void SetCurrentLocation(IContainer newLocation);
|
||||||
|
|||||||
@@ -11,10 +11,10 @@ public abstract class ContentProviderBase : IContentProvider
|
|||||||
{
|
{
|
||||||
private readonly ReadOnlyExtensionCollection _extensions;
|
private readonly ReadOnlyExtensionCollection _extensions;
|
||||||
|
|
||||||
protected BehaviorSubject<IObservable<IChangeSet<AbsolutePath>>?> Items { get; } = new(null);
|
protected BehaviorSubject<IObservable<IChangeSet<AbsolutePath, string>>?> Items { get; } = new(null);
|
||||||
protected ExtensionCollection Extensions { get; }
|
protected ExtensionCollection Extensions { get; }
|
||||||
|
|
||||||
IObservable<IObservable<IChangeSet<AbsolutePath>>?> IContainer.Items => Items;
|
IObservable<IObservable<IChangeSet<AbsolutePath, string>>?> IContainer.Items => Items;
|
||||||
|
|
||||||
public string Name { get; }
|
public string Name { get; }
|
||||||
|
|
||||||
|
|||||||
@@ -25,7 +25,7 @@ public record Container(
|
|||||||
PointInTime PointInTime,
|
PointInTime PointInTime,
|
||||||
IObservable<IEnumerable<Exception>> Exceptions,
|
IObservable<IEnumerable<Exception>> Exceptions,
|
||||||
ReadOnlyExtensionCollection Extensions,
|
ReadOnlyExtensionCollection Extensions,
|
||||||
IObservable<IObservable<IChangeSet<AbsolutePath>>?> Items) : IContainer
|
IObservable<IObservable<IChangeSet<AbsolutePath, string>>?> Items) : IContainer
|
||||||
{
|
{
|
||||||
BehaviorSubject<bool> IsLoading { get; } = new BehaviorSubject<bool>(false);
|
BehaviorSubject<bool> IsLoading { get; } = new BehaviorSubject<bool>(false);
|
||||||
IObservable<bool> IContainer.IsLoading => IsLoading.AsObservable();
|
IObservable<bool> IContainer.IsLoading => IsLoading.AsObservable();
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ public class Tab : ITab
|
|||||||
private PointInTime _currentPointInTime;
|
private PointInTime _currentPointInTime;
|
||||||
|
|
||||||
public IObservable<IContainer?> CurrentLocation { get; }
|
public IObservable<IContainer?> CurrentLocation { get; }
|
||||||
public IObservable<IObservable<IChangeSet<IItem>>?> CurrentItems { get; }
|
public IObservable<IObservable<IChangeSet<IItem, string>>?> CurrentItems { get; }
|
||||||
public IObservable<AbsolutePath?> CurrentSelectedItem { get; }
|
public IObservable<AbsolutePath?> CurrentSelectedItem { get; }
|
||||||
public FullName? LastDeepestSelectedPath { get; private set; }
|
public FullName? LastDeepestSelectedPath { get; private set; }
|
||||||
|
|
||||||
@@ -55,9 +55,9 @@ public class Tab : ITab
|
|||||||
(items, filters) => items?.Where(i => filters.All(f => f.Filter(i)))),
|
(items, filters) => items?.Where(i => filters.All(f => f.Filter(i)))),
|
||||||
CurrentLocation
|
CurrentLocation
|
||||||
.Where(c => c is null)
|
.Where(c => c is null)
|
||||||
.Select(_ => (IObservable<IChangeSet<IItem>>?)null)
|
.Select(_ => (IObservable<IChangeSet<IItem, string>>?)null)
|
||||||
)
|
)
|
||||||
.Publish((IObservable<IChangeSet<IItem>>?)null)
|
.Publish((IObservable<IChangeSet<IItem, string>>?)null)
|
||||||
.RefCount();
|
.RefCount();
|
||||||
|
|
||||||
CurrentSelectedItem =
|
CurrentSelectedItem =
|
||||||
|
|||||||
@@ -11,5 +11,5 @@ public interface IGuiAppState : IAppState
|
|||||||
bool NoCommandFound { get; set; }
|
bool NoCommandFound { get; set; }
|
||||||
string? MessageBoxText { get; set; }
|
string? MessageBoxText { get; set; }
|
||||||
List<CommandBindingConfiguration> PossibleCommands { get; set; }
|
List<CommandBindingConfiguration> PossibleCommands { get; set; }
|
||||||
BindedCollection<RootDriveInfo> RootDriveInfos { get; set; }
|
BindedCollection<RootDriveInfo, string> RootDriveInfos { get; set; }
|
||||||
}
|
}
|
||||||
@@ -17,7 +17,7 @@ public partial class GuiAppState : AppStateBase, IGuiAppState
|
|||||||
|
|
||||||
[Property] private List<CommandBindingConfiguration> _possibleCommands = new();
|
[Property] private List<CommandBindingConfiguration> _possibleCommands = new();
|
||||||
|
|
||||||
[Property] private BindedCollection<RootDriveInfo> _rootDriveInfos = new();
|
[Property] private BindedCollection<RootDriveInfo, string> _rootDriveInfos = new();
|
||||||
|
|
||||||
public List<KeyConfig> PreviousKeys { get; } = new();
|
public List<KeyConfig> PreviousKeys { get; } = new();
|
||||||
}
|
}
|
||||||
@@ -15,14 +15,15 @@ namespace FileTime.GuiApp.Services;
|
|||||||
public class RootDriveInfoService : IStartupHandler
|
public class RootDriveInfoService : IStartupHandler
|
||||||
{
|
{
|
||||||
private readonly SourceList<DriveInfo> _rootDrives = new();
|
private readonly SourceList<DriveInfo> _rootDrives = new();
|
||||||
private readonly IObservable<IChangeSet<AbsolutePath>> _localContentProviderStream;
|
private readonly IObservable<IChangeSet<AbsolutePath, string>> _localContentProviderStream;
|
||||||
|
|
||||||
public RootDriveInfoService(IGuiAppState guiAppState, ILocalContentProvider localContentProvider, ITimelessContentProvider timelessContentProvider)
|
public RootDriveInfoService(IGuiAppState guiAppState, ILocalContentProvider localContentProvider,
|
||||||
|
ITimelessContentProvider timelessContentProvider)
|
||||||
{
|
{
|
||||||
InitRootDrives();
|
InitRootDrives();
|
||||||
|
|
||||||
var localContentProviderAsList = new SourceList<AbsolutePath>();
|
var localContentProviderAsList = new SourceCache<AbsolutePath, string>(i => i.Path.Path);
|
||||||
localContentProviderAsList.Add(new AbsolutePath(timelessContentProvider, localContentProvider));
|
localContentProviderAsList.AddOrUpdate(new AbsolutePath(timelessContentProvider, localContentProvider));
|
||||||
_localContentProviderStream = localContentProviderAsList.Connect();
|
_localContentProviderStream = localContentProviderAsList.Connect();
|
||||||
|
|
||||||
var rootDriveInfos = Observable.CombineLatest(
|
var rootDriveInfos = Observable.CombineLatest(
|
||||||
@@ -31,7 +32,7 @@ public class RootDriveInfoService : IStartupHandler
|
|||||||
(items, drives) =>
|
(items, drives) =>
|
||||||
{
|
{
|
||||||
return items is null
|
return items is null
|
||||||
? Observable.Empty<IChangeSet<(AbsolutePath Path, DriveInfo? Drive)>>()
|
? Observable.Empty<IChangeSet<(AbsolutePath Path, DriveInfo? Drive), string>>()
|
||||||
: items!
|
: items!
|
||||||
.Or(new[] { _localContentProviderStream })
|
.Or(new[] { _localContentProviderStream })
|
||||||
.Transform(i => (Path: i, Drive: drives.FirstOrDefault(d =>
|
.Transform(i => (Path: i, Drive: drives.FirstOrDefault(d =>
|
||||||
@@ -39,7 +40,8 @@ public class RootDriveInfoService : IStartupHandler
|
|||||||
var containerPath = localContentProvider.GetNativePath(i.Path).Path;
|
var containerPath = localContentProvider.GetNativePath(i.Path).Path;
|
||||||
var drivePath = d.Name.TrimEnd(Path.DirectorySeparatorChar);
|
var drivePath = d.Name.TrimEnd(Path.DirectorySeparatorChar);
|
||||||
return containerPath == drivePath
|
return containerPath == drivePath
|
||||||
|| (RuntimeInformation.IsOSPlatform(OSPlatform.Linux) && containerPath == "/" && d.Name == "/");
|
|| (RuntimeInformation.IsOSPlatform(OSPlatform.Linux) && containerPath == "/" &&
|
||||||
|
d.Name == "/");
|
||||||
})))
|
})))
|
||||||
.Filter(t => t.Drive is not null);
|
.Filter(t => t.Drive is not null);
|
||||||
}
|
}
|
||||||
@@ -51,7 +53,7 @@ public class RootDriveInfoService : IStartupHandler
|
|||||||
.Transform(t => new RootDriveInfo(t.Drive, t.Container))
|
.Transform(t => new RootDriveInfo(t.Drive, t.Container))
|
||||||
.Sort(SortExpressionComparer<RootDriveInfo>.Ascending(d => d.Name));
|
.Sort(SortExpressionComparer<RootDriveInfo>.Ascending(d => d.Name));
|
||||||
|
|
||||||
guiAppState.RootDriveInfos = new BindedCollection<RootDriveInfo>(rootDriveInfos);
|
guiAppState.RootDriveInfos = new BindedCollection<RootDriveInfo, string>(rootDriveInfos);
|
||||||
|
|
||||||
void InitRootDrives()
|
void InitRootDrives()
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -327,11 +327,11 @@
|
|||||||
<ListBox
|
<ListBox
|
||||||
x:Name="CurrentItems"
|
x:Name="CurrentItems"
|
||||||
Grid.Row="1"
|
Grid.Row="1"
|
||||||
x:CompileBindings="False"
|
|
||||||
AutoScrollToSelectedItem="True"
|
AutoScrollToSelectedItem="True"
|
||||||
Classes="ContentListView"
|
Classes="ContentListView"
|
||||||
IsTabStop="True"
|
IsTabStop="True"
|
||||||
Items="{Binding AppState.SelectedTab^.CurrentItemsCollection.Collection}"
|
Items="{Binding AppState.SelectedTab^.CurrentItemsCollection.Collection}"
|
||||||
|
SelectedItem="{Binding AppState.SelectedTab^.CurrentSelectedItem^}"
|
||||||
ScrollViewer.HorizontalScrollBarVisibility="Hidden"
|
ScrollViewer.HorizontalScrollBarVisibility="Hidden"
|
||||||
ScrollViewer.VerticalScrollBarVisibility="Visible">
|
ScrollViewer.VerticalScrollBarVisibility="Visible">
|
||||||
<ListBox.ItemTemplate>
|
<ListBox.ItemTemplate>
|
||||||
|
|||||||
@@ -6,7 +6,6 @@ using FileTime.App.Core.Models;
|
|||||||
using FileTime.Core.ContentAccess;
|
using FileTime.Core.ContentAccess;
|
||||||
using FileTime.Core.Enums;
|
using FileTime.Core.Enums;
|
||||||
using FileTime.Core.Models;
|
using FileTime.Core.Models;
|
||||||
using FileTime.Core.Services;
|
|
||||||
using FileTime.Core.Timeline;
|
using FileTime.Core.Timeline;
|
||||||
|
|
||||||
namespace FileTime.Providers.Local;
|
namespace FileTime.Providers.Local;
|
||||||
@@ -14,7 +13,7 @@ namespace FileTime.Providers.Local;
|
|||||||
public sealed partial class LocalContentProvider : ContentProviderBase, ILocalContentProvider
|
public sealed partial class LocalContentProvider : ContentProviderBase, ILocalContentProvider
|
||||||
{
|
{
|
||||||
private readonly ITimelessContentProvider _timelessContentProvider;
|
private readonly ITimelessContentProvider _timelessContentProvider;
|
||||||
private readonly SourceList<AbsolutePath> _rootDirectories = new();
|
private readonly SourceCache<AbsolutePath, string> _rootDirectories = new(i => i.Path.Path);
|
||||||
private readonly bool _isCaseInsensitive;
|
private readonly bool _isCaseInsensitive;
|
||||||
|
|
||||||
public LocalContentProvider(ITimelessContentProvider timelessContentProvider) : base("local")
|
public LocalContentProvider(ITimelessContentProvider timelessContentProvider) : base("local")
|
||||||
@@ -43,7 +42,7 @@ public sealed partial class LocalContentProvider : ContentProviderBase, ILocalCo
|
|||||||
_rootDirectories.Edit(actions =>
|
_rootDirectories.Edit(actions =>
|
||||||
{
|
{
|
||||||
actions.Clear();
|
actions.Clear();
|
||||||
actions.AddRange(rootDirectories.Select(d => DirectoryToAbsolutePath(d, PointInTime.Present)));
|
actions.AddOrUpdate(rootDirectories.Select(d => DirectoryToAbsolutePath(d, PointInTime.Present)));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -147,7 +146,7 @@ public sealed partial class LocalContentProvider : ContentProviderBase, ILocalCo
|
|||||||
pointInTime,
|
pointInTime,
|
||||||
nonNullExceptions,
|
nonNullExceptions,
|
||||||
new ExtensionCollection().AsReadOnly(),
|
new ExtensionCollection().AsReadOnly(),
|
||||||
Observable.Return<IObservable<IChangeSet<AbsolutePath>>?>(null)
|
Observable.Return<IObservable<IChangeSet<AbsolutePath, string>>?>(null)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -216,16 +215,16 @@ public sealed partial class LocalContentProvider : ContentProviderBase, ILocalCo
|
|||||||
Observable.FromAsync(async () => await Task.Run(InitChildren))
|
Observable.FromAsync(async () => await Task.Run(InitChildren))
|
||||||
);
|
);
|
||||||
|
|
||||||
Task<IObservable<IChangeSet<AbsolutePath>>?> InitChildren()
|
Task<IObservable<IChangeSet<AbsolutePath, string>>?> InitChildren()
|
||||||
{
|
{
|
||||||
SourceList<AbsolutePath>? result = null;
|
SourceCache<AbsolutePath, string>? result = null;
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
var items = initializeChildren ? (List<AbsolutePath>?)GetItemsByContainer(directoryInfo, pointInTime) : null;
|
var items = initializeChildren ? (List<AbsolutePath>?)GetItemsByContainer(directoryInfo, pointInTime) : null;
|
||||||
if (items != null)
|
if (items != null)
|
||||||
{
|
{
|
||||||
result = new SourceList<AbsolutePath>();
|
result = new SourceCache<AbsolutePath, string>(i => i.Path.Path);
|
||||||
result.AddRange(items);
|
result.AddOrUpdate(items);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (Exception e)
|
catch (Exception e)
|
||||||
|
|||||||
Reference in New Issue
Block a user