Go to location, Warnings
This commit is contained in:
@@ -9,7 +9,7 @@ namespace FileTime.Core.Command
|
||||
private Func<IContainer, string, Task<IContainer>>? _createContainer;
|
||||
private TimeRunner? _timeRunner;
|
||||
|
||||
public IList<AbsolutePath>? Sources { get; } = new List<AbsolutePath>();
|
||||
public IList<AbsolutePath> Sources { get; } = new List<AbsolutePath>();
|
||||
|
||||
public IContainer? Target { get; set; }
|
||||
|
||||
|
||||
@@ -4,7 +4,7 @@ namespace FileTime.Core.Command
|
||||
{
|
||||
public interface ITransportationCommand : ICommand
|
||||
{
|
||||
IList<AbsolutePath>? Sources { get; }
|
||||
IList<AbsolutePath> Sources { get; }
|
||||
IContainer? Target { get; set;}
|
||||
TransportMode? TransportMode { get; set; }
|
||||
}
|
||||
|
||||
@@ -5,7 +5,7 @@ namespace FileTime.Core.Command
|
||||
{
|
||||
public class MoveCommand : ITransportationCommand
|
||||
{
|
||||
public IList<AbsolutePath>? Sources { get; } = new List<AbsolutePath>();
|
||||
public IList<AbsolutePath> Sources { get; } = new List<AbsolutePath>();
|
||||
|
||||
public IContainer? Target { get; set; }
|
||||
public TransportMode? TransportMode { get; set; } = Command.TransportMode.Merge;
|
||||
|
||||
@@ -6,7 +6,9 @@ namespace FileTime.Core.Components
|
||||
public class Tab
|
||||
{
|
||||
private IItem? _currentSelectedItem;
|
||||
#pragma warning disable CS8618 // Non-nullable field must contain a non-null value when exiting constructor. Consider declaring as nullable.
|
||||
private IContainer _currentLocation;
|
||||
#pragma warning restore CS8618 // Non-nullable field must contain a non-null value when exiting constructor. Consider declaring as nullable.
|
||||
private string? _lastPath;
|
||||
|
||||
public int CurrentSelectedIndex { get; private set; }
|
||||
|
||||
@@ -12,14 +12,18 @@ namespace FileTime.Core.Providers
|
||||
private readonly IReadOnlyList<IItem>? _items;
|
||||
private readonly IReadOnlyList<IElement>? _elements = new List<IElement>().AsReadOnly();
|
||||
|
||||
#pragma warning disable CS8603 // Possible null reference return.
|
||||
public string Name => null;
|
||||
#pragma warning restore CS8603 // Possible null reference return.
|
||||
|
||||
public string? FullName => null;
|
||||
|
||||
public bool IsHidden => false;
|
||||
public bool IsLoaded => true;
|
||||
|
||||
#pragma warning disable CS8603 // Possible null reference return.
|
||||
public IContentProvider Provider => null;
|
||||
#pragma warning restore CS8603 // Possible null reference return.
|
||||
public bool CanDelete => false;
|
||||
public bool CanRename => false;
|
||||
|
||||
|
||||
@@ -74,7 +74,7 @@ namespace FileTime.Core.Timeline
|
||||
}
|
||||
});
|
||||
|
||||
UpdateReadOnlyCommands();
|
||||
await UpdateReadOnlyCommands();
|
||||
}
|
||||
|
||||
public async Task TryStartCommandRunner()
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace FileTime.Avalonia
|
||||
{
|
||||
public static IServiceProvider ServiceProvider { get; private set; }
|
||||
|
||||
public App()
|
||||
static App()
|
||||
{
|
||||
ServiceProvider ??= DependencyInjection
|
||||
.RegisterDefaultServices()
|
||||
|
||||
@@ -41,8 +41,8 @@ namespace FileTime.Avalonia.ViewModels
|
||||
|
||||
private IClipboard _clipboard;
|
||||
private TimeRunner _timeRunner;
|
||||
private IEnumerable<IContentProvider>? _contentProviders;
|
||||
private Action? _inputHandler;
|
||||
private IEnumerable<IContentProvider> _contentProviders;
|
||||
private Func<Task>? _inputHandler;
|
||||
|
||||
[Property]
|
||||
private string _text;
|
||||
@@ -68,7 +68,7 @@ namespace FileTime.Avalonia.ViewModels
|
||||
{
|
||||
_clipboard = App.ServiceProvider.GetService<IClipboard>()!;
|
||||
_timeRunner = App.ServiceProvider.GetService<TimeRunner>()!;
|
||||
_contentProviders = App.ServiceProvider.GetService<IEnumerable<IContentProvider>>();
|
||||
_contentProviders = App.ServiceProvider.GetService<IEnumerable<IContentProvider>>()!;
|
||||
var inputInterface = (BasicInputHandler)App.ServiceProvider.GetService<IInputInterface>()!;
|
||||
inputInterface.InputHandler = ReadInputs2;
|
||||
App.ServiceProvider.GetService<TopContainer>();
|
||||
@@ -107,12 +107,12 @@ namespace FileTime.Avalonia.ViewModels
|
||||
RootDriveInfos = driveInfos.OrderBy(d => d.Name).ToList();
|
||||
}
|
||||
|
||||
private async Task<IContainer> GetContainerForWindowsDrive(DriveInfo drive)
|
||||
private async Task<IContainer?> GetContainerForWindowsDrive(DriveInfo drive)
|
||||
{
|
||||
return (await LocalContentProvider.GetRootContainers()).FirstOrDefault(d => d.Name == drive.Name.TrimEnd(Path.DirectorySeparatorChar));
|
||||
}
|
||||
|
||||
private async Task<IContainer> GetContainerForLinuxDrive(DriveInfo drive)
|
||||
private async Task<IContainer?> GetContainerForLinuxDrive(DriveInfo drive)
|
||||
{
|
||||
return await LocalContentProvider.GetByPath(drive.Name) as IContainer;
|
||||
}
|
||||
@@ -274,13 +274,13 @@ namespace FileTime.Avalonia.ViewModels
|
||||
|
||||
public Task CreateContainer()
|
||||
{
|
||||
var handler = () =>
|
||||
var handler = async () =>
|
||||
{
|
||||
if (Inputs != null)
|
||||
{
|
||||
var container = AppState.SelectedTab.CurrentLocation.Container;
|
||||
var createContainerCommand = new CreateContainerCommand(new Core.Models.AbsolutePath(container), Inputs[0].Value);
|
||||
_timeRunner.AddCommand(createContainerCommand).Wait();
|
||||
await _timeRunner.AddCommand(createContainerCommand);
|
||||
Inputs = null;
|
||||
}
|
||||
};
|
||||
@@ -292,13 +292,13 @@ namespace FileTime.Avalonia.ViewModels
|
||||
|
||||
public Task CreateElement()
|
||||
{
|
||||
var handler = () =>
|
||||
var handler = async () =>
|
||||
{
|
||||
if (Inputs != null)
|
||||
{
|
||||
var container = AppState.SelectedTab.CurrentLocation.Container;
|
||||
var createElementCommand = new CreateElementCommand(new Core.Models.AbsolutePath(container), Inputs[0].Value);
|
||||
_timeRunner.AddCommand(createElementCommand).Wait();
|
||||
await _timeRunner.AddCommand(createElementCommand);
|
||||
Inputs = null;
|
||||
}
|
||||
};
|
||||
@@ -346,7 +346,7 @@ namespace FileTime.Avalonia.ViewModels
|
||||
|
||||
public async Task Delete()
|
||||
{
|
||||
IList<Core.Models.AbsolutePath>? itemsToDelete = null;
|
||||
IList<AbsolutePath>? itemsToDelete = null;
|
||||
var askForDelete = false;
|
||||
var questionText = "";
|
||||
var shouldDelete = false;
|
||||
@@ -403,11 +403,11 @@ namespace FileTime.Avalonia.ViewModels
|
||||
}
|
||||
else if (shouldDelete)
|
||||
{
|
||||
HandleDelete();
|
||||
await HandleDelete();
|
||||
}
|
||||
}
|
||||
|
||||
void HandleDelete()
|
||||
async Task HandleDelete()
|
||||
{
|
||||
var deleteCommand = new DeleteCommand();
|
||||
|
||||
@@ -416,7 +416,7 @@ namespace FileTime.Avalonia.ViewModels
|
||||
deleteCommand.ItemsToDelete.Add(itemToDelete);
|
||||
}
|
||||
|
||||
_timeRunner.AddCommand(deleteCommand).Wait();
|
||||
await _timeRunner.AddCommand(deleteCommand);
|
||||
_clipboard.Clear();
|
||||
}
|
||||
}
|
||||
@@ -465,12 +465,12 @@ namespace FileTime.Avalonia.ViewModels
|
||||
var selectedItem = AppState.SelectedTab.SelectedItem?.Item;
|
||||
if (selectedItem != null)
|
||||
{
|
||||
var handler = () =>
|
||||
var handler = async () =>
|
||||
{
|
||||
if (Inputs != null)
|
||||
{
|
||||
var renameCommand = new RenameCommand(new Core.Models.AbsolutePath(selectedItem), Inputs[0].Value);
|
||||
_timeRunner.AddCommand(renameCommand).Wait();
|
||||
await _timeRunner.AddCommand(renameCommand);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -502,23 +502,45 @@ namespace FileTime.Avalonia.ViewModels
|
||||
await _timeRunner.Refresh();
|
||||
}
|
||||
|
||||
private async Task GoToContainer()
|
||||
private Task GoToContainer()
|
||||
{
|
||||
var handler = () =>
|
||||
var handler = async () =>
|
||||
{
|
||||
if (Inputs != null)
|
||||
{
|
||||
|
||||
var path = Inputs[0].Value;
|
||||
foreach (var contentProvider in _contentProviders)
|
||||
{
|
||||
if (contentProvider.CanHandlePath(path))
|
||||
{
|
||||
var possibleContainer = await contentProvider.GetByPath(path);
|
||||
if (possibleContainer is IContainer container)
|
||||
{
|
||||
AppState.SelectedTab.OpenContainer(container).Wait();
|
||||
}
|
||||
//TODO: multiple possible content provider handler
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
ReadInputs(new List<Core.Interactions.InputElement>() { new Core.Interactions.InputElement("Path", InputType.Text) }, handler);
|
||||
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
[Command]
|
||||
public void ProcessInputs()
|
||||
public async void ProcessInputs()
|
||||
{
|
||||
_inputHandler?.Invoke();
|
||||
try
|
||||
{
|
||||
if (_inputHandler != null)
|
||||
{
|
||||
await _inputHandler.Invoke();
|
||||
}
|
||||
}
|
||||
catch { }
|
||||
|
||||
Inputs = null;
|
||||
_inputHandler = null;
|
||||
@@ -683,6 +705,10 @@ namespace FileTime.Avalonia.ViewModels
|
||||
}
|
||||
|
||||
private void ReadInputs(List<Core.Interactions.InputElement> inputs, Action inputHandler)
|
||||
{
|
||||
ReadInputs(inputs, () => { inputHandler(); return Task.CompletedTask; });
|
||||
}
|
||||
private void ReadInputs(List<Core.Interactions.InputElement> inputs, Func<Task> inputHandler)
|
||||
{
|
||||
Inputs = inputs.Select(i => new InputElementWrapper(i, i.DefaultValue)).ToList();
|
||||
_inputHandler = inputHandler;
|
||||
@@ -706,7 +732,7 @@ namespace FileTime.Avalonia.ViewModels
|
||||
return result;
|
||||
}
|
||||
|
||||
private void ShowMessageBox(string text, Action inputHandler)
|
||||
private void ShowMessageBox(string text, Func<Task> inputHandler)
|
||||
{
|
||||
MessageBoxText = text;
|
||||
_inputHandler = inputHandler;
|
||||
|
||||
@@ -42,7 +42,7 @@ namespace FileTime.Avalonia.Views
|
||||
{
|
||||
if (_inputElementWrapper == null)
|
||||
{
|
||||
e.Handled = e.Handled || await ViewModel?.ProcessKeyDown(e.Key, e.KeyModifiers);
|
||||
e.Handled = e.Handled || await ViewModel!.ProcessKeyDown(e.Key, e.KeyModifiers);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,7 +50,7 @@ namespace FileTime.Avalonia.Views
|
||||
{
|
||||
if (_inputElementWrapper == null)
|
||||
{
|
||||
e.Handled = e.Handled || await ViewModel?.ProcessKeyUp(e.Key, e.KeyModifiers);
|
||||
e.Handled = e.Handled || await ViewModel!.ProcessKeyUp(e.Key, e.KeyModifiers);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -48,11 +48,13 @@ namespace FileTime.Providers.Local
|
||||
|
||||
public async Task<IItem?> GetByPath(string path)
|
||||
{
|
||||
path = path.Replace(Path.DirectorySeparatorChar, Constants.SeparatorChar).TrimEnd(Constants.SeparatorChar);
|
||||
var pathParts = (IsCaseInsensitive ? path.ToLower() : path).TrimStart(Constants.SeparatorChar).Split(Constants.SeparatorChar);
|
||||
|
||||
if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux) && pathParts.Length == 1 && pathParts[0] == "") return this;
|
||||
|
||||
var rootContainer = _rootContainers.FirstOrDefault(c => NormalizePath(c.Name) == NormalizePath(pathParts[0]));
|
||||
var normalizedRootContainerName = NormalizePath(pathParts[0]);
|
||||
var rootContainer = _rootContainers.FirstOrDefault(c => NormalizePath(c.Name) == normalizedRootContainerName);
|
||||
|
||||
if (rootContainer == null)
|
||||
{
|
||||
@@ -77,7 +79,11 @@ namespace FileTime.Providers.Local
|
||||
|
||||
internal string NormalizePath(string path) => IsCaseInsensitive ? path.ToLower() : path;
|
||||
|
||||
public bool CanHandlePath(string path) => _rootContainers.Any(r => path.StartsWith(r.Name));
|
||||
public bool CanHandlePath(string path)
|
||||
{
|
||||
var normalizedPath = NormalizePath(path);
|
||||
return _rootContainers.Any(r => normalizedPath.StartsWith(NormalizePath(r.Name)));
|
||||
}
|
||||
|
||||
public void SetParent(IContainer container) => _parent = container;
|
||||
public Task<IReadOnlyList<IContainer>> GetRootContainers(CancellationToken token = default) => Task.FromResult(_rootContainers);
|
||||
|
||||
Reference in New Issue
Block a user