public void CreateShortcut(Game game) { try { var path = Environment.ExpandEnvironmentVariables(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory), Paths.GetSafeFilename(game.Name) + ".url")); string icon = string.Empty; if (!game.Icon.IsNullOrEmpty()) { icon = Database.GetFullFilePath(game.Icon); } else { icon = game.GetDefaultIcon(AppSettings, Database, Extensions.GetLibraryPlugin(game.PluginId)); if (!File.Exists(icon)) { icon = string.Empty; } } if (File.Exists(icon)) { if (Path.GetExtension(icon) != ".ico") { var targetIconPath = Path.Combine(PlaynitePaths.TempPath, Guid.NewGuid() + ".ico"); BitmapExtensions.ConvertToIcon(icon, targetIconPath); var md5 = FileSystem.GetMD5(targetIconPath); var existingFile = Path.Combine(PlaynitePaths.TempPath, md5 + ".ico"); if (File.Exists(existingFile)) { icon = existingFile; File.Delete(targetIconPath); } else { File.Move(targetIconPath, existingFile); icon = existingFile; } } } else { icon = PlaynitePaths.DesktopExecutablePath; } var args = new CmdLineOptions() { Start = game.Id.ToString() }.ToString(); Programs.CreateUrlShortcut($"playnite://playnite/start/{game.Id}", icon, path); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to create shortcut: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameShortcutError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } }
public void RemoveGame(Game game) { if (game.IsInstalling || game.IsRunning || game.IsLaunching || game.IsUninstalling) { Dialogs.ShowMessage( resources.GetString("LOCGameRemoveRunningError"), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } if (Dialogs.ShowMessage( resources.GetString("LOCGameRemoveAskMessage"), resources.GetString("LOCGameRemoveAskTitle"), MessageBoxButton.YesNo, MessageBoxImage.Question) != MessageBoxResult.Yes) { return; } if (Database.Games[game.Id] == null) { logger.Warn($"Failed to remove game {game.Name} {game.Id}, game doesn't exists anymore."); } else { Database.Games.Remove(game); } }
public void RemoveGames(List <Game> games) { if (games.Exists(a => a.IsInstalling || a.IsRunning || a.IsLaunching || a.IsUninstalling)) { Dialogs.ShowMessage( resources.GetString("LOCGameRemoveRunningError"), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } if (Dialogs.ShowMessage( string.Format(resources.GetString("LOCGamesRemoveAskMessage"), games.Count()), resources.GetString("LOCGameRemoveAskTitle"), MessageBoxButton.YesNo, MessageBoxImage.Question) != MessageBoxResult.Yes) { return; } foreach (var game in games.ToList()) { if (Database.Games[game.Id] == null) { logger.Warn($"Failed to remove game {game.Name} {game.Id}, game doesn't exists anymore."); games.Remove(game); } } Database.Games.Remove(games); }
public void OpenManual(Game game) { if (game.Manual.IsNullOrEmpty()) { return; } try { var manualPath = game.Manual; if (!manualPath.IsUri() && !File.Exists(manualPath)) { manualPath = Path.Combine(Database.GetFileStoragePath(game.Id), manualPath); } if (manualPath.IsUri()) { ProcessStarter.StartUrl(manualPath); } else { ProcessStarter.StartProcess(manualPath); } } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to open manual."); Dialogs.ShowMessage( string.Format(resources.GetString("LOCManualOpenError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } }
public void CreateShortcut(Game game) { try { var path = Environment.ExpandEnvironmentVariables(Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory), Paths.GetSafeFilename(game.Name) + ".lnk")); string icon = string.Empty; if (!string.IsNullOrEmpty(game.Icon) && Path.GetExtension(game.Icon) == ".ico") { icon = Database.GetFullFilePath(game.Icon); } else if (game.PlayAction?.Type == GameActionType.File) { icon = game.GetRawExecutablePath(); } var args = new CmdLineOptions() { Start = game.Id.ToString() }.ToString(); Programs.CreateShortcut(PlaynitePaths.DesktopExecutablePath, args, icon, path); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to create shortcut: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameShortcutError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } }
public void UnInstallGame(Game game) { if (game.IsRunning || game.IsLaunching) { Dialogs.ShowMessage( resources.GetString("LOCGameUninstallRunningError"), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } logger.Info($"Uninstalling {game.GetIdentifierInfo()}"); IGameController controller = null; try { controller = controllers.GetGameBasedController(game, Extensions); if (controller == null) { logger.Error("Game uninstallation failed, library plugin not found."); Dialogs.ShowErrorMessage( resources.GetString("LOCErrorLibraryPluginNotFound"), resources.GetString("LOCGameError")); return; } if (controller is GenericGameController) { logger.Error("Game uninstallation failed, library plugin doesn't provide game controller."); return; } controllers.RemoveController(game.Id); controllers.AddController(controller); UpdateGameState(game.Id, null, null, null, true, null); controller.Uninstall(); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Cannot un-install game: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameUninstallError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); if (controller != null) { controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, false, null); } } }
public void OpenGameLocation(Game game) { if (string.IsNullOrEmpty(game.InstallDirectory)) { return; } try { var installDirectory = game.InstallDirectory; if (!Directory.Exists(installDirectory)) { var newInstallDirectory = FileSystem.LookupAlternativeDirectoryPath(installDirectory); if (!string.IsNullOrWhiteSpace(newInstallDirectory)) { logger.Warn($"InstallDirectory \"{installDirectory}\" does not exist for game \"{game.Name}\"" + $" and is temporarily changed to {newInstallDirectory}"); installDirectory = newInstallDirectory; } } installDirectory = game.ExpandVariables(installDirectory); if (AppSettings.DirectoryOpenCommand.IsNullOrWhiteSpace()) { Process.Start(installDirectory); } else { try { ProcessStarter.ShellExecute(AppSettings.DirectoryOpenCommand.Replace("{Dir}", installDirectory)); } catch (Exception e) { logger.Error(e, "Failed to open directory using custom command."); Process.Start(installDirectory); } } } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Cannot open game location: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameOpenLocationError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } }
public void ActivateAction(Game game, GameAction action) { try { var emulators = Database.Emulators.ToList(); var profile = GameActionActivator.GetGameActionEmulatorConfig(action, emulators)?.ExpandVariables(game); GameActionActivator.ActivateAction(action.ExpandVariables(game), profile); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartActionError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } }
public void OpenGameLocation(Game game) { if (string.IsNullOrEmpty(game.InstallDirectory)) { return; } try { Process.Start(game.ExpandVariables(game.InstallDirectory)); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameOpenLocationError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } }
public void RemoveGame(Game game) { if (game.IsInstalling || game.IsRunning || game.IsLaunching || game.IsUninstalling) { Dialogs.ShowMessage( resources.GetString("LOCGameRemoveRunningError"), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } if (Dialogs.ShowMessage( resources.GetString("LOCGameRemoveAskMessage"), resources.GetString("LOCGameRemoveAskTitle"), MessageBoxButton.YesNo, MessageBoxImage.Question) != MessageBoxResult.Yes) { return; } Database.Games.Remove(game); }
public void RemoveGames(List <Game> games) { if (games.Exists(a => a.IsInstalling || a.IsRunning || a.IsLaunching || a.IsUninstalling)) { Dialogs.ShowMessage( resources.GetString("LOCGameRemoveRunningError"), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } if (Dialogs.ShowMessage( string.Format(resources.GetString("LOCGamesRemoveAskMessage"), games.Count()), resources.GetString("LOCGameRemoveAskTitle"), MessageBoxButton.YesNo, MessageBoxImage.Question) != MessageBoxResult.Yes) { return; } Database.Games.Remove(games); }
public void PlayGame(Game game) { if (!game.IsInstalled) { InstallGame(game); return; } logger.Info($"Starting {game.GetIdentifierInfo()}"); var dbGame = Database.Games.Get(game.Id); if (dbGame == null) { Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartErrorNoGame"), game.Name), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); UpdateJumpList(); return; } IGameController controller = null; try { if (game.IsRunning || game.IsLaunching) { logger.Warn("Failed to start the game, game is already running/launching."); return; } if (game.PlayAction == null) { Dialogs.ShowErrorMessage( resources.GetString("LOCErrorNoPlayAction"), resources.GetString("LOCGameError")); return; } if (game.PlayAction.IsHandledByPlugin) { logger.Info("Using library plugin to start the game."); controller = controllers.GetGameBasedController(game, Extensions); } else { logger.Info("Using generic controller start the game."); controller = controllers.GetGenericGameController(game); } if (controller == null) { Dialogs.ShowErrorMessage( resources.GetString("LOCErrorLibraryPluginNotFound"), resources.GetString("LOCGameError")); return; } controllers.RemoveController(game.Id); controllers.AddController(controller); UpdateGameState(game.Id, null, null, null, null, true); if (!game.IsCustomGame && shutdownJobs.TryGetValue(game.PluginId, out var existingJob)) { logger.Debug($"Starting game with existing client shutdown job, canceling job {game.PluginId}."); existingJob.CancelToken.Cancel(); shutdownJobs.TryRemove(game.PluginId, out var _); } if (!AppSettings.PreScript.IsNullOrWhiteSpace()) { try { var expanded = game.ExpandVariables(AppSettings.PreScript); ExecuteScriptAction(AppSettings.ActionsScriptLanguage, expanded, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { var message = exc.Message; if (exc is ScriptRuntimeException err) { message = err.Message + "\n\n" + err.ScriptStackTrace; } logger.Error(exc, "Failed to execute global pre-script action."); logger.Error(AppSettings.PreScript); Dialogs.ShowMessage( message, resources.GetString("LOCErrorGlobalScriptAction"), MessageBoxButton.OK, MessageBoxImage.Error); controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); return; } } if (!game.PreScript.IsNullOrWhiteSpace()) { try { var expanded = game.ExpandVariables(game.PreScript); ExecuteScriptAction(game.ActionsScriptLanguage, expanded, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { var message = exc.Message; if (exc is ScriptRuntimeException err) { message = err.Message + "\n\n" + err.ScriptStackTrace; } logger.Error(exc, "Failed to execute game's pre-script action."); logger.Error(game.PreScript); Dialogs.ShowMessage( message, resources.GetString("LOCErrorGameScriptAction"), MessageBoxButton.OK, MessageBoxImage.Error); controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); return; } } controller.Play(); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Cannot start game: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); if (controller != null) { controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); } return; } UpdateJumpList(); }
public void PlayGame(Game game) { if (!game.IsInstalled) { InstallGame(game); return; } logger.Info($"Starting {game.GetIdentifierInfo()}"); var dbGame = Database.Games.Get(game.Id); if (dbGame == null) { Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartErrorNoGame"), game.Name), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); UpdateJumpList(); return; } IGameController controller = null; try { if (game.IsRunning) { logger.Warn("Failed to start the game, game is already running."); return; } if (game.PlayAction.IsHandledByPlugin) { logger.Info("Using library plugin to start the game."); controller = controllers.GetGameBasedController(game, Extensions); } else { logger.Info("Using generic controller start the game."); controller = controllers.GetGenericGameController(game); } if (controller == null) { Dialogs.ShowErrorMessage( resources.GetString("LOCErrorLibraryPluginNotFound"), resources.GetString("LOCGameError")); return; } controllers.RemoveController(game.Id); controllers.AddController(controller); UpdateGameState(game.Id, null, null, null, null, true); controller.Play(); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { if (controller != null) { controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); } logger.Error(exc, "Cannot start game: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } try { UpdateJumpList(); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to set jump list data: "); } }
public void PlayGame(Game game) { if (!game.IsInstalled) { InstallGame(game); return; } logger.Info($"Starting {game.GetIdentifierInfo()}"); var dbGame = Database.Games.Get(game.Id); if (dbGame == null) { Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartErrorNoGame"), game.Name), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); UpdateJumpList(); return; } IGameController controller = null; try { if (game.IsRunning || game.IsLaunching) { logger.Warn("Failed to start the game, game is already running/launching."); return; } if (game.PlayAction == null) { Dialogs.ShowErrorMessage( resources.GetString("LOCErrorNoPlayAction"), resources.GetString("LOCGameError")); return; } if (game.PlayAction.IsHandledByPlugin) { logger.Info("Using library plugin to start the game."); controller = controllers.GetGameBasedController(game, Extensions); } else { logger.Info("Using generic controller start the game."); controller = controllers.GetGenericGameController(game); } if (controller == null) { Dialogs.ShowErrorMessage( resources.GetString("LOCErrorLibraryPluginNotFound"), resources.GetString("LOCGameError")); return; } controllers.RemoveController(game.Id); controllers.AddController(controller); UpdateGameState(game.Id, null, null, null, null, true); if (!AppSettings.PreScript.IsNullOrWhiteSpace()) { try { ExecuteScriptAction(AppSettings.ActionsScriptLanguage, AppSettings.PreScript, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to execute global pre-script action."); logger.Error(AppSettings.PreScript); Dialogs.ShowMessage( string.Format(resources.GetString("LOCErrorGlobalScriptAction"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); return; } } if (!game.PreScript.IsNullOrWhiteSpace()) { try { ExecuteScriptAction(game.ActionsScriptLanguage, game.PreScript, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to execute game's pre-script action."); logger.Error(game.PreScript); Dialogs.ShowMessage( string.Format(resources.GetString("LOCErrorGameScriptAction"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); return; } } controller.Play(); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { if (controller != null) { controllers.RemoveController(game.Id); UpdateGameState(game.Id, null, null, null, null, false); } logger.Error(exc, "Cannot start game: "); Dialogs.ShowMessage( string.Format(resources.GetString("LOCGameStartError"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); return; } UpdateJumpList(); }
private void Controllers_Started(object sender, GameControllerEventArgs args) { var game = args.Controller.Game; logger.Info($"Started {game.Name} game."); UpdateGameState(game.Id, null, true, null, null, false); gameStartups.TryAdd(game.Id, DateTime.Now); if (!AppSettings.GameStartedScript.IsNullOrWhiteSpace() && game.UseGlobalGameStartedScript) { try { var expanded = game.ExpandVariables(AppSettings.GameStartedScript); ExecuteScriptAction(AppSettings.ActionsScriptLanguage, expanded, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { var message = exc.Message; if (exc is ScriptRuntimeException err) { message = err.Message + "\n\n" + err.ScriptStackTrace; } logger.Error(exc, "Failed to execute global game-started action."); logger.Error(AppSettings.GameStartedScript); Dialogs.ShowMessage( message, resources.GetString("LOCErrorGlobalScriptAction"), MessageBoxButton.OK, MessageBoxImage.Error); } } if (!game.GameStartedScript.IsNullOrWhiteSpace()) { try { var expanded = game.ExpandVariables(game.GameStartedScript); ExecuteScriptAction(game.ActionsScriptLanguage, expanded, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { var message = exc.Message; if (exc is ScriptRuntimeException err) { message = err.Message + "\n\n" + err.ScriptStackTrace; } logger.Error(exc, "Failed to execute game's game-started action."); logger.Error(game.GameStartedScript); Dialogs.ShowMessage( message, resources.GetString("LOCErrorGameScriptAction"), MessageBoxButton.OK, MessageBoxImage.Error); } } if (Application.Mode == ApplicationMode.Desktop) { if (AppSettings.AfterLaunch == AfterLaunchOptions.Close) { Application.Quit(); } else if (AppSettings.AfterLaunch == AfterLaunchOptions.Minimize) { Application.Minimize(); } } else { if (AppSettings.AfterLaunch == AfterLaunchOptions.Close) { Application.Quit(); } else { Application.Minimize(); } } if (AppSettings.DiscordPresenceEnabled) { Application.Discord?.SetPresence(game.Name); } }
public void RemoveGames(List <Game> games) { if (games.Exists(a => a.IsInstalling || a.IsRunning || a.IsLaunching || a.IsUninstalling)) { Dialogs.ShowMessage( "LOCGameRemoveRunningError", "LOCGameError", MessageBoxButton.OK, MessageBoxImage.Error); return; } var addToExclusionList = false; if (games.All(a => a.IsCustomGame)) { if (Dialogs.ShowMessage( string.Format(resources.GetString("LOCGamesRemoveAskMessage"), games.Count()), "LOCGameRemoveAskTitle", MessageBoxButton.YesNo, MessageBoxImage.Question) != MessageBoxResult.Yes) { return; } } else { var options = new List <MessageBoxOption> { new MessageBoxOption("LOCRemoveAskAddToExlusionListYesResponse"), new MessageBoxOption("LOCYesLabel", true), new MessageBoxOption("LOCNoLabel", false, true) }; var result = Dialogs.ShowMessage( string.Format(resources.GetString("LOCGamesRemoveAskMessageIgnoreOption"), games.Count()), "LOCGameRemoveAskTitle", MessageBoxImage.Question, options); if (result == options[0]) { addToExclusionList = true; } else if (result == options[2]) { return; } } foreach (var game in games.ToList()) { if (Database.Games[game.Id] == null) { logger.Warn($"Failed to remove game {game.Name} {game.Id}, game doesn't exists anymore."); games.Remove(game); } if (addToExclusionList && !game.IsCustomGame) { AppSettings.ImportExclusionList.Add(game.GameId, game.Name, game.PluginId, Extensions.GetLibraryPlugin(game.PluginId)?.Name); } } Database.Games.Remove(games); }
private void Controllers_Stopped(object sender, GameControllerEventArgs args) { var game = args.Controller.Game; logger.Info($"Game {game.Name} stopped after {args.EllapsedTime} seconds."); var dbGame = Database.Games.Get(game.Id); dbGame.IsRunning = false; dbGame.IsLaunching = false; dbGame.Playtime += args.EllapsedTime; Database.Games.Update(dbGame); controllers.RemoveController(args.Controller); if (Application.Mode == ApplicationMode.Desktop) { if (AppSettings.AfterGameClose == AfterGameCloseOptions.Restore) { Application.Restore(); } } else { // The delay should hopefully fix rare cases where Fullscreen mode doesn't get proper focus after restore. // https://www.reddit.com/r/playnite/comments/f6d73l/bug_full_screen_ui_wont_respond_to_left_stick/ Task.Delay(TimeSpan.FromSeconds(2)).ContinueWith(a => Application.Restore()); } if (!game.PostScript.IsNullOrWhiteSpace()) { try { var expanded = game.ExpandVariables(game.PostScript); ExecuteScriptAction(game.ActionsScriptLanguage, expanded, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { var message = exc.Message; if (exc is ScriptRuntimeException err) { message = err.Message + "\n\n" + err.ScriptStackTrace; } logger.Error(exc, "Failed to execute game's post-script action."); logger.Error(game.PostScript); Dialogs.ShowMessage( message, resources.GetString("LOCErrorGameScriptAction"), MessageBoxButton.OK, MessageBoxImage.Error); } } if (!AppSettings.PostScript.IsNullOrWhiteSpace()) { try { var expanded = game.ExpandVariables(AppSettings.PostScript); ExecuteScriptAction(AppSettings.ActionsScriptLanguage, expanded, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { var message = exc.Message; if (exc is ScriptRuntimeException err) { message = err.Message + "\n\n" + err.ScriptStackTrace; } logger.Error(exc, "Failed to execute global post-script action."); logger.Error(AppSettings.PostScript); Dialogs.ShowMessage( message, resources.GetString("LOCErrorGlobalScriptAction"), MessageBoxButton.OK, MessageBoxImage.Error); } } if (AppSettings.ClientAutoShutdown.ShutdownClients && !game.IsCustomGame) { if (args.EllapsedTime <= AppSettings.ClientAutoShutdown.MinimalSessionTime) { logger.Debug("Game session was too short for client to be shutdown."); } else { var plugin = Extensions.GetLibraryPlugin(game.PluginId); if (plugin?.Capabilities?.CanShutdownClient == true && AppSettings.ClientAutoShutdown.ShutdownPlugins.Contains(plugin.Id)) { if (shutdownJobs.TryGetValue(game.PluginId, out var existingJob)) { existingJob.CancelToken.Cancel(); shutdownJobs.TryRemove(game.PluginId, out var _); } var newJob = new ClientShutdownJob { PluginId = plugin.Id, CancelToken = new CancellationTokenSource() }; var task = new Task(async() => { var ct = newJob.CancelToken; var libPlugin = plugin; var timeout = AppSettings.ClientAutoShutdown.GraceTimeout; var curTime = 0; logger.Info($"Scheduled {libPlugin.Name} to be closed after {timeout} seconds."); while (curTime < timeout) { if (ct.IsCancellationRequested) { logger.Debug($"Client {libPlugin.Name} shutdown canceled."); return; } await Task.Delay(1000); curTime++; } if (curTime >= timeout) { try { shutdownJobs.TryRemove(libPlugin.Id, out var _); libPlugin.Client.Shutdown(); } catch (Exception e) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(e, $"Failed to shutdown {libPlugin.Name} client."); } } }); newJob.CancelTask = task; shutdownJobs.TryAdd(plugin.Id, newJob); newJob.CancelTask.Start(); } } } }
private void Controllers_Stopped(object sender, GameControllerEventArgs args) { var game = args.Controller.Game; logger.Info($"Game {game.Name} stopped after {args.EllapsedTime} seconds."); var dbGame = Database.Games.Get(game.Id); dbGame.IsRunning = false; dbGame.IsLaunching = false; dbGame.Playtime += args.EllapsedTime; Database.Games.Update(dbGame); controllers.RemoveController(args.Controller); if (Application.Mode == ApplicationMode.Desktop) { if (AppSettings.AfterGameClose == AfterGameCloseOptions.Restore) { Application.Restore(); } } else { Application.Restore(); } if (!game.PostScript.IsNullOrWhiteSpace()) { try { ExecuteScriptAction(game.ActionsScriptLanguage, game.PostScript, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to execute game's post-script action."); logger.Error(game.PostScript); Dialogs.ShowMessage( string.Format(resources.GetString("LOCErrorGameScriptAction"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } } if (!AppSettings.PostScript.IsNullOrWhiteSpace()) { try { ExecuteScriptAction(AppSettings.ActionsScriptLanguage, AppSettings.PostScript, game); } catch (Exception exc) when(!PlayniteEnvironment.ThrowAllErrors) { logger.Error(exc, "Failed to execute global post-script action."); logger.Error(AppSettings.PostScript); Dialogs.ShowMessage( string.Format(resources.GetString("LOCErrorGlobalScriptAction"), exc.Message), resources.GetString("LOCGameError"), MessageBoxButton.OK, MessageBoxImage.Error); } } }