2020-04-17 21:45:50 +01:00
|
|
|
|
// /***************************************************************************
|
|
|
|
|
|
// Aaru Data Preservation Suite
|
|
|
|
|
|
// ----------------------------------------------------------------------------
|
|
|
|
|
|
//
|
|
|
|
|
|
// Filename : MainWindowViewModel.cs
|
|
|
|
|
|
// Author(s) : Natalia Portillo <claunia@claunia.com>
|
|
|
|
|
|
//
|
|
|
|
|
|
// Component : GUI view models.
|
|
|
|
|
|
//
|
|
|
|
|
|
// --[ Description ] ----------------------------------------------------------
|
|
|
|
|
|
//
|
|
|
|
|
|
// View model and code for the main window.
|
|
|
|
|
|
//
|
|
|
|
|
|
// --[ License ] --------------------------------------------------------------
|
|
|
|
|
|
//
|
|
|
|
|
|
// This program is free software: you can redistribute it and/or modify
|
|
|
|
|
|
// it under the terms of the GNU General public License as
|
|
|
|
|
|
// published by the Free Software Foundation, either version 3 of the
|
|
|
|
|
|
// License, or (at your option) any later version.
|
|
|
|
|
|
//
|
|
|
|
|
|
// This program is distributed in the hope that it will be useful,
|
|
|
|
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
|
|
// GNU General public License for more details.
|
|
|
|
|
|
//
|
|
|
|
|
|
// You should have received a copy of the GNU General public License
|
|
|
|
|
|
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
|
|
//
|
|
|
|
|
|
// ----------------------------------------------------------------------------
|
2022-02-18 10:02:53 +00:00
|
|
|
|
// Copyright © 2011-2022 Natalia Portillo
|
2020-04-17 21:45:50 +01:00
|
|
|
|
// ****************************************************************************/
|
|
|
|
|
|
|
|
|
|
|
|
using System;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
|
using System.Collections.ObjectModel;
|
|
|
|
|
|
using System.IO;
|
2020-04-11 04:35:38 +01:00
|
|
|
|
using System.Linq;
|
2020-04-10 18:52:50 +01:00
|
|
|
|
using System.Reactive;
|
2022-03-26 16:52:00 +00:00
|
|
|
|
using System.Threading.Tasks;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
using Aaru.CommonTypes;
|
|
|
|
|
|
using Aaru.CommonTypes.Enums;
|
|
|
|
|
|
using Aaru.CommonTypes.Interfaces;
|
2020-04-11 04:35:38 +01:00
|
|
|
|
using Aaru.CommonTypes.Interop;
|
2020-04-14 22:32:47 +01:00
|
|
|
|
using Aaru.CommonTypes.Structs.Devices.SCSI;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
using Aaru.Console;
|
|
|
|
|
|
using Aaru.Core;
|
2020-04-15 05:52:13 +01:00
|
|
|
|
using Aaru.Core.Media.Info;
|
2020-04-10 18:52:50 +01:00
|
|
|
|
using Aaru.Database;
|
2020-04-14 22:32:47 +01:00
|
|
|
|
using Aaru.Devices;
|
2020-04-11 04:35:38 +01:00
|
|
|
|
using Aaru.Gui.Models;
|
2020-04-16 20:40:25 +01:00
|
|
|
|
using Aaru.Gui.ViewModels.Dialogs;
|
|
|
|
|
|
using Aaru.Gui.ViewModels.Panels;
|
|
|
|
|
|
using Aaru.Gui.Views.Dialogs;
|
|
|
|
|
|
using Aaru.Gui.Views.Panels;
|
|
|
|
|
|
using Aaru.Gui.Views.Windows;
|
2022-11-19 21:10:41 +00:00
|
|
|
|
using Aaru.Localization;
|
2020-04-09 18:18:56 +01:00
|
|
|
|
using Avalonia;
|
|
|
|
|
|
using Avalonia.Controls;
|
|
|
|
|
|
using Avalonia.Controls.ApplicationLifetimes;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
using Avalonia.Media.Imaging;
|
|
|
|
|
|
using Avalonia.Platform;
|
2020-07-22 13:20:25 +01:00
|
|
|
|
using JetBrains.Annotations;
|
2020-04-10 18:52:50 +01:00
|
|
|
|
using MessageBox.Avalonia;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
using MessageBox.Avalonia.Enums;
|
2020-04-10 01:10:55 +01:00
|
|
|
|
using ReactiveUI;
|
2020-04-15 04:40:24 +01:00
|
|
|
|
using DeviceInfo = Aaru.Core.Devices.Info.DeviceInfo;
|
2020-04-16 21:29:40 +01:00
|
|
|
|
using ImageInfo = Aaru.Gui.Views.Panels.ImageInfo;
|
|
|
|
|
|
using Partition = Aaru.Gui.Views.Panels.Partition;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
using PlatformID = Aaru.CommonTypes.Interop.PlatformID;
|
2020-04-09 18:18:56 +01:00
|
|
|
|
|
2022-11-15 15:58:43 +00:00
|
|
|
|
namespace Aaru.Gui.ViewModels.Windows;
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
public sealed class MainWindowViewModel : ViewModelBase
|
2020-04-09 02:26:04 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
readonly IAssetLoader _assets;
|
|
|
|
|
|
readonly DevicesRootModel _devicesRoot;
|
|
|
|
|
|
readonly Bitmap _ejectIcon;
|
|
|
|
|
|
readonly Bitmap _genericFolderIcon;
|
|
|
|
|
|
readonly Bitmap _genericHddIcon;
|
|
|
|
|
|
readonly Bitmap _genericOpticalIcon;
|
|
|
|
|
|
readonly Bitmap _genericTapeIcon;
|
|
|
|
|
|
readonly ImagesRootModel _imagesRoot;
|
|
|
|
|
|
readonly Bitmap _removableIcon;
|
|
|
|
|
|
readonly Bitmap _sdIcon;
|
|
|
|
|
|
readonly Bitmap _usbIcon;
|
|
|
|
|
|
readonly MainWindow _view;
|
2022-11-15 15:58:43 +00:00
|
|
|
|
Views.Dialogs.Console _console;
|
2022-03-06 13:29:38 +00:00
|
|
|
|
object _contentPanel;
|
|
|
|
|
|
bool _devicesSupported;
|
|
|
|
|
|
object _treeViewSelectedItem;
|
|
|
|
|
|
|
|
|
|
|
|
public MainWindowViewModel(MainWindow view)
|
2020-04-09 02:26:04 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
AboutCommand = ReactiveCommand.Create(ExecuteAboutCommand);
|
|
|
|
|
|
EncodingsCommand = ReactiveCommand.Create(ExecuteEncodingsCommand);
|
|
|
|
|
|
PluginsCommand = ReactiveCommand.Create(ExecutePluginsCommand);
|
|
|
|
|
|
StatisticsCommand = ReactiveCommand.Create(ExecuteStatisticsCommand);
|
|
|
|
|
|
ExitCommand = ReactiveCommand.Create(ExecuteExitCommand);
|
|
|
|
|
|
SettingsCommand = ReactiveCommand.Create(ExecuteSettingsCommand);
|
|
|
|
|
|
ConsoleCommand = ReactiveCommand.Create(ExecuteConsoleCommand);
|
|
|
|
|
|
OpenCommand = ReactiveCommand.Create(ExecuteOpenCommand);
|
|
|
|
|
|
CalculateEntropyCommand = ReactiveCommand.Create(ExecuteCalculateEntropyCommand);
|
|
|
|
|
|
VerifyImageCommand = ReactiveCommand.Create(ExecuteVerifyImageCommand);
|
|
|
|
|
|
ChecksumImageCommand = ReactiveCommand.Create(ExecuteChecksumImageCommand);
|
|
|
|
|
|
ConvertImageCommand = ReactiveCommand.Create(ExecuteConvertImageCommand);
|
|
|
|
|
|
CreateSidecarCommand = ReactiveCommand.Create(ExecuteCreateSidecarCommand);
|
|
|
|
|
|
ViewImageSectorsCommand = ReactiveCommand.Create(ExecuteViewImageSectorsCommand);
|
|
|
|
|
|
DecodeImageMediaTagsCommand = ReactiveCommand.Create(ExecuteDecodeImageMediaTagsCommand);
|
|
|
|
|
|
RefreshDevicesCommand = ReactiveCommand.Create(ExecuteRefreshDevicesCommand);
|
|
|
|
|
|
_view = view;
|
|
|
|
|
|
TreeRoot = new ObservableCollection<RootModel>();
|
|
|
|
|
|
_assets = AvaloniaLocator.Current.GetService<IAssetLoader>();
|
|
|
|
|
|
ContentPanel = Greeting;
|
|
|
|
|
|
|
|
|
|
|
|
_imagesRoot = new ImagesRootModel
|
2020-04-14 19:58:23 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
Name = UI.Title_Images
|
2022-03-06 13:29:38 +00:00
|
|
|
|
};
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
TreeRoot.Add(_imagesRoot);
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
switch(DetectOS.GetRealPlatformID())
|
|
|
|
|
|
{
|
|
|
|
|
|
case PlatformID.Win32NT:
|
|
|
|
|
|
case PlatformID.Linux:
|
|
|
|
|
|
case PlatformID.FreeBSD:
|
|
|
|
|
|
_devicesRoot = new DevicesRootModel
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
Name = UI.Title_Devices
|
2022-03-06 13:29:38 +00:00
|
|
|
|
};
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
TreeRoot.Add(_devicesRoot);
|
|
|
|
|
|
DevicesSupported = true;
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
}
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-17 00:46:26 +00:00
|
|
|
|
if(_assets == null)
|
|
|
|
|
|
return;
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_genericHddIcon =
|
|
|
|
|
|
new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/drive-harddisk.png")));
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_genericOpticalIcon =
|
|
|
|
|
|
new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/drive-optical.png")));
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_genericTapeIcon =
|
|
|
|
|
|
new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/media-tape.png")));
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_genericFolderIcon =
|
|
|
|
|
|
new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/inode-directory.png")));
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_usbIcon =
|
|
|
|
|
|
new
|
2022-03-26 17:46:59 +00:00
|
|
|
|
Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/drive-removable-media-usb.png")));
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_removableIcon =
|
2022-03-26 17:46:59 +00:00
|
|
|
|
new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/drive-removable-media.png")));
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_sdIcon =
|
|
|
|
|
|
new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/media-flash-sd-mmc.png")));
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-26 17:46:59 +00:00
|
|
|
|
_ejectIcon = new Bitmap(_assets.Open(new Uri("avares://Aaru.Gui/Assets/Icons/oxygen/32x32/media-eject.png")));
|
2022-03-06 13:29:38 +00:00
|
|
|
|
}
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-11-19 21:10:41 +00:00
|
|
|
|
public string FileLabel => UI.Menu_File;
|
|
|
|
|
|
public string OpenLabel => UI.Menu_Open;
|
|
|
|
|
|
public string SettingsLabel => UI.Menu_Settings;
|
|
|
|
|
|
public string ExitLabel => UI.Menu_Exit;
|
|
|
|
|
|
public string DevicesLabel => UI.Menu_Devices;
|
|
|
|
|
|
public string RefreshDevicesLabel => UI.Menu_Refresh;
|
|
|
|
|
|
public string WindowLabel => UI.Menu_Window;
|
|
|
|
|
|
public string ConsoleLabel => UI.Menu_Console;
|
|
|
|
|
|
public string HelpLabel => UI.Menu_Help;
|
|
|
|
|
|
public string EncodingsLabel => UI.Menu_Encodings;
|
|
|
|
|
|
public string PluginsLabel => UI.Menu_Plugins;
|
|
|
|
|
|
public string StatisticsLabel => UI.Menu_Statistics;
|
|
|
|
|
|
public string AboutLabel => UI.Menu_About;
|
|
|
|
|
|
public string RefreshDevicesFullLabel => UI.Menu_Refresh_devices;
|
|
|
|
|
|
public string CloseAllImagesLabel => UI.Menu_Close_all_images;
|
|
|
|
|
|
public string CalculateEntropyLabel => UI.ButtonLabel_Calculate_entropy;
|
|
|
|
|
|
public string VerifyImageLabel => UI.ButtonLabel_Verify;
|
|
|
|
|
|
public string ChecksumImageLabel => UI.ButtonLabel_Checksum;
|
|
|
|
|
|
public string CreateSidecarLabel => UI.ButtonLabel_Create_CICM_XML_sidecar;
|
|
|
|
|
|
public string ViewImageSectorsLabel => UI.ButtonLabel_View_sectors;
|
|
|
|
|
|
public string DecodeImageMediaTagsLabel => UI.ButtonLabel_Decode_media_tags;
|
2022-11-16 21:40:54 +00:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
public bool DevicesSupported
|
|
|
|
|
|
{
|
|
|
|
|
|
get => _devicesSupported;
|
|
|
|
|
|
set => this.RaiseAndSetIfChanged(ref _devicesSupported, value);
|
|
|
|
|
|
}
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
public bool NativeMenuSupported =>
|
2022-03-17 00:46:26 +00:00
|
|
|
|
NativeMenu.GetIsNativeMenuExported((Application.Current?.ApplicationLifetime as
|
2022-03-06 13:29:38 +00:00
|
|
|
|
IClassicDesktopStyleApplicationLifetime)?.MainWindow);
|
|
|
|
|
|
|
|
|
|
|
|
[NotNull]
|
2022-11-19 21:10:41 +00:00
|
|
|
|
public string Greeting => UI.Welcome_to_Aaru;
|
2022-03-06 13:29:38 +00:00
|
|
|
|
public ObservableCollection<RootModel> TreeRoot { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> AboutCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> ConsoleCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> EncodingsCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> PluginsCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> StatisticsCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> ExitCommand { get; }
|
2022-03-26 16:52:00 +00:00
|
|
|
|
public ReactiveCommand<Unit, Task> SettingsCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Task> OpenCommand { get; }
|
2022-03-06 13:29:38 +00:00
|
|
|
|
public ReactiveCommand<Unit, Unit> CalculateEntropyCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> VerifyImageCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> ChecksumImageCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> ConvertImageCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> CreateSidecarCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> ViewImageSectorsCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> DecodeImageMediaTagsCommand { get; }
|
|
|
|
|
|
public ReactiveCommand<Unit, Unit> RefreshDevicesCommand { get; }
|
|
|
|
|
|
|
|
|
|
|
|
public object ContentPanel
|
|
|
|
|
|
{
|
|
|
|
|
|
get => _contentPanel;
|
|
|
|
|
|
set => this.RaiseAndSetIfChanged(ref _contentPanel, value);
|
|
|
|
|
|
}
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
public object TreeViewSelectedItem
|
|
|
|
|
|
{
|
|
|
|
|
|
get => _treeViewSelectedItem;
|
|
|
|
|
|
set
|
2020-04-14 19:58:23 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(value == _treeViewSelectedItem)
|
|
|
|
|
|
return;
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
this.RaiseAndSetIfChanged(ref _treeViewSelectedItem, value);
|
2020-04-15 04:40:24 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
ContentPanel = null;
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
switch(value)
|
|
|
|
|
|
{
|
|
|
|
|
|
case ImageModel imageModel:
|
|
|
|
|
|
ContentPanel = new ImageInfo
|
|
|
|
|
|
{
|
|
|
|
|
|
DataContext = imageModel.ViewModel
|
|
|
|
|
|
};
|
2020-04-14 22:05:03 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
case PartitionModel partitionModel:
|
|
|
|
|
|
ContentPanel = new Partition
|
|
|
|
|
|
{
|
|
|
|
|
|
DataContext = partitionModel.ViewModel
|
|
|
|
|
|
};
|
2020-04-15 04:40:24 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
case FileSystemModel fileSystemModel:
|
|
|
|
|
|
ContentPanel = new FileSystem
|
|
|
|
|
|
{
|
|
|
|
|
|
DataContext = fileSystemModel.ViewModel
|
|
|
|
|
|
};
|
2020-04-15 04:40:24 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
case SubdirectoryModel subdirectoryModel:
|
|
|
|
|
|
ContentPanel = new Subdirectory
|
|
|
|
|
|
{
|
|
|
|
|
|
DataContext = new SubdirectoryViewModel(subdirectoryModel, _view)
|
|
|
|
|
|
};
|
2020-04-15 04:40:24 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
case DeviceModel deviceModel:
|
|
|
|
|
|
{
|
|
|
|
|
|
if(deviceModel.ViewModel is null)
|
2022-03-26 20:18:01 +00:00
|
|
|
|
{
|
|
|
|
|
|
var dev = Device.Create(deviceModel.Path, out ErrorNumber devErrno);
|
|
|
|
|
|
|
|
|
|
|
|
switch(dev)
|
2020-04-15 05:52:13 +01:00
|
|
|
|
{
|
2022-03-26 20:18:01 +00:00
|
|
|
|
case null:
|
2022-11-19 21:10:41 +00:00
|
|
|
|
ContentPanel = string.Format(UI.Error_0_opening_device, devErrno);
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
return;
|
|
|
|
|
|
case Devices.Remote.Device remoteDev:
|
2022-03-26 19:35:13 +00:00
|
|
|
|
Statistics.AddRemote(remoteDev.RemoteApplication, remoteDev.RemoteVersion,
|
|
|
|
|
|
remoteDev.RemoteOperatingSystem,
|
|
|
|
|
|
remoteDev.RemoteOperatingSystemVersion,
|
|
|
|
|
|
remoteDev.RemoteArchitecture);
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
break;
|
|
|
|
|
|
}
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
if(dev.Error)
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
ContentPanel = string.Format(UI.Error_0_opening_device, dev.LastError);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
var devInfo = new DeviceInfo(dev);
|
|
|
|
|
|
|
|
|
|
|
|
deviceModel.ViewModel = new DeviceInfoViewModel(devInfo, _view);
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
if(!dev.IsRemovable)
|
|
|
|
|
|
deviceModel.Media.Add(new MediaModel
|
|
|
|
|
|
{
|
|
|
|
|
|
NonRemovable = true,
|
2022-11-19 21:10:41 +00:00
|
|
|
|
Name = UI.Non_removable_device_commands_not_yet_implemented
|
2022-03-26 20:18:01 +00:00
|
|
|
|
});
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
// TODO: Removable non-SCSI?
|
|
|
|
|
|
var scsiInfo = new ScsiInfo(dev);
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
if(!scsiInfo.MediaInserted)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
deviceModel.Media.Add(new MediaModel
|
|
|
|
|
|
{
|
2022-03-26 20:18:01 +00:00
|
|
|
|
NoMediaInserted = true,
|
|
|
|
|
|
Icon = _ejectIcon,
|
2022-11-19 21:10:41 +00:00
|
|
|
|
Name = UI.No_media_inserted
|
2022-03-06 13:29:38 +00:00
|
|
|
|
});
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
2022-03-26 20:18:01 +00:00
|
|
|
|
var mediaResource =
|
|
|
|
|
|
new Uri($"avares://Aaru.Gui/Assets/Logos/Media/{scsiInfo.MediaType}.png");
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
deviceModel.Media.Add(new MediaModel
|
2020-04-15 05:52:13 +01:00
|
|
|
|
{
|
2022-03-26 20:18:01 +00:00
|
|
|
|
DevicePath = deviceModel.Path,
|
|
|
|
|
|
Icon = _assets.Exists(mediaResource) ? new Bitmap(_assets.Open(mediaResource))
|
|
|
|
|
|
: null,
|
|
|
|
|
|
Name = $"{scsiInfo.MediaType}",
|
|
|
|
|
|
ViewModel = new MediaInfoViewModel(scsiInfo, deviceModel.Path, _view)
|
|
|
|
|
|
});
|
2020-04-15 04:40:24 +01:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
dev.Close();
|
|
|
|
|
|
}
|
2020-04-15 04:40:24 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
ContentPanel = new Views.Panels.DeviceInfo
|
2020-04-15 04:40:24 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
DataContext = deviceModel.ViewModel
|
|
|
|
|
|
};
|
2020-04-15 05:52:13 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
}
|
|
|
|
|
|
case MediaModel { NonRemovable: true }:
|
2022-11-19 21:10:41 +00:00
|
|
|
|
ContentPanel = UI.Non_removable_device_commands_not_yet_implemented;
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
case MediaModel { NoMediaInserted: true }:
|
2022-11-19 21:10:41 +00:00
|
|
|
|
ContentPanel = UI.No_media_inserted;
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
case MediaModel mediaModel:
|
|
|
|
|
|
{
|
|
|
|
|
|
if(mediaModel.ViewModel != null)
|
|
|
|
|
|
ContentPanel = new MediaInfo
|
|
|
|
|
|
{
|
|
|
|
|
|
DataContext = mediaModel.ViewModel
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
break;
|
2020-04-15 04:40:24 +01:00
|
|
|
|
}
|
2020-04-14 19:58:23 +01:00
|
|
|
|
}
|
|
|
|
|
|
}
|
2022-03-06 13:29:38 +00:00
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteCalculateEntropyCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var imageEntropyWindow = new ImageEntropy();
|
|
|
|
|
|
imageEntropyWindow.DataContext = new ImageEntropyViewModel(imageModel.Image, imageEntropyWindow);
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-16 00:31:33 +00:00
|
|
|
|
imageEntropyWindow.Closed += (_, _) => imageEntropyWindow = null;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
imageEntropyWindow.Show();
|
|
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteVerifyImageCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var imageVerifyWindow = new ImageVerify();
|
|
|
|
|
|
imageVerifyWindow.DataContext = new ImageVerifyViewModel(imageModel.Image, imageVerifyWindow);
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-16 00:31:33 +00:00
|
|
|
|
imageVerifyWindow.Closed += (_, _) => imageVerifyWindow = null;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
imageVerifyWindow.Show();
|
|
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteChecksumImageCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var imageChecksumWindow = new ImageChecksum();
|
|
|
|
|
|
imageChecksumWindow.DataContext = new ImageChecksumViewModel(imageModel.Image, imageChecksumWindow);
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-16 00:31:33 +00:00
|
|
|
|
imageChecksumWindow.Closed += (_, _) => imageChecksumWindow = null;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
imageChecksumWindow.Show();
|
|
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteConvertImageCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var imageConvertWindow = new ImageConvert();
|
2020-04-14 19:58:23 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
imageConvertWindow.DataContext =
|
|
|
|
|
|
new ImageConvertViewModel(imageModel.Image, imageModel.Path, imageConvertWindow);
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-16 00:31:33 +00:00
|
|
|
|
imageConvertWindow.Closed += (_, _) => imageConvertWindow = null;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
imageConvertWindow.Show();
|
|
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteCreateSidecarCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var imageSidecarWindow = new ImageSidecar();
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
// TODO: Pass thru chosen default encoding
|
|
|
|
|
|
imageSidecarWindow.DataContext =
|
|
|
|
|
|
new ImageSidecarViewModel(imageModel.Image, imageModel.Path, imageModel.Filter.Id, null,
|
|
|
|
|
|
imageSidecarWindow);
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
imageSidecarWindow.Show();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void ExecuteViewImageSectorsCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
new ViewSector
|
2020-04-14 19:27:07 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
DataContext = new ViewSectorViewModel(imageModel.Image)
|
|
|
|
|
|
}.Show();
|
|
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteDecodeImageMediaTagsCommand()
|
|
|
|
|
|
{
|
2022-11-14 01:20:28 +00:00
|
|
|
|
if(TreeViewSelectedItem is not ImageModel imageModel)
|
2022-03-06 13:29:38 +00:00
|
|
|
|
return;
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
new DecodeMediaTags
|
2020-04-14 19:27:07 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
DataContext = new DecodeMediaTagsViewModel(imageModel.Image)
|
|
|
|
|
|
}.Show();
|
|
|
|
|
|
}
|
2020-04-14 19:27:07 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
internal void ExecuteAboutCommand()
|
|
|
|
|
|
{
|
|
|
|
|
|
var dialog = new About();
|
|
|
|
|
|
dialog.DataContext = new AboutViewModel(dialog);
|
|
|
|
|
|
dialog.ShowDialog(_view);
|
|
|
|
|
|
}
|
2020-04-10 01:10:55 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteEncodingsCommand()
|
|
|
|
|
|
{
|
|
|
|
|
|
var dialog = new Encodings();
|
|
|
|
|
|
dialog.DataContext = new EncodingsViewModel(dialog);
|
|
|
|
|
|
dialog.ShowDialog(_view);
|
|
|
|
|
|
}
|
2020-04-10 02:50:38 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecutePluginsCommand()
|
|
|
|
|
|
{
|
|
|
|
|
|
var dialog = new PluginsDialog();
|
|
|
|
|
|
dialog.DataContext = new PluginsViewModel(dialog);
|
|
|
|
|
|
dialog.ShowDialog(_view);
|
|
|
|
|
|
}
|
2020-04-10 04:16:48 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteStatisticsCommand()
|
|
|
|
|
|
{
|
2022-11-15 15:58:43 +00:00
|
|
|
|
using var ctx = AaruContext.Create(Settings.Settings.LocalDbPath);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
if(!ctx.Commands.Any() &&
|
|
|
|
|
|
!ctx.Filesystems.Any() &&
|
|
|
|
|
|
!ctx.Filters.Any() &&
|
|
|
|
|
|
!ctx.MediaFormats.Any() &&
|
|
|
|
|
|
!ctx.Medias.Any() &&
|
|
|
|
|
|
!ctx.Partitions.Any() &&
|
|
|
|
|
|
!ctx.SeenDevices.Any())
|
2020-04-10 04:16:48 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
MessageBoxManager.GetMessageBoxStandardWindow(UI.Title_Warning, UI.There_are_no_statistics).
|
|
|
|
|
|
ShowDialog(_view);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
return;
|
2020-04-10 04:16:48 +01:00
|
|
|
|
}
|
2020-04-10 18:52:50 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var dialog = new StatisticsDialog();
|
|
|
|
|
|
dialog.DataContext = new StatisticsViewModel(dialog);
|
|
|
|
|
|
dialog.ShowDialog(_view);
|
|
|
|
|
|
}
|
2020-04-10 18:52:50 +01:00
|
|
|
|
|
2022-03-26 16:52:00 +00:00
|
|
|
|
internal async Task ExecuteSettingsCommand()
|
2022-03-06 13:29:38 +00:00
|
|
|
|
{
|
|
|
|
|
|
var dialog = new SettingsDialog();
|
|
|
|
|
|
dialog.DataContext = new SettingsViewModel(dialog, false);
|
|
|
|
|
|
await dialog.ShowDialog(_view);
|
|
|
|
|
|
}
|
2020-04-10 18:52:50 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
internal void ExecuteExitCommand() =>
|
2022-03-17 00:46:26 +00:00
|
|
|
|
(Application.Current?.ApplicationLifetime as ClassicDesktopStyleApplicationLifetime)?.Shutdown();
|
2020-04-10 19:11:19 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void ExecuteConsoleCommand()
|
|
|
|
|
|
{
|
|
|
|
|
|
if(_console is null)
|
2020-04-10 22:33:27 +01:00
|
|
|
|
{
|
2022-11-15 15:58:43 +00:00
|
|
|
|
_console = new Views.Dialogs.Console();
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_console.DataContext = new ConsoleViewModel(_console);
|
2020-04-10 22:33:27 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_console.Show();
|
|
|
|
|
|
}
|
2020-04-11 03:05:21 +01:00
|
|
|
|
|
2022-03-26 16:52:00 +00:00
|
|
|
|
async Task ExecuteOpenCommand()
|
2022-03-06 13:29:38 +00:00
|
|
|
|
{
|
|
|
|
|
|
// TODO: Extensions
|
|
|
|
|
|
var dlgOpenImage = new OpenFileDialog
|
2020-04-11 03:05:21 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
Title = UI.Dialog_Choose_image_to_open,
|
2022-03-06 13:29:38 +00:00
|
|
|
|
AllowMultiple = false
|
|
|
|
|
|
};
|
2020-04-11 03:05:21 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
string[] result = await dlgOpenImage.ShowAsync(_view);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(result?.Length != 1)
|
|
|
|
|
|
return;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var filtersList = new FiltersList();
|
|
|
|
|
|
IFilter inputFilter = filtersList.GetFilter(result[0]);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(inputFilter == null)
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
MessageBoxManager.GetMessageBoxStandardWindow(UI.Title_Error, UI.Cannot_open_specified_file, ButtonEnum.Ok,
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Icon.Error);
|
|
|
|
|
|
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
try
|
|
|
|
|
|
{
|
2022-11-14 01:49:10 +00:00
|
|
|
|
if(ImageFormat.Detect(inputFilter) is not IMediaImage imageFormat)
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
MessageBoxManager.GetMessageBoxStandardWindow(UI.Title_Error, UI.Image_format_not_identified,
|
|
|
|
|
|
ButtonEnum.Ok, Icon.Error);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(UI.Image_format_identified_by_0_1, imageFormat.Name, imageFormat.Id);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
2020-04-11 21:04:20 +01:00
|
|
|
|
try
|
|
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
ErrorNumber opened = imageFormat.Open(inputFilter);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(opened != ErrorNumber.NoError)
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
MessageBoxManager.GetMessageBoxStandardWindow(UI.Title_Error,
|
|
|
|
|
|
string.Format(UI.Error_0_opening_image_format,
|
|
|
|
|
|
opened), ButtonEnum.Ok, Icon.Error);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.ErrorWriteLine(UI.Unable_to_open_image_format);
|
|
|
|
|
|
AaruConsole.ErrorWriteLine(UI.No_error_given);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
2020-04-11 21:04:20 +01:00
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-07 07:36:44 +00:00
|
|
|
|
var mediaResource = new Uri($"avares://Aaru.Gui/Assets/Logos/Media/{imageFormat.Info.MediaType}.png");
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var imageModel = new ImageModel
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Path = result[0],
|
|
|
|
|
|
Icon = _assets.Exists(mediaResource)
|
|
|
|
|
|
? new Bitmap(_assets.Open(mediaResource))
|
|
|
|
|
|
: imageFormat.Info.XmlMediaType == XmlMediaType.BlockMedia
|
|
|
|
|
|
? _genericHddIcon
|
|
|
|
|
|
: imageFormat.Info.XmlMediaType == XmlMediaType.OpticalDisc
|
|
|
|
|
|
? _genericOpticalIcon
|
|
|
|
|
|
: _genericFolderIcon,
|
|
|
|
|
|
FileName = Path.GetFileName(result[0]),
|
|
|
|
|
|
Image = imageFormat,
|
|
|
|
|
|
ViewModel = new ImageInfoViewModel(result[0], inputFilter, imageFormat, _view),
|
|
|
|
|
|
Filter = inputFilter
|
|
|
|
|
|
};
|
|
|
|
|
|
|
2022-11-15 15:58:43 +00:00
|
|
|
|
List<CommonTypes.Partition> partitions = Core.Partitions.GetAll(imageFormat);
|
|
|
|
|
|
Core.Partitions.AddSchemesToStats(partitions);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
2022-11-15 15:58:43 +00:00
|
|
|
|
bool checkRaw = false;
|
2022-03-06 13:29:38 +00:00
|
|
|
|
List<string> idPlugins;
|
|
|
|
|
|
IFilesystem plugin;
|
|
|
|
|
|
PluginBase plugins = GetPluginBase.Instance;
|
|
|
|
|
|
|
|
|
|
|
|
if(partitions.Count == 0)
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.DebugWriteLine("Fs-info command", UI.No_partitions_found);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
checkRaw = true;
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(UI._0_partitions_found, partitions.Count);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
foreach(string scheme in partitions.Select(p => p.Scheme).Distinct().OrderBy(s => s))
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
// TODO: Add icons to partition schemes
|
|
|
|
|
|
var schemeModel = new PartitionSchemeModel
|
|
|
|
|
|
{
|
|
|
|
|
|
Name = scheme
|
|
|
|
|
|
};
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
foreach(CommonTypes.Partition partition in partitions.Where(p => p.Scheme == scheme).
|
|
|
|
|
|
OrderBy(p => p.Start))
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var partitionModel = new PartitionModel
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
// TODO: Add icons to partition types
|
|
|
|
|
|
Name = $"{partition.Name} ({partition.Type})",
|
|
|
|
|
|
Partition = partition,
|
|
|
|
|
|
ViewModel = new PartitionViewModel(partition)
|
2020-04-11 21:04:20 +01:00
|
|
|
|
};
|
|
|
|
|
|
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(UI.Identifying_filesystems_on_partition);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
2022-11-15 15:58:43 +00:00
|
|
|
|
Core.Filesystems.Identify(imageFormat, out idPlugins, partition);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(idPlugins.Count == 0)
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(UI.Filesystem_not_identified);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
else
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(string.Format(UI.Identified_by_0_plugins, idPlugins.Count));
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
foreach(string pluginName in idPlugins)
|
|
|
|
|
|
if(plugins.PluginsList.TryGetValue(pluginName, out plugin))
|
|
|
|
|
|
{
|
|
|
|
|
|
plugin.GetInformation(imageFormat, partition, out string information, null);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var fsPlugin = plugin as IReadOnlyFilesystem;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(fsPlugin != null)
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
ErrorNumber error =
|
|
|
|
|
|
fsPlugin.Mount(imageFormat, partition, null,
|
|
|
|
|
|
new Dictionary<string, string>(), null);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(error != ErrorNumber.NoError)
|
|
|
|
|
|
fsPlugin = null;
|
|
|
|
|
|
}
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var filesystemModel = new FileSystemModel
|
|
|
|
|
|
{
|
|
|
|
|
|
VolumeName =
|
|
|
|
|
|
plugin.XmlFsType.VolumeName is null ? $"{plugin.XmlFsType.Type}"
|
|
|
|
|
|
: $"{plugin.XmlFsType.VolumeName} ({plugin.XmlFsType.Type})",
|
|
|
|
|
|
Filesystem = plugin,
|
|
|
|
|
|
ReadOnlyFilesystem = fsPlugin,
|
|
|
|
|
|
ViewModel = new FileSystemViewModel(plugin.XmlFsType, information)
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
// TODO: Trap expanding item
|
|
|
|
|
|
if(fsPlugin != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
filesystemModel.Roots.Add(new SubdirectoryModel
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Name = "/",
|
|
|
|
|
|
Path = "",
|
|
|
|
|
|
Plugin = fsPlugin
|
|
|
|
|
|
});
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Statistics.AddCommand("ls");
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Statistics.AddFilesystem(plugin.XmlFsType.Type);
|
|
|
|
|
|
partitionModel.FileSystems.Add(filesystemModel);
|
|
|
|
|
|
}
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
schemeModel.Partitions.Add(partitionModel);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
imageModel.PartitionSchemesOrFileSystems.Add(schemeModel);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
2022-03-06 13:29:38 +00:00
|
|
|
|
}
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(checkRaw)
|
|
|
|
|
|
{
|
|
|
|
|
|
var wholePart = new CommonTypes.Partition
|
2020-04-11 21:04:20 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
Name = Localization.Core.Whole_device,
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Length = imageFormat.Info.Sectors,
|
|
|
|
|
|
Size = imageFormat.Info.Sectors * imageFormat.Info.SectorSize
|
|
|
|
|
|
};
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-11-15 15:58:43 +00:00
|
|
|
|
Core.Filesystems.Identify(imageFormat, out idPlugins, wholePart);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(idPlugins.Count == 0)
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(UI.Filesystem_not_identified);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
else
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(string.Format(UI.Identified_by_0_plugins, idPlugins.Count));
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
foreach(string pluginName in idPlugins)
|
|
|
|
|
|
if(plugins.PluginsList.TryGetValue(pluginName, out plugin))
|
|
|
|
|
|
{
|
|
|
|
|
|
plugin.GetInformation(imageFormat, wholePart, out string information, null);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var fsPlugin = plugin as IReadOnlyFilesystem;
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(fsPlugin != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
ErrorNumber error = fsPlugin.Mount(imageFormat, wholePart, null,
|
|
|
|
|
|
new Dictionary<string, string>(), null);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
if(error != ErrorNumber.NoError)
|
|
|
|
|
|
fsPlugin = null;
|
|
|
|
|
|
}
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var filesystemModel = new FileSystemModel
|
|
|
|
|
|
{
|
|
|
|
|
|
VolumeName = plugin.XmlFsType.VolumeName is null ? $"{plugin.XmlFsType.Type}"
|
|
|
|
|
|
: $"{plugin.XmlFsType.VolumeName} ({plugin.XmlFsType.Type})",
|
|
|
|
|
|
Filesystem = plugin,
|
|
|
|
|
|
ReadOnlyFilesystem = fsPlugin,
|
|
|
|
|
|
ViewModel = new FileSystemViewModel(plugin.XmlFsType, information)
|
|
|
|
|
|
};
|
2020-04-14 22:05:03 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
// TODO: Trap expanding item
|
|
|
|
|
|
if(fsPlugin != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
filesystemModel.Roots.Add(new SubdirectoryModel
|
|
|
|
|
|
{
|
|
|
|
|
|
Name = "/",
|
|
|
|
|
|
Path = "",
|
|
|
|
|
|
Plugin = fsPlugin
|
|
|
|
|
|
});
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Statistics.AddCommand("ls");
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Statistics.AddFilesystem(plugin.XmlFsType.Type);
|
|
|
|
|
|
imageModel.PartitionSchemesOrFileSystems.Add(filesystemModel);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Statistics.AddMediaFormat(imageFormat.Format);
|
|
|
|
|
|
Statistics.AddMedia(imageFormat.Info.MediaType, false);
|
|
|
|
|
|
Statistics.AddFilter(inputFilter.Name);
|
|
|
|
|
|
|
|
|
|
|
|
_imagesRoot.Images.Add(imageModel);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
|
|
|
|
|
catch(Exception ex)
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
MessageBoxManager.GetMessageBoxStandardWindow(UI.Title_Error, UI.Unable_to_open_image_format,
|
|
|
|
|
|
ButtonEnum.Ok, Icon.Error);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.ErrorWriteLine(UI.Unable_to_open_image_format);
|
2022-11-23 16:06:46 +00:00
|
|
|
|
AaruConsole.ErrorWriteLine(Localization.Core.Error_0, ex.Message);
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.DebugWriteLine("Image-info command", Localization.Core.Stack_trace_0, ex.StackTrace);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
2022-03-06 13:29:38 +00:00
|
|
|
|
}
|
|
|
|
|
|
catch(Exception ex)
|
|
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
MessageBoxManager.GetMessageBoxStandardWindow(UI.Title_Error, UI.Exception_reading_file, ButtonEnum.Ok,
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Icon.Error);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.ErrorWriteLine(string.Format(UI.Error_reading_file_0, ex.Message));
|
2022-03-06 13:29:38 +00:00
|
|
|
|
AaruConsole.DebugWriteLine("Image-info command", ex.StackTrace);
|
2020-04-11 21:04:20 +01:00
|
|
|
|
}
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Statistics.AddCommand("image-info");
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
internal void LoadComplete() => RefreshDevices();
|
|
|
|
|
|
|
|
|
|
|
|
void ExecuteRefreshDevicesCommand() => RefreshDevices();
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
void RefreshDevices()
|
|
|
|
|
|
{
|
|
|
|
|
|
if(!DevicesSupported)
|
|
|
|
|
|
return;
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
try
|
2020-04-14 22:32:47 +01:00
|
|
|
|
{
|
2022-11-19 21:10:41 +00:00
|
|
|
|
AaruConsole.WriteLine(UI.Refreshing_devices);
|
2022-03-06 13:29:38 +00:00
|
|
|
|
_devicesRoot.Devices.Clear();
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-07 07:36:44 +00:00
|
|
|
|
foreach(Devices.DeviceInfo device in Device.ListDevices().Where(d => d.Supported).OrderBy(d => d.Vendor).
|
|
|
|
|
|
ThenBy(d => d.Model))
|
2020-04-14 22:32:47 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
AaruConsole.DebugWriteLine("Main window",
|
2022-11-19 21:10:41 +00:00
|
|
|
|
UI.Found_supported_device_model_0_by_manufacturer_1_on_bus_2_and_path_3,
|
2022-03-06 13:29:38 +00:00
|
|
|
|
device.Model, device.Vendor, device.Bus, device.Path);
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
var deviceModel = new DeviceModel
|
2020-04-14 22:32:47 +01:00
|
|
|
|
{
|
2022-03-06 13:29:38 +00:00
|
|
|
|
Icon = _genericHddIcon,
|
|
|
|
|
|
Name = $"{device.Vendor} {device.Model} ({device.Bus})",
|
|
|
|
|
|
Path = device.Path
|
|
|
|
|
|
};
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
var dev = Device.Create(device.Path, out _);
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-26 20:18:01 +00:00
|
|
|
|
if(dev != null)
|
|
|
|
|
|
{
|
2022-03-26 19:35:13 +00:00
|
|
|
|
if(dev is Devices.Remote.Device remoteDev)
|
|
|
|
|
|
Statistics.AddRemote(remoteDev.RemoteApplication, remoteDev.RemoteVersion,
|
|
|
|
|
|
remoteDev.RemoteOperatingSystem, remoteDev.RemoteOperatingSystemVersion,
|
|
|
|
|
|
remoteDev.RemoteArchitecture);
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
switch(dev.Type)
|
|
|
|
|
|
{
|
|
|
|
|
|
case DeviceType.ATAPI:
|
|
|
|
|
|
case DeviceType.SCSI:
|
|
|
|
|
|
switch(dev.ScsiType)
|
|
|
|
|
|
{
|
|
|
|
|
|
case PeripheralDeviceTypes.DirectAccess:
|
|
|
|
|
|
case PeripheralDeviceTypes.SCSIZonedBlockDevice:
|
|
|
|
|
|
case PeripheralDeviceTypes.SimplifiedDevice:
|
2022-11-15 15:58:43 +00:00
|
|
|
|
deviceModel.Icon = dev.IsRemovable ? dev.IsUsb ? _usbIcon : _removableIcon
|
|
|
|
|
|
: _genericHddIcon;
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
case PeripheralDeviceTypes.SequentialAccess:
|
|
|
|
|
|
deviceModel.Icon = _genericTapeIcon;
|
|
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
case PeripheralDeviceTypes.OpticalDevice:
|
|
|
|
|
|
case PeripheralDeviceTypes.WriteOnceDevice:
|
|
|
|
|
|
case PeripheralDeviceTypes.OCRWDevice:
|
|
|
|
|
|
deviceModel.Icon = _removableIcon;
|
|
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
case PeripheralDeviceTypes.MultiMediaDevice:
|
|
|
|
|
|
deviceModel.Icon = _genericOpticalIcon;
|
|
|
|
|
|
|
|
|
|
|
|
break;
|
|
|
|
|
|
}
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
case DeviceType.SecureDigital:
|
|
|
|
|
|
case DeviceType.MMC:
|
|
|
|
|
|
deviceModel.Icon = _sdIcon;
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
|
|
|
|
|
case DeviceType.NVMe:
|
|
|
|
|
|
deviceModel.Icon = null;
|
2020-04-14 22:32:47 +01:00
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
break;
|
2020-04-14 22:32:47 +01:00
|
|
|
|
}
|
|
|
|
|
|
|
2022-03-06 13:29:38 +00:00
|
|
|
|
dev.Close();
|
2020-04-14 22:32:47 +01:00
|
|
|
|
}
|
2022-03-06 13:29:38 +00:00
|
|
|
|
|
|
|
|
|
|
_devicesRoot.Devices.Add(deviceModel);
|
2020-04-14 22:32:47 +01:00
|
|
|
|
}
|
2022-03-06 13:29:38 +00:00
|
|
|
|
}
|
|
|
|
|
|
catch(InvalidOperationException ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
AaruConsole.ErrorWriteLine(ex.Message);
|
2020-04-14 22:32:47 +01:00
|
|
|
|
}
|
2020-04-09 02:26:04 +01:00
|
|
|
|
}
|
2020-04-09 04:18:29 +01:00
|
|
|
|
}
|