setupToggleCommands

Library that creates toggleable menu commands for userscript managers

目前为 2024-06-16 提交的版本。查看 最新版本

此脚本不应直接安装,它是一个供其他脚本使用的外部库。如果您需要使用该库,请在脚本元属性加入:// @require https://update.cn-greasyfork.org/scripts/498119/1395413/setupToggleCommands.js

  1. // ==UserScript==
  2. // @name setupToggleCommands
  3. // @license MIT
  4. // @namespace rtonne
  5. // @match *://*/*
  6. // @version 1.0
  7. // @author Rtonne
  8. // @description Library that creates toggleable menu commands for userscript managers
  9. // @grant GM.registerMenuCommand
  10. // @grant GM.unregisterMenuCommand
  11. // @grant GM.getValue
  12. // @grant GM.setValue
  13. // ==/UserScript==
  14.  
  15. /**
  16. * Can be the only function of this library used externally.
  17. * @param {_Command[]} command_list The list of all toggle commands that are to be added.
  18. */
  19. async function setupToggleCommands(command_list) {
  20. for (const command of command_list) {
  21. _runCommandFunction(command);
  22. }
  23. for (const command of command_list) {
  24. await _registerCommand(command_list, command);
  25. }
  26. }
  27.  
  28. /**
  29. * @typedef {Object} _Command
  30. * @property {string} id The id of the menu command and the key for the value.
  31. * @property {boolean} default The default value.
  32. * @property {string} off_text The text displayed when the last function ran was toggleOffFunction.
  33. * @property {string} on_text The text displayed when the last function ran was toggleOnFunction.
  34. * @property {() => void} toggleOffFunction A function to be run then toggling off the command.
  35. * @property {() => void} toggleOnFunction A function to be run then toggling on the command.
  36. */
  37.  
  38. // To check if in place command replacement is supported
  39. // https://violentmonkey.github.io/api/gm/#gm_registermenucommand
  40. const _can_replace_in_place =
  41. "test" === GM.registerMenuCommand("test", () => {}, { id: "test" });
  42. GM.unregisterMenuCommand("test");
  43.  
  44. /**
  45. * Runs the correct command function, and toggles the command text.
  46. * @param {_Command[]} command_list The list of all commands (may be used to replace old commands).
  47. * @param {_Command} command The command being toggled.
  48. */
  49. async function _toggleCommand(command_list, command) {
  50. await GM.setValue(
  51. command.id,
  52. !(await GM.getValue(command.id, command.default))
  53. );
  54. _runCommandFunction(command);
  55. if (_can_replace_in_place) {
  56. await _registerCommand(command_list, command);
  57. } else {
  58. // If we can't replace commands, we need to remove them all, then re-add them
  59. for (const command of command_list) {
  60. GM.unregisterMenuCommand(command.id);
  61. }
  62. for (const command of command_list) {
  63. await _registerCommand(command_list, command);
  64. }
  65. }
  66. }
  67.  
  68. /**
  69. * Registers the command with the correct text.
  70. * @param {_Command[]} command_list The list of all commands (may be used to replace old commands).
  71. * @param {_Command} command
  72. */
  73. async function _registerCommand(command_list, command) {
  74. let text = command.on_text;
  75. if (!(await GM.getValue(command.id, command.default))) {
  76. text = command.off_text;
  77. }
  78.  
  79. GM.registerMenuCommand(text, () => _toggleCommand(command_list, command), {
  80. id: command.id,
  81. autoClose: false,
  82. });
  83. }
  84.  
  85. /**
  86. * Runs the correct command function.
  87. * @param {_Command} command
  88. */
  89. async function _runCommandFunction(command) {
  90. if (await GM.getValue(command.id, command.default)) {
  91. command.toggleOnFunction();
  92. } else {
  93. command.toggleOffFunction();
  94. }
  95. }