using Microsoft.Win32; using System; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Diagnostics; using System.IO; using System.Linq; using System.Text; using System.Threading.Tasks; using Tango.Core.Commands; using Tango.Core.DI; using Tango.Core.IO; using Tango.Integration.ExternalBridge; using Tango.Integration.Storage; using Tango.MachineStudio.Common; using Tango.MachineStudio.Common.FirmwareUpgrade; using Tango.MachineStudio.Common.Notifications; using Tango.MachineStudio.Common.StudioApplication; using Tango.MachineStudio.Storage.Models; namespace Tango.MachineStudio.Storage.ViewModels { public class MainViewVM : StudioViewModel { public event EventHandler CurrentFolderChanged; private IStudioApplicationManager _applicationManager; private INotificationProvider _notification; private IFirmwareUpgrader _firmwareUpgrader; private bool _machine_operator_changed = true; private StorageManager _storageManager; public StorageManager StorageManager { get { return _storageManager; } set { _storageManager = value; RaisePropertyChangedAuto(); } } private StorageItem _selectedStorageItem; public StorageItem SelectedStorageItem { get { return _selectedStorageItem; } set { _selectedStorageItem = value; RaisePropertyChangedAuto(); InvalidateRelayCommands(); } } private String _currentPath; public String CurrentPath { get { return _currentPath; } set { _currentPath = value; RaisePropertyChangedAuto(); } } public ObservableCollection FileHandlers { get; set; } public RelayCommand BackCommand { get; set; } public RelayCommand RefreshCommand { get; set; } public RelayCommand GoCommand { get; set; } public RelayCommand CancelFileHandlerCommand { get; set; } public RelayCommand OpenFileHandlerCommand { get; set; } public RelayCommand RemoveFileHandlerCommand { get; set; } public RelayCommand DownloadFileCommand { get; set; } public RelayCommand DeleteFileCommand { get; set; } public RelayCommand CreateFolderCommand { get; set; } public RelayCommand DeleteFolderCommand { get; set; } public RelayCommand UploadFileCommand { get; set; } public RelayCommand UploadVersionCommand { get; set; } public RelayCommand ValidateVersionCommand { get; set; } public RelayCommand ActivateVersionCommand { get; set; } public RelayCommand GenerateTfpCommand { get; set; } public MainViewVM() { } [TangoInject] public MainViewVM(IStudioApplicationManager applicationManager, INotificationProvider notificationProvider, IFirmwareUpgrader firmwareUpgrader) { _applicationManager = applicationManager; _notification = notificationProvider; _firmwareUpgrader = firmwareUpgrader; _applicationManager.ConnectedMachineChanged += _applicationManager_ConnectedMachineChanged; FileHandlers = new ObservableCollection(); GoCommand = new RelayCommand(() => NavigateToPath(CurrentPath), () => StorageManager != null); BackCommand = new RelayCommand(NavigateBack, () => StorageManager != null && StorageManager.CurrentFolder.Parent != null); CancelFileHandlerCommand = new RelayCommand(CancelFileHandler); OpenFileHandlerCommand = new RelayCommand(OpenFileHandler); RefreshCommand = new RelayCommand(Refresh, () => StorageManager != null); RemoveFileHandlerCommand = new RelayCommand(RemoveFileHandler); DownloadFileCommand = new RelayCommand(DownloadFile, () => StorageManager != null && SelectedStorageItem != null && SelectedStorageItem is StorageFile); DeleteFileCommand = new RelayCommand(DeleteFile, () => StorageManager != null && SelectedStorageItem != null && SelectedStorageItem is StorageFile); CreateFolderCommand = new RelayCommand(CreateFolder, () => StorageManager != null && StorageManager.CurrentFolder != null); DeleteFolderCommand = new RelayCommand(DeleteFolder, () => StorageManager != null && SelectedStorageItem != null && SelectedStorageItem is StorageFolder); UploadFileCommand = new RelayCommand(UploadFile, () => StorageManager != null && StorageManager.CurrentFolder != null); UploadVersionCommand = new RelayCommand(UploadVersion, () => StorageManager != null && StorageManager.CurrentFolder != null); ValidateVersionCommand = new RelayCommand(ValidateVersion, () => StorageManager != null && StorageManager.CurrentFolder != null); ActivateVersionCommand = new RelayCommand(ActivateVersion, () => StorageManager != null && StorageManager.CurrentFolder != null); GenerateTfpCommand = new RelayCommand(GenerateTFP); } private void UploadFile() { OpenFileDialog dlg = new OpenFileDialog(); dlg.Title = "Selected a file to upload"; if (dlg.ShowDialog().Value) { UploadFile(dlg.FileName); } } private async void DeleteFolder() { if (SelectedStorageItem == null) return; if (_notification.ShowQuestion("Are you sure you want to delete the selected folder?")) { try { IsFree = false; await StorageManager.DeleteItem(SelectedStorageItem); Refresh(); } catch (Exception ex) { _notification.ShowError($"Error deleting the selected folder.\n{ex.Message}"); } IsFree = true; } } private async void CreateFolder() { try { var name = _notification.ShowTextInput("Enter Folder Name", ""); if (!String.IsNullOrWhiteSpace(name)) { IsFree = false; await StorageManager.CreateFolder(Path.Combine(StorageManager.CurrentPath, name)); Refresh(); } } catch (Exception ex) { _notification.ShowError($"Error creating the new folder.\n{ex.Message}"); } IsFree = true; } private async void DeleteFile() { if (SelectedStorageItem == null) return; if (_notification.ShowQuestion("Are you sure you want to delete the selected file?")) { try { IsFree = false; await StorageManager.DeleteItem(SelectedStorageItem); Refresh(); } catch (Exception ex) { _notification.ShowError($"Error deleting the selected file.\n{ex.Message}"); } IsFree = true; } } private void DownloadFile() { DownloadStorageItem(SelectedStorageItem as StorageFile); } private void OpenFileHandler(StorageFileHandlerModel handler) { ShowInExplorer(handler.FilePath); } private async void CancelFileHandler(StorageFileHandlerModel handler) { await handler.Handler.Cancel(); } private void _applicationManager_ConnectedMachineChanged(object sender, IExternalBridgeClient e) { _machine_operator_changed = true; if (IsVisible) { Initialize(); } } public override void OnApplicationReady() { } public override void OnNavigatedTo() { base.OnNavigatedTo(); if (_machine_operator_changed) { _machine_operator_changed = false; Initialize(); } } private async void NavigateToPath(String path, bool raiseEvent = true) { IsFree = false; try { await StorageManager.GetFolder(path); CurrentPath = StorageManager.CurrentPath; if (raiseEvent) { CurrentFolderChanged?.Invoke(this, new EventArgs()); } } catch (Exception ex) { _notification.ShowError($"Error navigating to the specified path.\n{ex.Message}"); } IsFree = true; InvalidateRelayCommands(); } private async void Initialize() { if (_applicationManager.ConnectedMachine != null) { try { StorageManager = _applicationManager.ConnectedMachine.CreateStorageManager(); await StorageManager.GetStorageDrive(); await StorageManager.GetRootFolder(); CurrentPath = StorageManager.StorageDrive.Root; } catch (Exception ex) { _notification.ShowError($"An error occurred while trying to initialize the storage manager.\n{ex.Message}"); } InvalidateRelayCommands(); } } public void OnStorageItemDoubleClicked(StorageItem storageItem) { if (storageItem is StorageFolder && storageItem != null) { NavigateToPath(storageItem.Path); } else { DownloadStorageItem(storageItem as StorageFile); } } private void NavigateBack() { NavigateToPath(StorageManager.CurrentFolder.Parent); } private void Refresh() { NavigateToPath(StorageManager.CurrentFolder.Path, false); } private async void DownloadStorageItem(StorageFile storageFile) { SaveFileDialog dlg = new SaveFileDialog(); dlg.Title = "Select download location"; dlg.DefaultExt = Path.GetExtension(storageFile.Path); dlg.FileName = storageFile.Name; if (dlg.ShowDialog().Value) { FileStream fs = new FileStream(dlg.FileName, FileMode.Create); var handler = await StorageManager.DownloadFile(storageFile, fs); handler.Completed += (_, __) => { fs.Dispose(); }; handler.Canceled += (_, __) => { fs.Dispose(); File.Delete(dlg.FileName); }; handler.Failed += (_, __) => { fs.Dispose(); File.Delete(dlg.FileName); }; FileHandlers.Insert(0, new StorageFileHandlerModel(handler, dlg.FileName, StorageFileHandlerType.Download)); } } private async void UploadFile(String path) { FileStream fs = new FileStream(path, FileMode.Open); var handler = await StorageManager.UploadFile(Path.Combine(StorageManager.CurrentPath, Path.GetFileName(path)), fs); handler.Completed += (_, __) => { fs.Dispose(); }; handler.Canceled += (_, __) => { fs.Dispose(); }; handler.Failed += (_, __) => { fs.Dispose(); }; FileHandlers.Insert(0, new StorageFileHandlerModel(handler, path, StorageFileHandlerType.Upload)); } /// /// Shows the file in explorer. /// /// Name of the file/folder. public static void ShowInExplorer(String path) { Process.Start("explorer.exe", string.Format("/select,\"{0}\"", path)); } private void RemoveFileHandler(StorageFileHandlerModel handler) { if (handler.Handler.Status == StorageFileHandlerStatus.Active) { if (_notification.ShowQuestion("Are you sure you want to cancel this file operation?")) { handler.Handler.Cancel(); FileHandlers.Remove(handler); } } else { FileHandlers.Remove(handler); } } private void UploadVersion() { _firmwareUpgrader.InvokeUpgradeUI(); } private async void ValidateVersion() { using (_notification.PushTaskItem("Validating firmware version...")) { try { await _applicationManager.ConnectedMachine.ValidateFirmwareVersion(StorageManager.CurrentPath); _notification.ShowInfo($"Version validated successfully!"); } catch (Exception ex) { _notification.ShowError($"Error validating firmware version.\n{ex.FlattenMessage()}"); } } } private async void ActivateVersion() { using (_notification.PushTaskItem("Activating firmware version...")) { try { await _applicationManager.ConnectedMachine.ActivateFirmwareVersion(StorageManager.CurrentPath); _notification.ShowInfo($"Version activated successfully!"); } catch (Exception ex) { _notification.ShowError($"Error activating firmware version.\n{ex.FlattenMessage()}"); } } } private void GenerateTFP() { Tango.FirmwarePackageGenerator.MainWindow fWindow = new FirmwarePackageGenerator.MainWindow(); fWindow.Topmost = true; fWindow.Show(); _applicationManager.RegisterOpenedWindow(fWindow); } } }