91 Plus

自由轉調、輕鬆練歌,打造 91 譜的最佳體驗!

目前為 2023-12-13 提交的版本,檢視 最新版本

// ==UserScript==
// @name         91 Plus
// @namespace    https://github.com/DonkeyBear
// @version      1.2.0
// @author       DonkeyBear
// @description  自由轉調、輕鬆練歌,打造 91 譜的最佳體驗!
// @icon         https://www.91pu.com.tw/icons/favicon-32x32.png
// @match        *://www.91pu.com.tw/m/*
// @match        *://www.91pu.com.tw/song/*
// @require      https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.global.prod.js
// @grant        GM_addStyle
// @grant        GM_getValue
// @grant        GM_setValue
// @antifeature  tracking  使用 Google Analytics 了解使用情況
// ==/UserScript==

(e=>{if(typeof GM_addStyle=="function"){GM_addStyle(e);return}const a=document.createElement("style");a.textContent=e,document.head.append(a)})(" #trigger-overlay[data-v-1d03dd38]{position:fixed;top:0;left:0;right:0;bottom:0;z-index:500}.material-symbols-rounded[data-v-db75303e]{cursor:pointer;-webkit-user-select:none;user-select:none;color:var(--46f2ba82);font-size:1.25rem;padding:0 .75rem}.slide-and-fade-enter-active[data-v-95b1456e],.slide-and-fade-leave-active[data-v-95b1456e]{transition:all .2s}.slide-and-fade-enter-from[data-v-95b1456e],.slide-and-fade-leave-to[data-v-95b1456e]{transform:translateY(10%);opacity:0}#plus91-sheet-popup[data-v-95b1456e]{position:absolute;left:0;right:0;bottom:3rem;background:#fafafa;border:1px solid lightgray;padding:1rem 2rem;border-radius:1rem;margin:0 1rem}.transpose-range-container input[type=range][data-v-95b1456e]{width:100%}.transpose-button-group[data-v-95b1456e]{display:flex;margin-bottom:1rem}.transpose-button-group .capo-button[data-v-95b1456e]{border:0;background:transparent}.transpose-button-group .capo-button.info[data-v-95b1456e]{flex-grow:1}.transpose-button-group .capo-button.increase[data-v-95b1456e]{padding-left:1rem}.transpose-button-group .capo-button.decrease[data-v-95b1456e]{padding-right:1rem}.slide-and-fade-enter-active[data-v-f2a3726b],.slide-and-fade-leave-active[data-v-f2a3726b]{transition:all .2s}.slide-and-fade-enter-from[data-v-f2a3726b],.slide-and-fade-leave-to[data-v-f2a3726b]{transform:translateY(10%);opacity:0}#plus91-font-popup[data-v-f2a3726b]{position:absolute;left:0;right:0;bottom:3rem;background:#fafafa;border:1px solid lightgray;padding:1rem 2rem;border-radius:1rem;margin:0 1rem}.font-button-group[data-v-f2a3726b]{display:flex}.font-button-group .capo-button[data-v-f2a3726b]{border:0;background:transparent}.font-button-group .capo-button.info[data-v-f2a3726b]{flex-grow:1}.font-button-group .capo-button.increase[data-v-f2a3726b]{padding-left:1rem}.font-button-group .capo-button.decrease[data-v-f2a3726b]{padding-right:1rem}.slide-and-fade-enter-active[data-v-430d5768],.slide-and-fade-leave-active[data-v-430d5768]{transition:all .2s}.slide-and-fade-enter-from[data-v-430d5768],.slide-and-fade-leave-to[data-v-430d5768]{transform:translateY(10%);opacity:0}#plus91-settings-popup[data-v-430d5768]{position:absolute;left:0;right:0;bottom:3rem;background:#fafafa;border:1px solid lightgray;border-radius:1rem;margin:0 1rem;padding:1rem}#plus91-settings-popup .setting-item[data-v-430d5768]{display:flex;align-items:center;justify-content:space-between;padding:.5rem 1rem;border-radius:.5rem;cursor:pointer}#plus91-settings-popup .setting-item[data-v-430d5768]:hover{background:rgba(0,0,0,.05)}.icon-button[data-v-29985f23]{display:flex;flex-direction:column;align-items:center;cursor:pointer}.icon-button .button-text[data-v-29985f23]{font-size:.5rem;color:var(--045d7cb5)}.slide-and-fade-enter-active[data-v-f742366d],.slide-and-fade-leave-active[data-v-f742366d]{transition:all .2s}.slide-and-fade-enter-from[data-v-f742366d],.slide-and-fade-leave-to[data-v-f742366d]{transform:translateY(10%);opacity:0}#plus91-menu-popup[data-v-f742366d]{position:absolute;left:0;right:0;bottom:3rem;background:#fafafa;border:1px solid lightgray;padding:1rem 2rem;border-radius:1rem;margin:0 1rem}#plus91-menu-popup .menu-popup-container[data-v-f742366d]{display:flex;justify-content:space-around}.slide-enter-active[data-v-d937ce2c],.slide-leave-active[data-v-d937ce2c]{transition:transform .2s}.slide-enter-from[data-v-d937ce2c],.slide-leave-to[data-v-d937ce2c]{transform:translateY(100%)}#plus91-footer[data-v-d937ce2c]{z-index:800;display:flex;justify-content:center;position:fixed;left:0;right:0;bottom:0}.footer-container[data-v-d937ce2c]{width:min(100vw,768px);background:rgba(50,80,200,.5);-webkit-backdrop-filter:blur(3px);backdrop-filter:blur(3px);padding:.6rem;display:flex;justify-content:space-between;align-items:center;border-radius:1rem 1rem 0 0}.slide-enter-active[data-v-183b97c5],.slide-leave-active[data-v-183b97c5]{transition:transform .2s}.slide-enter-from[data-v-183b97c5],.slide-leave-to[data-v-183b97c5]{transform:translateY(-100%)}#plus91-header[data-v-183b97c5]{z-index:800;display:flex;justify-content:center;position:fixed;left:0;right:0;top:0}.header-container[data-v-183b97c5]{width:min(100vw,768px);background:rgba(50,80,200,.5);-webkit-backdrop-filter:blur(3px);backdrop-filter:blur(3px);padding:.6rem;display:flex;justify-content:space-between;align-items:center;border-radius:0 0 1rem 1rem}.header-container input[data-v-183b97c5]{flex-grow:1;width:100%;border-radius:50rem;border:0;font-size:.75rem;padding:.35rem 1rem;background:rgba(255,255,255,.6666666667);color:#0009;opacity:.5;transition:all .2s}.header-container input[data-v-183b97c5]:focus-visible{outline:0;opacity:1}.fade-enter-active[data-v-a07a2507],.fade-leave-active[data-v-a07a2507]{transition:opacity .2s}.fade-enter-from[data-v-a07a2507],.fade-leave-to[data-v-a07a2507]{opacity:0}#dark-mode-overlay[data-v-a07a2507]{position:fixed;top:0;left:0;right:0;bottom:0;z-index:1000;-webkit-backdrop-filter:invert(1) hue-rotate(145deg) saturate(.75);backdrop-filter:invert(1) hue-rotate(145deg) saturate(.75);pointer-events:none}html{background:#fafafa url(/templets/pu/images/tone-bg.gif)}.tfunc2{margin:10px}#mtitle{font-family:system-ui}input[type=range],input[type=range]::-webkit-slider-thumb,input[type=range]::-webkit-slider-runnable-track{-webkit-appearance:none;box-shadow:none}input[type=range]::-webkit-slider-thumb,input[type=range]::-webkit-slider-runnable-track{border:1px solid rgba(0,0,128,.2)}input[type=range]::-webkit-slider-thumb{background:rgb(141,193,226)}#viptoneWindow.window,#bottomad,.update_vip_bar,.wmask,header,footer,.autoscroll,.backplace,.set .keys,.set .plays,.set .clear,.setint .hr:nth-child(4),.setint .hr:nth-child(5),.setint .hr:nth-child(6),.adsbygoogle{display:none!important} ");

(function (vue) {
  'use strict';

  var __defProp = Object.defineProperty;
  var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
  var __publicField = (obj, key, value) => {
    __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
    return value;
  };
  var __accessCheck = (obj, member, msg) => {
    if (!member.has(obj))
      throw TypeError("Cannot " + msg);
  };
  var __privateGet = (obj, member, getter) => {
    __accessCheck(obj, member, "read from private field");
    return getter ? getter.call(obj) : member.get(obj);
  };
  var __privateAdd = (obj, member, value) => {
    if (member.has(obj))
      throw TypeError("Cannot add the same private member more than once");
    member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
  };
  var __privateSet = (obj, member, value, setter) => {
    __accessCheck(obj, member, "write to private field");
    setter ? setter.call(obj, value) : member.set(obj, value);
    return value;
  };
  var __privateMethod = (obj, member, method) => {
    __accessCheck(obj, member, "access private method");
    return method;
  };
  var _unformat, unformat_fn, _store, _watchTranspose, watchTranspose_fn, _watchFontSize, watchFontSize_fn;
  var isVue2 = false;
  /*!
   * pinia v2.1.7
   * (c) 2023 Eduardo San Martin Morote
   * @license MIT
   */
  let activePinia;
  const setActivePinia = (pinia2) => activePinia = pinia2;
  const piniaSymbol = (
    /* istanbul ignore next */
    Symbol()
  );
  function isPlainObject(o) {
    return o && typeof o === "object" && Object.prototype.toString.call(o) === "[object Object]" && typeof o.toJSON !== "function";
  }
  var MutationType;
  (function(MutationType2) {
    MutationType2["direct"] = "direct";
    MutationType2["patchObject"] = "patch object";
    MutationType2["patchFunction"] = "patch function";
  })(MutationType || (MutationType = {}));
  function createPinia() {
    const scope = vue.effectScope(true);
    const state = scope.run(() => vue.ref({}));
    let _p = [];
    let toBeInstalled = [];
    const pinia2 = vue.markRaw({
      install(app) {
        setActivePinia(pinia2);
        {
          pinia2._a = app;
          app.provide(piniaSymbol, pinia2);
          app.config.globalProperties.$pinia = pinia2;
          toBeInstalled.forEach((plugin) => _p.push(plugin));
          toBeInstalled = [];
        }
      },
      use(plugin) {
        if (!this._a && !isVue2) {
          toBeInstalled.push(plugin);
        } else {
          _p.push(plugin);
        }
        return this;
      },
      _p,
      // it's actually undefined here
      // @ts-expect-error
      _a: null,
      _e: scope,
      _s: /* @__PURE__ */ new Map(),
      state
    });
    return pinia2;
  }
  const noop = () => {
  };
  function addSubscription(subscriptions, callback, detached, onCleanup = noop) {
    subscriptions.push(callback);
    const removeSubscription = () => {
      const idx = subscriptions.indexOf(callback);
      if (idx > -1) {
        subscriptions.splice(idx, 1);
        onCleanup();
      }
    };
    if (!detached && vue.getCurrentScope()) {
      vue.onScopeDispose(removeSubscription);
    }
    return removeSubscription;
  }
  function triggerSubscriptions(subscriptions, ...args) {
    subscriptions.slice().forEach((callback) => {
      callback(...args);
    });
  }
  const fallbackRunWithContext = (fn) => fn();
  function mergeReactiveObjects(target, patchToApply) {
    if (target instanceof Map && patchToApply instanceof Map) {
      patchToApply.forEach((value, key) => target.set(key, value));
    }
    if (target instanceof Set && patchToApply instanceof Set) {
      patchToApply.forEach(target.add, target);
    }
    for (const key in patchToApply) {
      if (!patchToApply.hasOwnProperty(key))
        continue;
      const subPatch = patchToApply[key];
      const targetValue = target[key];
      if (isPlainObject(targetValue) && isPlainObject(subPatch) && target.hasOwnProperty(key) && !vue.isRef(subPatch) && !vue.isReactive(subPatch)) {
        target[key] = mergeReactiveObjects(targetValue, subPatch);
      } else {
        target[key] = subPatch;
      }
    }
    return target;
  }
  const skipHydrateSymbol = (
    /* istanbul ignore next */
    Symbol()
  );
  function shouldHydrate(obj) {
    return !isPlainObject(obj) || !obj.hasOwnProperty(skipHydrateSymbol);
  }
  const { assign } = Object;
  function isComputed(o) {
    return !!(vue.isRef(o) && o.effect);
  }
  function createOptionsStore(id, options, pinia2, hot) {
    const { state, actions, getters } = options;
    const initialState = pinia2.state.value[id];
    let store;
    function setup() {
      if (!initialState && true) {
        {
          pinia2.state.value[id] = state ? state() : {};
        }
      }
      const localState = vue.toRefs(pinia2.state.value[id]);
      return assign(localState, actions, Object.keys(getters || {}).reduce((computedGetters, name) => {
        computedGetters[name] = vue.markRaw(vue.computed(() => {
          setActivePinia(pinia2);
          const store2 = pinia2._s.get(id);
          return getters[name].call(store2, store2);
        }));
        return computedGetters;
      }, {}));
    }
    store = createSetupStore(id, setup, options, pinia2, hot, true);
    return store;
  }
  function createSetupStore($id, setup, options = {}, pinia2, hot, isOptionsStore) {
    let scope;
    const optionsForPlugin = assign({ actions: {} }, options);
    const $subscribeOptions = {
      deep: true
      // flush: 'post',
    };
    let isListening;
    let isSyncListening;
    let subscriptions = [];
    let actionSubscriptions = [];
    let debuggerEvents;
    const initialState = pinia2.state.value[$id];
    if (!isOptionsStore && !initialState && true) {
      {
        pinia2.state.value[$id] = {};
      }
    }
    vue.ref({});
    let activeListener;
    function $patch(partialStateOrMutator) {
      let subscriptionMutation;
      isListening = isSyncListening = false;
      if (typeof partialStateOrMutator === "function") {
        partialStateOrMutator(pinia2.state.value[$id]);
        subscriptionMutation = {
          type: MutationType.patchFunction,
          storeId: $id,
          events: debuggerEvents
        };
      } else {
        mergeReactiveObjects(pinia2.state.value[$id], partialStateOrMutator);
        subscriptionMutation = {
          type: MutationType.patchObject,
          payload: partialStateOrMutator,
          storeId: $id,
          events: debuggerEvents
        };
      }
      const myListenerId = activeListener = Symbol();
      vue.nextTick().then(() => {
        if (activeListener === myListenerId) {
          isListening = true;
        }
      });
      isSyncListening = true;
      triggerSubscriptions(subscriptions, subscriptionMutation, pinia2.state.value[$id]);
    }
    const $reset = isOptionsStore ? function $reset2() {
      const { state } = options;
      const newState = state ? state() : {};
      this.$patch(($state) => {
        assign($state, newState);
      });
    } : (
      /* istanbul ignore next */
      noop
    );
    function $dispose() {
      scope.stop();
      subscriptions = [];
      actionSubscriptions = [];
      pinia2._s.delete($id);
    }
    function wrapAction(name, action) {
      return function() {
        setActivePinia(pinia2);
        const args = Array.from(arguments);
        const afterCallbackList = [];
        const onErrorCallbackList = [];
        function after(callback) {
          afterCallbackList.push(callback);
        }
        function onError(callback) {
          onErrorCallbackList.push(callback);
        }
        triggerSubscriptions(actionSubscriptions, {
          args,
          name,
          store,
          after,
          onError
        });
        let ret;
        try {
          ret = action.apply(this && this.$id === $id ? this : store, args);
        } catch (error) {
          triggerSubscriptions(onErrorCallbackList, error);
          throw error;
        }
        if (ret instanceof Promise) {
          return ret.then((value) => {
            triggerSubscriptions(afterCallbackList, value);
            return value;
          }).catch((error) => {
            triggerSubscriptions(onErrorCallbackList, error);
            return Promise.reject(error);
          });
        }
        triggerSubscriptions(afterCallbackList, ret);
        return ret;
      };
    }
    const partialStore = {
      _p: pinia2,
      // _s: scope,
      $id,
      $onAction: addSubscription.bind(null, actionSubscriptions),
      $patch,
      $reset,
      $subscribe(callback, options2 = {}) {
        const removeSubscription = addSubscription(subscriptions, callback, options2.detached, () => stopWatcher());
        const stopWatcher = scope.run(() => vue.watch(() => pinia2.state.value[$id], (state) => {
          if (options2.flush === "sync" ? isSyncListening : isListening) {
            callback({
              storeId: $id,
              type: MutationType.direct,
              events: debuggerEvents
            }, state);
          }
        }, assign({}, $subscribeOptions, options2)));
        return removeSubscription;
      },
      $dispose
    };
    const store = vue.reactive(partialStore);
    pinia2._s.set($id, store);
    const runWithContext = pinia2._a && pinia2._a.runWithContext || fallbackRunWithContext;
    const setupStore = runWithContext(() => pinia2._e.run(() => (scope = vue.effectScope()).run(setup)));
    for (const key in setupStore) {
      const prop = setupStore[key];
      if (vue.isRef(prop) && !isComputed(prop) || vue.isReactive(prop)) {
        if (!isOptionsStore) {
          if (initialState && shouldHydrate(prop)) {
            if (vue.isRef(prop)) {
              prop.value = initialState[key];
            } else {
              mergeReactiveObjects(prop, initialState[key]);
            }
          }
          {
            pinia2.state.value[$id][key] = prop;
          }
        }
      } else if (typeof prop === "function") {
        const actionValue = wrapAction(key, prop);
        {
          setupStore[key] = actionValue;
        }
        optionsForPlugin.actions[key] = prop;
      } else
        ;
    }
    {
      assign(store, setupStore);
      assign(vue.toRaw(store), setupStore);
    }
    Object.defineProperty(store, "$state", {
      get: () => pinia2.state.value[$id],
      set: (state) => {
        $patch(($state) => {
          assign($state, state);
        });
      }
    });
    pinia2._p.forEach((extender) => {
      {
        assign(store, scope.run(() => extender({
          store,
          app: pinia2._a,
          pinia: pinia2,
          options: optionsForPlugin
        })));
      }
    });
    if (initialState && isOptionsStore && options.hydrate) {
      options.hydrate(store.$state, initialState);
    }
    isListening = true;
    isSyncListening = true;
    return store;
  }
  function defineStore(idOrOptions, setup, setupOptions) {
    let id;
    let options;
    const isSetupStore = typeof setup === "function";
    if (typeof idOrOptions === "string") {
      id = idOrOptions;
      options = isSetupStore ? setupOptions : setup;
    } else {
      options = idOrOptions;
      id = idOrOptions.id;
    }
    function useStore2(pinia2, hot) {
      const hasContext = vue.hasInjectionContext();
      pinia2 = // in test mode, ignore the argument provided as we can always retrieve a
      // pinia instance with getActivePinia()
      pinia2 || (hasContext ? vue.inject(piniaSymbol, null) : null);
      if (pinia2)
        setActivePinia(pinia2);
      pinia2 = activePinia;
      if (!pinia2._s.has(id)) {
        if (isSetupStore) {
          createSetupStore(id, setup, options, pinia2);
        } else {
          createOptionsStore(id, options, pinia2);
        }
      }
      const store = pinia2._s.get(id);
      return store;
    }
    useStore2.$id = id;
    return useStore2;
  }
  function isObject$1(v) {
    return typeof v === "object" && v !== null;
  }
  function normalizeOptions(options, factoryOptions) {
    options = isObject$1(options) ? options : /* @__PURE__ */ Object.create(null);
    return new Proxy(options, {
      get(target, key, receiver) {
        if (key === "key")
          return Reflect.get(target, key, receiver);
        return Reflect.get(target, key, receiver) || Reflect.get(factoryOptions, key, receiver);
      }
    });
  }
  function get(state, path) {
    return path.reduce((obj, p) => {
      return obj == null ? void 0 : obj[p];
    }, state);
  }
  function set(state, path, val) {
    return path.slice(0, -1).reduce((obj, p) => {
      if (/^(__proto__)$/.test(p))
        return {};
      else
        return obj[p] = obj[p] || {};
    }, state)[path[path.length - 1]] = val, state;
  }
  function pick(baseState, paths) {
    return paths.reduce((substate, path) => {
      const pathArray = path.split(".");
      return set(substate, pathArray, get(baseState, pathArray));
    }, {});
  }
  function hydrateStore(store, { storage, serializer, key, debug }) {
    try {
      const fromStorage = storage == null ? void 0 : storage.getItem(key);
      if (fromStorage)
        store.$patch(serializer == null ? void 0 : serializer.deserialize(fromStorage));
    } catch (error) {
      if (debug)
        console.error(error);
    }
  }
  function persistState(state, { storage, serializer, key, paths, debug }) {
    try {
      const toStore = Array.isArray(paths) ? pick(state, paths) : state;
      storage.setItem(key, serializer.serialize(toStore));
    } catch (error) {
      if (debug)
        console.error(error);
    }
  }
  function createPersistedState(factoryOptions = {}) {
    return (context) => {
      const { auto = false } = factoryOptions;
      const {
        options: { persist = auto },
        store,
        pinia: pinia2
      } = context;
      if (!persist)
        return;
      if (!(store.$id in pinia2.state.value)) {
        const original_store = pinia2._s.get(store.$id.replace("__hot:", ""));
        if (original_store)
          Promise.resolve().then(() => original_store.$persist());
        return;
      }
      const persistences = (Array.isArray(persist) ? persist.map((p) => normalizeOptions(p, factoryOptions)) : [normalizeOptions(persist, factoryOptions)]).map(
        ({
          storage = localStorage,
          beforeRestore = null,
          afterRestore = null,
          serializer = {
            serialize: JSON.stringify,
            deserialize: JSON.parse
          },
          key = store.$id,
          paths = null,
          debug = false
        }) => {
          var _a;
          return {
            storage,
            beforeRestore,
            afterRestore,
            serializer,
            key: ((_a = factoryOptions.key) != null ? _a : (k) => k)(typeof key == "string" ? key : key(store.$id)),
            paths,
            debug
          };
        }
      );
      store.$persist = () => {
        persistences.forEach((persistence) => {
          persistState(store.$state, persistence);
        });
      };
      store.$hydrate = ({ runHooks = true } = {}) => {
        persistences.forEach((persistence) => {
          const { beforeRestore, afterRestore } = persistence;
          if (runHooks)
            beforeRestore == null ? void 0 : beforeRestore(context);
          hydrateStore(store, persistence);
          if (runHooks)
            afterRestore == null ? void 0 : afterRestore(context);
        });
      };
      persistences.forEach((persistence) => {
        const { beforeRestore, afterRestore } = persistence;
        beforeRestore == null ? void 0 : beforeRestore(context);
        hydrateStore(store, persistence);
        afterRestore == null ? void 0 : afterRestore(context);
        store.$subscribe(
          (_mutation, state) => {
            persistState(state, persistence);
          },
          {
            detached: true
          }
        );
      });
    };
  }
  var src_default = createPersistedState();
  const _export_sfc = (sfc, props) => {
    const target = sfc.__vccOpts || sfc;
    for (const [key, val] of props) {
      target[key] = val;
    }
    return target;
  };
  const _sfc_main$a = {};
  const _hoisted_1$9 = { id: "trigger-overlay" };
  function _sfc_render(_ctx, _cache) {
    return vue.openBlock(), vue.createElementBlock("div", _hoisted_1$9);
  }
  const TriggerOverlay = /* @__PURE__ */ _export_sfc(_sfc_main$a, [["render", _sfc_render], ["__scopeId", "data-v-1d03dd38"]]);
  const _Chord = class _Chord {
    /** @param {string} chordString  */
    constructor(chordString) {
      this.chordString = chordString;
    }
    /**
     * @param {number} delta
     * @returns {Chord}
     */
    transpose(delta) {
      this.chordString = this.chordString.replaceAll(/[A-G][#b]?/g, (note) => {
        const isSharp = _Chord.sharps.includes(note);
        const scale = isSharp ? _Chord.sharps : _Chord.flats;
        const noteIndex = scale.indexOf(note);
        const transposedIndex = (noteIndex + delta + 12) % 12;
        const transposedNote = scale[transposedIndex];
        return transposedNote;
      });
      return this;
    }
    /** @returns {Chord} */
    switchModifier() {
      this.chordString = this.chordString.replaceAll(/[A-G][#b]/g, (note) => {
        const scale = note.includes("#") ? _Chord.sharps : _Chord.flats;
        const newScale = note.includes("#") ? _Chord.flats : _Chord.sharps;
        const noteIndex = scale.indexOf(note);
        return newScale[noteIndex];
      });
      return this;
    }
    /** @returns {Chord} */
    useSharpModifier() {
      this.chordString = this.chordString.replaceAll(/[A-G]b/g, (note) => {
        const noteIndex = _Chord.flats.indexOf(note);
        return _Chord.sharps[noteIndex];
      });
      return this;
    }
    /** @returns {Chord} */
    useFlatModifier() {
      this.chordString = this.chordString.replaceAll(/[A-G]#/g, (note) => {
        const noteIndex = _Chord.sharps.indexOf(note);
        return _Chord.flats[noteIndex];
      });
      return this;
    }
    /** @returns {string} */
    toString() {
      return this.chordString;
    }
    /** @returns {string} */
    toFormattedString() {
      return this.chordString.replaceAll(
        /[#b]/g,
        /* html */
        `<sup>$&</sup>`
      );
    }
  };
  __publicField(_Chord, "sharps", ["C", "C#", "D", "D#", "E", "F", "F#", "G", "G#", "A", "A#", "B"]);
  __publicField(_Chord, "flats", ["C", "Db", "D", "Eb", "E", "F", "Gb", "G", "Ab", "A", "Bb", "B"]);
  let Chord = _Chord;
  var _GM_getValue = /* @__PURE__ */ (() => typeof GM_getValue != "undefined" ? GM_getValue : void 0)();
  var _GM_setValue = /* @__PURE__ */ (() => typeof GM_setValue != "undefined" ? GM_setValue : void 0)();
  class MonkeyStorage {
    /**
     * @param {String} key 
     * @returns {String|null}
     */
    static getItem(key) {
      if (_GM_getValue) {
        return _GM_getValue(key, null);
      } else {
        return localStorage.getItem(key);
      }
    }
    /**
     * @param {String} key 
     * @param {String} value 
     * @returns {void}
     */
    static setItem(key, value) {
      if (_GM_setValue) {
        _GM_setValue(key, value);
      } else {
        localStorage.setItem(key, value);
      }
    }
  }
  var commonjsGlobal = typeof globalThis !== "undefined" ? globalThis : typeof window !== "undefined" ? window : typeof global !== "undefined" ? global : typeof self !== "undefined" ? self : {};
  var lib = {};
  var compress$1 = {};
  var any = {};
  var constants = {};
  (function(exports) {
    Object.defineProperty(exports, "__esModule", { value: true });
    exports.FLOAT_COMPRESSION_PRECISION = 1e3;
    exports.DATE_LOW_PRECISION = 1e5;
    exports.FLOAT_FULL_PRECISION_DELIMITER = ",";
    exports.FLOAT_REDUCED_PRECISION_DELIMITER = ".";
    exports.INTEGER_TOKEN = "¢";
    exports.FLOAT_TOKEN = "£";
    exports.STRING_TOKEN = "¨";
    exports.DATE_TOKEN = "ø";
    exports.LP_DATE_TOKEN = "±";
    exports.UNREFERENCED_INTEGER_TOKEN = "¤";
    exports.UNREFERENCED_FLOAT_TOKEN = "¥";
    exports.UNREFERENCED_STRING_TOKEN = "´";
    exports.UNREFERENCED_DATE_TOKEN = "¿";
    exports.UNREFERENCED_LP_DATE_TOKEN = "ÿ";
    exports.REF_INTEGER_TOKEN = "º";
    exports.REF_FLOAT_TOKEN = "Ý";
    exports.REF_STRING_TOKEN = "ß";
    exports.REF_DATE_TOKEN = "×";
    exports.REF_LP_DATE_TOKEN = "ü";
    exports.NULL_TOKEN = "§";
    exports.UNDEFINED_TOKEN = "µ";
    exports.BOOLEAN_TRUE_TOKEN = "»";
    exports.BOOLEAN_FALSE_TOKEN = "«";
    exports.ESCAPE_CHARACTER = "\\";
    exports.ESCAPED_STRING_TOKEN = "" + exports.ESCAPE_CHARACTER + exports.STRING_TOKEN;
    exports.ESCAPED_UNREFERENCED_STRING_TOKEN = "" + exports.ESCAPE_CHARACTER + exports.UNREFERENCED_STRING_TOKEN;
    exports.REGEX_ESCAPE_CHARACTER = new RegExp(exports.ESCAPE_CHARACTER.replace("\\", "\\\\"), "g");
    exports.REGEX_ESCAPED_ESCAPE_CHARACTER = new RegExp(exports.ESCAPE_CHARACTER.replace("\\", "\\\\") + exports.ESCAPE_CHARACTER.replace("\\", "\\\\"), "g");
    exports.REGEX_STRING_TOKEN = new RegExp(exports.STRING_TOKEN, "g");
    exports.REGEX_ESCAPED_STRING_TOKEN = new RegExp(exports.ESCAPE_CHARACTER + exports.ESCAPED_STRING_TOKEN, "g");
    exports.REGEX_UNREFERENCED_STRING_TOKEN = new RegExp(exports.UNREFERENCED_STRING_TOKEN, "g");
    exports.REGEX_UNREFERENCED_ESCAPED_STRING_TOKEN = new RegExp(exports.ESCAPE_CHARACTER + exports.ESCAPED_UNREFERENCED_STRING_TOKEN, "g");
    exports.DATE_REGEX = /\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(\.\d+)?Z/;
    exports.OBJECT_START_TOKEN = "{";
    exports.OBJECT_END_TOKEN = "}";
    exports.TEMPLATE_OBJECT_START = "¦";
    exports.TEMPLATE_OBJECT_END = "‡";
    exports.TEMPLATE_OBJECT_FINAL = "—";
    exports.ARRAY_START_TOKEN = "|";
    exports.ARRAY_END_TOKEN = "÷";
    exports.ARRAY_REPEAT_TOKEN = "þ";
    exports.ARRAY_REPEAT_MANY_TOKEN = "^";
    exports.ARRAY_REPEAT_COUNT_THRESHOLD = 4;
    exports.REFERENCE_HEADER_LENGTH = 1;
    exports.DELIMITING_TOKENS_THRESHOLD = 122;
    exports.STRING_IDENT_PREFIX = "$";
    exports.INTEGER_SMALL_EXCLUSIVE_BOUND_LOWER = -10;
    exports.INTEGER_SMALL_EXCLUSIVE_BOUND_UPPER = 10;
    exports.INTEGER_SMALL_TOKEN_EXCLUSIVE_BOUND_LOWER = 191;
    exports.INTEGER_SMALL_TOKEN_EXCLUSIVE_BOUND_UPPER = 211;
    exports.INTEGER_SMALL_TOKEN_OFFSET = -201;
    exports.INTEGER_SMALL_TOKEN_ELEMENT_OFFSET = 9;
    exports.INTEGER_SMALL_TOKENS = ["À", "Á", "Â", "Ã", "Ä", "Å", "Æ", "Ç", "È", "É", "Ê", "Ë", "Ì", "Í", "Î", "Ï", "Ð", "Ñ", "Ò"];
  })(constants);
  Object.defineProperty(any, "__esModule", { value: true });
  var constants_1$a = constants;
  function compressAny(compressors2, context, obj, invertedIndex, writer2, options) {
    var type = typeof obj;
    if (type === "number") {
      compressors2.number(compressors2, context, obj, invertedIndex, writer2, options);
    } else if (type === "string") {
      compressors2.string(compressors2, context, obj, invertedIndex, writer2, options);
    } else if (type === "boolean") {
      writer2.write(obj ? constants_1$a.BOOLEAN_TRUE_TOKEN : constants_1$a.BOOLEAN_FALSE_TOKEN);
    } else if (obj === null) {
      writer2.write(constants_1$a.NULL_TOKEN);
    } else if (obj === void 0) {
      writer2.write(constants_1$a.UNDEFINED_TOKEN);
    } else if (Array.isArray(obj)) {
      compressors2.array(compressors2, context, obj, invertedIndex, writer2, options);
    } else if (obj instanceof Date) {
      compressors2.date(compressors2, context, obj.getTime(), invertedIndex, writer2, options);
    } else {
      compressors2.object(compressors2, context, obj, invertedIndex, writer2, options);
    }
  }
  any.compressAny = compressAny;
  var array = {};
  var writer = {};
  var __extends = commonjsGlobal && commonjsGlobal.__extends || function() {
    var extendStatics = Object.setPrototypeOf || { __proto__: [] } instanceof Array && function(d, b) {
      d.__proto__ = b;
    } || function(d, b) {
      for (var p in b)
        if (b.hasOwnProperty(p))
          d[p] = b[p];
    };
    return function(d, b) {
      extendStatics(d, b);
      function __() {
        this.constructor = d;
      }
      d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
    };
  }();
  Object.defineProperty(writer, "__esModule", { value: true });
  var ZipsonWriter = (
    /** @class */
    function() {
      function ZipsonWriter2() {
      }
      return ZipsonWriter2;
    }()
  );
  writer.ZipsonWriter = ZipsonWriter;
  var ZipsonStringWriter = (
    /** @class */
    function(_super) {
      __extends(ZipsonStringWriter2, _super);
      function ZipsonStringWriter2() {
        var _this = _super !== null && _super.apply(this, arguments) || this;
        _this.value = "";
        return _this;
      }
      ZipsonStringWriter2.prototype.write = function(data) {
        this.value += data;
      };
      ZipsonStringWriter2.prototype.end = function() {
      };
      return ZipsonStringWriter2;
    }(ZipsonWriter)
  );
  writer.ZipsonStringWriter = ZipsonStringWriter;
  var util$1 = {};
  Object.defineProperty(util$1, "__esModule", { value: true });
  var constants_1$9 = constants;
  var maxInteger = 2147483648;
  var minInteger = -2147483649;
  var base62 = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
  function compressInteger(number2) {
    if (number2 === 0) {
      return "0";
    }
    var result = "";
    var carry = number2 < 0 ? -number2 : number2;
    var current = 0;
    var fraction;
    while (carry > 0) {
      carry = carry / 62;
      fraction = carry % 1;
      current = fraction * 62 + 0.1 << 0;
      carry -= fraction;
      result = base62[current] + result;
    }
    result = number2 < 0 ? "-" + result : result;
    return result;
  }
  util$1.compressInteger = compressInteger;
  function decompressInteger(compressedInteger) {
    var value = 0;
    if (compressedInteger[0] === "0") {
      return value;
    } else {
      var negative = compressedInteger[0] === "-";
      var multiplier = 1;
      var leftBound = negative ? 1 : 0;
      for (var i = compressedInteger.length - 1; i >= leftBound; i--) {
        var code = compressedInteger.charCodeAt(i);
        var current = code - 48;
        if (code >= 97) {
          current -= 13;
        } else if (code >= 65) {
          current -= 7;
        }
        value += current * multiplier;
        multiplier *= 62;
      }
      return negative ? -value : value;
    }
  }
  util$1.decompressInteger = decompressInteger;
  function compressFloat(float, fullPrecision) {
    if (fullPrecision === void 0) {
      fullPrecision = false;
    }
    if (fullPrecision) {
      var _a = float.toString().split("."), integer = _a[0], fraction = _a[1];
      var operator = integer === "-0" ? "-" : "";
      return "" + operator + compressInteger(parseInt(integer)) + constants_1$9.FLOAT_FULL_PRECISION_DELIMITER + fraction;
    } else {
      var integer = float >= maxInteger ? Math.floor(float) : float <= minInteger ? Math.ceil(float) : float << 0;
      var fraction = Math.round(constants_1$9.FLOAT_COMPRESSION_PRECISION * (float % 1));
      return "" + compressInteger(integer) + constants_1$9.FLOAT_REDUCED_PRECISION_DELIMITER + compressInteger(fraction);
    }
  }
  util$1.compressFloat = compressFloat;
  function decompressFloat(compressedFloat) {
    if (compressedFloat.indexOf(constants_1$9.FLOAT_FULL_PRECISION_DELIMITER) > -1) {
      var _a = compressedFloat.split(constants_1$9.FLOAT_FULL_PRECISION_DELIMITER), integer = _a[0], fraction = _a[1];
      var mult = integer === "-0" ? -1 : 1;
      var uncompressedInteger = decompressInteger(integer);
      return mult * parseFloat(uncompressedInteger + "." + fraction);
    } else {
      var _b = compressedFloat.split(constants_1$9.FLOAT_REDUCED_PRECISION_DELIMITER), integer = _b[0], fraction = _b[1];
      var uncompressedInteger = decompressInteger(integer);
      var uncompressedFraction = decompressInteger(fraction);
      return uncompressedInteger + uncompressedFraction / constants_1$9.FLOAT_COMPRESSION_PRECISION;
    }
  }
  util$1.decompressFloat = decompressFloat;
  Object.defineProperty(array, "__esModule", { value: true });
  var constants_1$8 = constants;
  var writer_1 = writer;
  var util_1$5 = util$1;
  function compressArray(compressors2, context, array2, invertedIndex, writer2, options) {
    context.arrayLevel++;
    if (context.arrayLevel > context.arrayItemWriters.length) {
      context.arrayItemWriters.push(new writer_1.ZipsonStringWriter());
    }
    var arrayItemWriter = context.arrayItemWriters[context.arrayLevel - 1];
    var parentWriter = context.arrayItemWriters[context.arrayLevel - 2] || writer2;
    parentWriter.write(constants_1$8.ARRAY_START_TOKEN);
    var previousItem = "";
    var repeatedTimes = 0;
    var repeatManyCount = 0;
    var templateObject = new compressors2.template.Object(array2[0], array2[1]);
    if (templateObject.isTemplating) {
      templateObject.compressTemplate(compressors2, context, invertedIndex, parentWriter, options);
    }
    for (var i = 0; i < array2.length; i++) {
      var item = array2[i];
      arrayItemWriter.value = "";
      if (item === void 0) {
        item = null;
      }
      if (i > 1 && templateObject.isTemplating) {
        templateObject.isNextTemplateable(array2[i], parentWriter);
      }
      if (templateObject.isTemplating) {
        templateObject.compressTemplateValues(compressors2, context, invertedIndex, arrayItemWriter, options, array2[i]);
      } else {
        compressors2.any(compressors2, context, item, invertedIndex, arrayItemWriter, options);
      }
      if (arrayItemWriter.value === previousItem) {
        repeatedTimes++;
        if (repeatedTimes >= constants_1$8.ARRAY_REPEAT_COUNT_THRESHOLD) {
          if (repeatManyCount === 0) {
            parentWriter.write(constants_1$8.ARRAY_REPEAT_MANY_TOKEN);
          }
          repeatManyCount++;
        } else {
          parentWriter.write(constants_1$8.ARRAY_REPEAT_TOKEN);
        }
      } else {
        repeatedTimes = 0;
        if (repeatManyCount > 0) {
          parentWriter.write(util_1$5.compressInteger(repeatManyCount));
          repeatManyCount = 0;
        }
        parentWriter.write(arrayItemWriter.value);
        previousItem = arrayItemWriter.value;
      }
    }
    if (repeatManyCount > 0) {
      parentWriter.write(util_1$5.compressInteger(repeatManyCount));
    }
    if (templateObject.isTemplating) {
      templateObject.end(parentWriter);
    }
    parentWriter.write(constants_1$8.ARRAY_END_TOKEN);
    context.arrayLevel--;
  }
  array.compressArray = compressArray;
  var string = {};
  Object.defineProperty(string, "__esModule", { value: true });
  var constants_1$7 = constants;
  var util_1$4 = util$1;
  function compressString(compressors2, context, obj, invertedIndex, writer2, options) {
    var foundRef;
    var stringIdent = constants_1$7.STRING_IDENT_PREFIX + obj;
    if (options.detectUtcTimestamps && obj[obj.length - 1] === "Z" && obj.match(constants_1$7.DATE_REGEX)) {
      var date2 = Date.parse(obj);
      compressors2.date(compressors2, context, date2, invertedIndex, writer2, options);
    } else if ((foundRef = invertedIndex.stringMap[stringIdent]) !== void 0) {
      writer2.write("" + constants_1$7.REF_STRING_TOKEN + foundRef);
    } else {
      var ref2 = util_1$4.compressInteger(invertedIndex.stringCount);
      var newRef = "" + constants_1$7.STRING_TOKEN + obj.replace(constants_1$7.REGEX_ESCAPE_CHARACTER, constants_1$7.ESCAPE_CHARACTER + constants_1$7.ESCAPE_CHARACTER).replace(constants_1$7.REGEX_STRING_TOKEN, constants_1$7.ESCAPED_STRING_TOKEN) + constants_1$7.STRING_TOKEN;
      if (ref2.length + constants_1$7.REFERENCE_HEADER_LENGTH + 1 < newRef.length) {
        invertedIndex.stringMap[stringIdent] = ref2;
        invertedIndex.stringCount++;
        writer2.write(newRef);
      } else {
        writer2.write("" + constants_1$7.UNREFERENCED_STRING_TOKEN + obj.replace(constants_1$7.REGEX_ESCAPE_CHARACTER, constants_1$7.ESCAPE_CHARACTER + constants_1$7.ESCAPE_CHARACTER).replace(constants_1$7.REGEX_UNREFERENCED_STRING_TOKEN, constants_1$7.ESCAPED_UNREFERENCED_STRING_TOKEN) + constants_1$7.UNREFERENCED_STRING_TOKEN);
      }
    }
  }
  string.compressString = compressString;
  var number = {};
  Object.defineProperty(number, "__esModule", { value: true });
  var constants_1$6 = constants;
  var util_1$3 = util$1;
  function compressNumber(compressors2, context, obj, invertedIndex, writer2, options) {
    var foundRef;
    if (obj % 1 === 0) {
      if (obj < constants_1$6.INTEGER_SMALL_EXCLUSIVE_BOUND_UPPER && obj > constants_1$6.INTEGER_SMALL_EXCLUSIVE_BOUND_LOWER) {
        writer2.write(constants_1$6.INTEGER_SMALL_TOKENS[obj + constants_1$6.INTEGER_SMALL_TOKEN_ELEMENT_OFFSET]);
      } else if ((foundRef = invertedIndex.integerMap[obj]) !== void 0) {
        writer2.write("" + constants_1$6.REF_INTEGER_TOKEN + foundRef);
      } else {
        var ref2 = util_1$3.compressInteger(invertedIndex.integerCount);
        var compressedInteger = util_1$3.compressInteger(obj);
        var newRef = "" + constants_1$6.INTEGER_TOKEN + compressedInteger;
        if (ref2.length + constants_1$6.REFERENCE_HEADER_LENGTH < newRef.length) {
          invertedIndex.integerMap[obj] = ref2;
          invertedIndex.integerCount++;
          writer2.write(newRef);
        } else {
          writer2.write("" + constants_1$6.UNREFERENCED_INTEGER_TOKEN + compressedInteger);
        }
      }
    } else {
      var compressedFloat = util_1$3.compressFloat(obj, options.fullPrecisionFloats);
      if ((foundRef = invertedIndex.floatMap[compressedFloat]) !== void 0) {
        writer2.write("" + constants_1$6.REF_FLOAT_TOKEN + foundRef);
      } else {
        var ref2 = util_1$3.compressInteger(invertedIndex.floatCount);
        var newRef = "" + constants_1$6.FLOAT_TOKEN + compressedFloat;
        if (ref2.length + constants_1$6.REFERENCE_HEADER_LENGTH < newRef.length) {
          invertedIndex.floatMap[compressedFloat] = ref2;
          invertedIndex.floatCount++;
          writer2.write(newRef);
        } else {
          writer2.write("" + constants_1$6.UNREFERENCED_FLOAT_TOKEN + compressedFloat);
        }
      }
    }
  }
  number.compressNumber = compressNumber;
  var object$1 = {};
  Object.defineProperty(object$1, "__esModule", { value: true });
  var constants_1$5 = constants;
  function compressObject(compressors2, context, obj, invertedIndex, writer2, options) {
    writer2.write(constants_1$5.OBJECT_START_TOKEN);
    var keys = Object.keys(obj);
    var templateObject = new compressors2.template.Object(obj[keys[0]], obj[keys[1]]);
    if (templateObject.isTemplating) {
      templateObject.compressTemplate(compressors2, context, invertedIndex, writer2, options);
    }
    for (var i = 0; i < keys.length; i++) {
      if (i > 1 && templateObject.isTemplating) {
        templateObject.isNextTemplateable(obj[keys[i]], writer2);
      }
      if (templateObject.isTemplating) {
        compressors2.string(compressors2, context, keys[i], invertedIndex, writer2, options);
        templateObject.compressTemplateValues(compressors2, context, invertedIndex, writer2, options, obj[keys[i]]);
      } else {
        var key = keys[i];
        var val = obj[key];
        if (val !== void 0) {
          compressors2.string(compressors2, context, key, invertedIndex, writer2, options);
          compressors2.any(compressors2, context, val, invertedIndex, writer2, options);
        }
      }
    }
    if (templateObject.isTemplating) {
      templateObject.end(writer2);
    }
    writer2.write(constants_1$5.OBJECT_END_TOKEN);
  }
  object$1.compressObject = compressObject;
  var date = {};
  Object.defineProperty(date, "__esModule", { value: true });
  var constants_1$4 = constants;
  var util_1$2 = util$1;
  function compressDate(compressors2, context, obj, invertedIndex, writer2, options) {
    var foundRef;
    var lowPrecisionDate = obj / constants_1$4.DATE_LOW_PRECISION;
    var isLowPrecision = lowPrecisionDate % 1 === 0;
    if (isLowPrecision) {
      if ((foundRef = invertedIndex.lpDateMap[lowPrecisionDate]) !== void 0) {
        writer2.write("" + constants_1$4.REF_LP_DATE_TOKEN + foundRef);
      } else {
        var ref2 = util_1$2.compressInteger(invertedIndex.lpDateCount);
        var compressedDate = util_1$2.compressInteger(lowPrecisionDate);
        var newRef = "" + constants_1$4.LP_DATE_TOKEN + compressedDate;
        if (ref2.length + constants_1$4.REFERENCE_HEADER_LENGTH < newRef.length) {
          invertedIndex.lpDateMap[lowPrecisionDate] = ref2;
          invertedIndex.lpDateCount++;
          writer2.write(newRef);
        } else {
          writer2.write("" + constants_1$4.UNREFERENCED_LP_DATE_TOKEN + compressedDate);
        }
      }
    } else {
      if ((foundRef = invertedIndex.dateMap[obj]) !== void 0) {
        writer2.write("" + constants_1$4.REF_DATE_TOKEN + foundRef);
      } else {
        var ref2 = util_1$2.compressInteger(invertedIndex.dateCount);
        var compressedDate = util_1$2.compressInteger(obj);
        var newRef = "" + constants_1$4.DATE_TOKEN + compressedDate;
        if (ref2.length + constants_1$4.REFERENCE_HEADER_LENGTH < newRef.length) {
          invertedIndex.dateMap[obj] = ref2;
          invertedIndex.dateCount++;
          writer2.write(newRef);
        } else {
          writer2.write("" + constants_1$4.UNREFERENCED_DATE_TOKEN + compressedDate);
        }
      }
    }
  }
  date.compressDate = compressDate;
  var object = {};
  var util = {};
  Object.defineProperty(util, "__esModule", { value: true });
  function isObject(obj) {
    var type = typeof obj;
    if (type === "number") {
      return false;
    } else if (type === "string") {
      return false;
    } else if (type === "boolean") {
      return false;
    } else if (obj === null) {
      return false;
    } else if (Array.isArray(obj)) {
      return false;
    } else if (obj instanceof Date) {
      return false;
    } else if (obj === void 0) {
      return false;
    } else {
      return true;
    }
  }
  util.isObject = isObject;
  Object.defineProperty(object, "__esModule", { value: true });
  var constants_1$3 = constants;
  var util_1$1 = util;
  var TemplateObject = (
    /** @class */
    function() {
      function TemplateObject2(a, b) {
        this.isTemplating = false;
        this.struct = [];
        if (a != null && b != null) {
          this.isTemplating = buildTemplate(a, b, this.struct);
        }
      }
      TemplateObject2.prototype.compressTemplate = function(compressors2, context, invertedIndex, writer2, options) {
        compresObjectTemplate(compressors2, context, invertedIndex, writer2, options, this.struct);
      };
      TemplateObject2.prototype.compressTemplateValues = function(compressors2, context, invertedIndex, writer2, options, obj) {
        compressObjectValues(compressors2, context, invertedIndex, writer2, options, this.struct, obj);
      };
      TemplateObject2.prototype.isNextTemplateable = function(obj, writer2) {
        this.isTemplating = conformsToStructure(this.struct, obj);
        if (!this.isTemplating) {
          writer2.write(constants_1$3.TEMPLATE_OBJECT_FINAL);
        }
      };
      TemplateObject2.prototype.end = function(writer2) {
        writer2.write(constants_1$3.TEMPLATE_OBJECT_FINAL);
      };
      return TemplateObject2;
    }()
  );
  object.TemplateObject = TemplateObject;
  function buildTemplate(a, b, struct, level) {
    if (level === void 0) {
      level = 0;
    }
    if (level > 6) {
      return false;
    }
    var keysA = Object.keys(a);
    var keysB = Object.keys(b);
    if (keysA.length !== keysB.length) {
      return false;
    }
    if (keysA.length > 10) {
      return false;
    }
    keysA.sort(function(a2, b2) {
      return a2.localeCompare(b2);
    });
    keysB.sort(function(a2, b2) {
      return a2.localeCompare(b2);
    });
    for (var i = 0; i < keysA.length; i++) {
      var keyA = keysA[i];
      var keyB = keysB[i];
      if (keyA !== keyB) {
        return false;
      }
      var valueA = a[keyA];
      var valueB = b[keyB];
      if (util_1$1.isObject(valueA)) {
        if (!util_1$1.isObject(valueB)) {
          return false;
        }
        var nextStruct = [];
        struct.push([keyA, nextStruct]);
        if (!buildTemplate(valueA, valueB, nextStruct, level + 1)) {
          return false;
        }
      } else if (util_1$1.isObject(valueB)) {
        return false;
      } else {
        struct.push([keyA]);
      }
    }
    return level > 0 || util_1$1.isObject(a);
  }
  function conformsToStructure(struct, obj) {
    if (!obj) {
      return false;
    }
    if (Object.keys(obj).length !== struct.length) {
      return false;
    }
    for (var i = 0; i < struct.length; i++) {
      var key = struct[i][0];
      var isNested = struct[i].length > 1;
      if (obj[key] === void 0) {
        return false;
      }
      if (isNested) {
        var x = struct[i];
        x[1];
        if (!conformsToStructure(struct[i][1], obj[key])) {
          return false;
        }
      } else {
        if (util_1$1.isObject(obj[key])) {
          return false;
        }
      }
    }
    return true;
  }
  function compresObjectTemplate(compressors2, context, invertedIndex, writer2, options, struct) {
    writer2.write(constants_1$3.TEMPLATE_OBJECT_START);
    for (var i = 0; i < struct.length; i++) {
      var key = struct[i][0];
      var isNested = struct[i].length > 1;
      compressors2.string(compressors2, context, key, invertedIndex, writer2, options);
      if (isNested) {
        compresObjectTemplate(compressors2, context, invertedIndex, writer2, options, struct[i][1]);
      }
    }
    writer2.write(constants_1$3.TEMPLATE_OBJECT_END);
  }
  function compressObjectValues(compressors2, context, invertedIndex, writer2, options, struct, obj) {
    for (var i = 0; i < struct.length; i++) {
      var key = struct[i][0];
      var value = obj[key];
      var isNested = struct[i].length > 1;
      if (isNested) {
        compressObjectValues(compressors2, context, invertedIndex, writer2, options, struct[i][1], value);
      } else {
        compressors2.any(compressors2, context, value, invertedIndex, writer2, options);
      }
    }
  }
  Object.defineProperty(compress$1, "__esModule", { value: true });
  var any_1 = any;
  var array_1 = array;
  var string_1 = string;
  var number_1 = number;
  var object_1 = object$1;
  var date_1 = date;
  var object_2 = object;
  var compressors = {
    any: any_1.compressAny,
    array: array_1.compressArray,
    object: object_1.compressObject,
    string: string_1.compressString,
    date: date_1.compressDate,
    number: number_1.compressNumber,
    template: {
      Object: object_2.TemplateObject
    }
  };
  function makeCompressContext() {
    return {
      arrayItemWriters: [],
      arrayLevel: 0
    };
  }
  compress$1.makeCompressContext = makeCompressContext;
  function makeInvertedIndex() {
    return {
      stringMap: {},
      integerMap: {},
      floatMap: {},
      dateMap: {},
      lpDateMap: {},
      stringCount: 0,
      integerCount: 0,
      floatCount: 0,
      dateCount: 0,
      lpDateCount: 0
    };
  }
  compress$1.makeInvertedIndex = makeInvertedIndex;
  function compress(context, obj, invertedIndex, writer2, options) {
    compressors.any(compressors, context, obj, invertedIndex, writer2, options);
  }
  compress$1.compress = compress;
  var decompress$1 = {};
  var common = {};
  (function(exports) {
    Object.defineProperty(exports, "__esModule", { value: true });
    exports.SKIP_SCALAR = {};
    (function(TargetType) {
      TargetType["ARRAY"] = "ARRAY";
      TargetType["OBJECT"] = "OBJECT";
      TargetType["SCALAR"] = "SCALAR";
      TargetType["TEMPLATE_OBJECT"] = "TEMPLATE_OBJECT";
      TargetType["TEMPLATE_OBJECT_PROPERTIES"] = "TEMPLATE_OBJECT_PROPERTIES";
      TargetType["TEMPLATE_OBJECT_ELEMENTS"] = "TEMPLATE_OBJECT_ELEMENTS";
    })(exports.TargetType || (exports.TargetType = {}));
  })(common);
  var stages = {};
  var scalar = {};
  Object.defineProperty(scalar, "__esModule", { value: true });
  var constants_1$2 = constants;
  var common_1$3 = common;
  var util_1 = util$1;
  function decompressScalar(token, data, cursor, orderedIndex) {
    var startIndex = cursor.index;
    var endIndex = cursor.index + 1;
    var foundStringToken;
    if (token === constants_1$2.STRING_TOKEN && (foundStringToken = constants_1$2.STRING_TOKEN) || token === constants_1$2.UNREFERENCED_STRING_TOKEN && (foundStringToken = constants_1$2.UNREFERENCED_STRING_TOKEN)) {
      var escaped = true;
      while (escaped && endIndex < data.length) {
        endIndex = data.indexOf(foundStringToken, endIndex);
        var iNumEscapeCharacters = 1;
        escaped = false;
        while (data[endIndex - iNumEscapeCharacters] === constants_1$2.ESCAPE_CHARACTER) {
          escaped = iNumEscapeCharacters % 2 === 1;
          iNumEscapeCharacters++;
        }
        endIndex++;
      }
      if (endIndex <= startIndex) {
        endIndex = data.length;
      }
    } else {
      while (!(data.charCodeAt(endIndex) > constants_1$2.DELIMITING_TOKENS_THRESHOLD) && endIndex < data.length) {
        endIndex++;
      }
    }
    if (!cursor.drain && endIndex === data.length) {
      return common_1$3.SKIP_SCALAR;
    }
    cursor.index = endIndex - 1;
    var tokenCharCode = token.charCodeAt(0);
    if (tokenCharCode > constants_1$2.INTEGER_SMALL_TOKEN_EXCLUSIVE_BOUND_LOWER && tokenCharCode < constants_1$2.INTEGER_SMALL_TOKEN_EXCLUSIVE_BOUND_UPPER) {
      return tokenCharCode + constants_1$2.INTEGER_SMALL_TOKEN_OFFSET;
    } else if (token === constants_1$2.ARRAY_REPEAT_MANY_TOKEN) {
      return util_1.decompressInteger(data.substring(startIndex + 1, endIndex));
    } else if (token === constants_1$2.REF_STRING_TOKEN) {
      return orderedIndex.strings[util_1.decompressInteger(data.substring(startIndex + 1, endIndex))];
    } else if (token === constants_1$2.REF_INTEGER_TOKEN) {
      return orderedIndex.integers[util_1.decompressInteger(data.substring(startIndex + 1, endIndex))];
    } else if (token === constants_1$2.REF_FLOAT_TOKEN) {
      return orderedIndex.floats[util_1.decompressInteger(data.substring(startIndex + 1, endIndex))];
    } else if (token === constants_1$2.REF_DATE_TOKEN) {
      return orderedIndex.dates[util_1.decompressInteger(data.substring(startIndex + 1, endIndex))];
    } else if (token === constants_1$2.REF_LP_DATE_TOKEN) {
      return orderedIndex.lpDates[util_1.decompressInteger(data.substring(startIndex + 1, endIndex))];
    } else if (token === constants_1$2.STRING_TOKEN) {
      return orderedIndex.strings[orderedIndex.strings.length] = data.substring(startIndex + 1, endIndex - 1).replace(constants_1$2.REGEX_ESCAPED_ESCAPE_CHARACTER, constants_1$2.ESCAPE_CHARACTER).replace(constants_1$2.REGEX_ESCAPED_STRING_TOKEN, constants_1$2.STRING_TOKEN);
    } else if (token === constants_1$2.INTEGER_TOKEN) {
      return orderedIndex.integers[orderedIndex.integers.length] = util_1.decompressInteger(data.substring(startIndex + 1, endIndex));
    } else if (token === constants_1$2.FLOAT_TOKEN) {
      return orderedIndex.floats[orderedIndex.floats.length] = util_1.decompressFloat(data.substring(startIndex + 1, endIndex));
    } else if (token === constants_1$2.DATE_TOKEN) {
      return orderedIndex.dates[orderedIndex.dates.length] = new Date(util_1.decompressInteger(data.substring(startIndex + 1, endIndex))).toISOString();
    } else if (token === constants_1$2.LP_DATE_TOKEN) {
      return orderedIndex.lpDates[orderedIndex.lpDates.length] = new Date(constants_1$2.DATE_LOW_PRECISION * util_1.decompressInteger(data.substring(startIndex + 1, endIndex))).toISOString();
    } else if (token === constants_1$2.UNREFERENCED_STRING_TOKEN) {
      return data.substring(startIndex + 1, endIndex - 1).replace(constants_1$2.REGEX_ESCAPED_ESCAPE_CHARACTER, constants_1$2.ESCAPE_CHARACTER).replace(constants_1$2.REGEX_UNREFERENCED_ESCAPED_STRING_TOKEN, constants_1$2.UNREFERENCED_STRING_TOKEN);
    } else if (token === constants_1$2.UNREFERENCED_INTEGER_TOKEN) {
      return util_1.decompressInteger(data.substring(startIndex + 1, endIndex));
    } else if (token === constants_1$2.UNREFERENCED_FLOAT_TOKEN) {
      return util_1.decompressFloat(data.substring(startIndex + 1, endIndex));
    } else if (token === constants_1$2.UNREFERENCED_DATE_TOKEN) {
      return new Date(util_1.decompressInteger(data.substring(startIndex + 1, endIndex))).toISOString();
    } else if (token === constants_1$2.UNREFERENCED_LP_DATE_TOKEN) {
      return new Date(constants_1$2.DATE_LOW_PRECISION * util_1.decompressInteger(data.substring(startIndex + 1, endIndex))).toISOString();
    } else if (token === constants_1$2.BOOLEAN_TRUE_TOKEN) {
      return true;
    } else if (token === constants_1$2.BOOLEAN_FALSE_TOKEN) {
      return false;
    } else if (token === constants_1$2.NULL_TOKEN) {
      return null;
    } else if (token === constants_1$2.UNDEFINED_TOKEN) {
      return void 0;
    }
    throw new Error("Unexpected scalar " + token + " at " + startIndex + "-" + endIndex);
  }
  scalar.decompressScalar = decompressScalar;
  var element = {};
  var template = {};
  Object.defineProperty(template, "__esModule", { value: true });
  function appendTemplateObjectValue(templateObjectTarget, targetValue) {
    var currentPath = templateObjectTarget.paths[templateObjectTarget.currentPathIndex];
    var i = 0;
    var targetObject = templateObjectTarget.currentObject;
    for (; i < currentPath.length - 1; i++) {
      var fragment = currentPath[i];
      targetObject = targetObject[fragment] = targetObject[fragment] || {};
    }
    if (targetValue !== void 0) {
      targetObject[currentPath[i]] = targetValue;
    }
  }
  function appendTemplateObjectPropertiesValue(templateObjectElementsTarget, targetValue) {
    if (templateObjectElementsTarget.currentPathIndex === -1) {
      templateObjectElementsTarget.value[targetValue] = templateObjectElementsTarget.currentObject = {};
    } else {
      appendTemplateObjectValue(templateObjectElementsTarget, targetValue);
    }
    if (++templateObjectElementsTarget.currentPathIndex === templateObjectElementsTarget.expectedPaths) {
      templateObjectElementsTarget.currentPathIndex = -1;
    }
  }
  template.appendTemplateObjectPropertiesValue = appendTemplateObjectPropertiesValue;
  function appendTemplateObjectElementsValue(templateObjectPropertiesTarget, targetValue) {
    if (templateObjectPropertiesTarget.currentPathIndex === 0) {
      templateObjectPropertiesTarget.currentObject = {};
      templateObjectPropertiesTarget.value.push(templateObjectPropertiesTarget.currentObject);
    }
    appendTemplateObjectValue(templateObjectPropertiesTarget, targetValue);
    if (++templateObjectPropertiesTarget.currentPathIndex === templateObjectPropertiesTarget.expectedPaths) {
      templateObjectPropertiesTarget.currentPathIndex = 0;
    }
  }
  template.appendTemplateObjectElementsValue = appendTemplateObjectElementsValue;
  Object.defineProperty(element, "__esModule", { value: true });
  var constants_1$1 = constants;
  var common_1$2 = common;
  var scalar_1$1 = scalar;
  var template_1 = template;
  function decompressElement(c, cursor, data, orderedIndex) {
    var targetValue;
    if (c === constants_1$1.ARRAY_END_TOKEN || c === constants_1$1.OBJECT_END_TOKEN) {
      targetValue = cursor.currentTarget.value;
      cursor.currentTarget = cursor.stack[cursor.pointer - 1];
      cursor.pointer--;
    } else {
      targetValue = scalar_1$1.decompressScalar(c, data, cursor, orderedIndex);
      if (targetValue === common_1$2.SKIP_SCALAR) {
        return false;
      }
    }
    if (cursor.currentTarget.type === common_1$2.TargetType.SCALAR) {
      cursor.currentTarget.value = targetValue;
    } else if (cursor.currentTarget.type === common_1$2.TargetType.ARRAY) {
      cursor.currentTarget.value[cursor.currentTarget.value.length] = targetValue;
    } else if (cursor.currentTarget.type === common_1$2.TargetType.OBJECT) {
      if (cursor.currentTarget.key != null) {
        cursor.currentTarget.value[cursor.currentTarget.key] = targetValue;
        cursor.currentTarget.key = void 0;
      } else {
        cursor.currentTarget.key = targetValue;
      }
    } else if (cursor.currentTarget.type === common_1$2.TargetType.TEMPLATE_OBJECT) {
      cursor.currentTarget.currentToken = targetValue;
      cursor.currentTarget.currentTokens.push(targetValue);
    } else if (cursor.currentTarget.type === common_1$2.TargetType.TEMPLATE_OBJECT_PROPERTIES) {
      template_1.appendTemplateObjectPropertiesValue(cursor.currentTarget, targetValue);
    } else if (cursor.currentTarget.type === common_1$2.TargetType.TEMPLATE_OBJECT_ELEMENTS) {
      template_1.appendTemplateObjectElementsValue(cursor.currentTarget, targetValue);
    }
    return true;
  }
  element.decompressElement = decompressElement;
  Object.defineProperty(stages, "__esModule", { value: true });
  var constants_1 = constants;
  var common_1$1 = common;
  var scalar_1 = scalar;
  var element_1 = element;
  function decompressStages(cursor, data, orderedIndex) {
    for (; cursor.index < data.length; cursor.index++) {
      var c = data[cursor.index];
      if (c === constants_1.ARRAY_START_TOKEN) {
        cursor.currentTarget = { type: common_1$1.TargetType.ARRAY, value: [] };
        cursor.stack[++cursor.pointer] = cursor.currentTarget;
      } else if (c === constants_1.OBJECT_START_TOKEN) {
        cursor.currentTarget = { type: common_1$1.TargetType.OBJECT, value: {} };
        cursor.stack[++cursor.pointer] = cursor.currentTarget;
      } else if (c === constants_1.ARRAY_REPEAT_TOKEN && (cursor.currentTarget.type === common_1$1.TargetType.ARRAY || cursor.currentTarget.type === common_1$1.TargetType.TEMPLATE_OBJECT_ELEMENTS)) {
        var repeatedItem = cursor.currentTarget.value[cursor.currentTarget.value.length - 1];
        cursor.currentTarget.value.push(repeatedItem);
      } else if (c === constants_1.ARRAY_REPEAT_MANY_TOKEN && (cursor.currentTarget.type === common_1$1.TargetType.ARRAY || cursor.currentTarget.type === common_1$1.TargetType.TEMPLATE_OBJECT_ELEMENTS)) {
        var repeatCount = scalar_1.decompressScalar(data[cursor.index], data, cursor, orderedIndex);
        if (repeatCount === common_1$1.SKIP_SCALAR) {
          return;
        }
        var repeatedItem = cursor.currentTarget.value[cursor.currentTarget.value.length - 1];
        for (var i = 0; i < repeatCount; i++) {
          cursor.currentTarget.value.push(repeatedItem);
        }
      } else if (c === constants_1.TEMPLATE_OBJECT_START && (cursor.currentTarget.type === common_1$1.TargetType.TEMPLATE_OBJECT || cursor.currentTarget.type === common_1$1.TargetType.OBJECT || cursor.currentTarget.type === common_1$1.TargetType.ARRAY)) {
        if (cursor.currentTarget.type !== common_1$1.TargetType.TEMPLATE_OBJECT) {
          var parentTarget = cursor.currentTarget;
          cursor.currentTarget = { type: common_1$1.TargetType.TEMPLATE_OBJECT, value: void 0, currentTokens: [], currentRoute: [], paths: [], level: 0, parentTarget };
          cursor.stack[++cursor.pointer] = cursor.currentTarget;
        } else {
          for (var i = 0; i < cursor.currentTarget.currentTokens.length - 1; i++) {
            var currentToken = cursor.currentTarget.currentTokens[i];
            cursor.currentTarget.paths[cursor.currentTarget.paths.length] = cursor.currentTarget.currentRoute.concat(currentToken);
          }
          if (cursor.currentTarget.currentToken != null) {
            cursor.currentTarget.currentRoute.push(cursor.currentTarget.currentToken);
          }
          cursor.currentTarget.currentTokens = [];
          cursor.currentTarget.level++;
        }
      } else if (c === constants_1.TEMPLATE_OBJECT_END && cursor.currentTarget.type === common_1$1.TargetType.TEMPLATE_OBJECT) {
        for (var i = 0; i < cursor.currentTarget.currentTokens.length; i++) {
          var currentToken = cursor.currentTarget.currentTokens[i];
          cursor.currentTarget.paths[cursor.currentTarget.paths.length] = cursor.currentTarget.currentRoute.concat(currentToken);
        }
        cursor.currentTarget.currentTokens = [];
        cursor.currentTarget.currentRoute = cursor.currentTarget.currentRoute.slice(0, -1);
        cursor.currentTarget.level--;
        if (cursor.currentTarget.level < 0) {
          var paths = cursor.currentTarget.paths;
          var parentTarget = cursor.currentTarget.parentTarget;
          cursor.pointer--;
          if (parentTarget.type === common_1$1.TargetType.ARRAY) {
            cursor.currentTarget = { type: common_1$1.TargetType.TEMPLATE_OBJECT_ELEMENTS, value: parentTarget.value, paths, currentPathIndex: 0, expectedPaths: paths.length, currentObject: {} };
          } else if (parentTarget.type === common_1$1.TargetType.OBJECT) {
            cursor.currentTarget = { type: common_1$1.TargetType.TEMPLATE_OBJECT_PROPERTIES, value: parentTarget.value, paths, currentPathIndex: -1, expectedPaths: paths.length, currentObject: {} };
          }
          cursor.stack[++cursor.pointer] = cursor.currentTarget;
        }
      } else if (c === constants_1.TEMPLATE_OBJECT_FINAL) {
        cursor.currentTarget = cursor.stack[--cursor.pointer];
      } else {
        if (!element_1.decompressElement(c, cursor, data, orderedIndex)) {
          return;
        }
      }
    }
  }
  stages.decompressStages = decompressStages;
  Object.defineProperty(decompress$1, "__esModule", { value: true });
  var common_1 = common;
  var stages_1 = stages;
  function makeOrderedIndex() {
    return {
      strings: [],
      integers: [],
      floats: [],
      dates: [],
      lpDates: []
    };
  }
  decompress$1.makeOrderedIndex = makeOrderedIndex;
  function makeCursor(drain) {
    var rootTarget = { type: common_1.TargetType.SCALAR, value: void 0 };
    var stack = new Array(10);
    stack[0] = rootTarget;
    return { index: 0, rootTarget, stack, currentTarget: rootTarget, pointer: 0, drain };
  }
  function decompress(data, orderedIndex) {
    var cursor = makeCursor(true);
    stages_1.decompressStages(cursor, data, orderedIndex);
    return cursor.rootTarget.value;
  }
  decompress$1.decompress = decompress;
  function decompressIncremental(orderedIndex) {
    var cursor = makeCursor(false);
    var buffer = "";
    function increment(data) {
      if (data === null) {
        cursor.drain = true;
      } else if (data.length === 0) {
        return;
      } else {
        buffer += data;
      }
      var cursorIndexBefore = cursor.index;
      stages_1.decompressStages(cursor, buffer, orderedIndex);
      var movedAmount = cursor.index - cursorIndexBefore;
      if (movedAmount > 0) {
        buffer = buffer.substring(movedAmount);
        cursor.index -= movedAmount;
      }
    }
    return { increment, cursor };
  }
  decompress$1.decompressIncremental = decompressIncremental;
  (function(exports) {
    function __export(m) {
      for (var p in m)
        if (!exports.hasOwnProperty(p))
          exports[p] = m[p];
    }
    Object.defineProperty(exports, "__esModule", { value: true });
    var compress_1 = compress$1;
    var writer_12 = writer;
    var decompress_1 = decompress$1;
    __export(writer);
    __export(common);
    function parse(data) {
      var orderedIndex = decompress_1.makeOrderedIndex();
      return decompress_1.decompress(data, orderedIndex);
    }
    exports.parse = parse;
    function parseIncremental() {
      var orderedIndex = decompress_1.makeOrderedIndex();
      var _a = decompress_1.decompressIncremental(orderedIndex), cursor = _a.cursor, increment = _a.increment;
      return function(data) {
        increment(data);
        if (data === null) {
          return cursor.rootTarget.value;
        }
      };
    }
    exports.parseIncremental = parseIncremental;
    function stringifyTo(data, writer2, options) {
      if (options === void 0) {
        options = {};
      }
      var invertedIndex = compress_1.makeInvertedIndex();
      var context = compress_1.makeCompressContext();
      compress_1.compress(context, data, invertedIndex, writer2, options);
      writer2.end();
    }
    exports.stringifyTo = stringifyTo;
    function stringify(data, options) {
      var writer2 = new writer_12.ZipsonStringWriter();
      stringifyTo(data, writer2, options);
      return writer2.value;
    }
    exports.stringify = stringify;
  })(lib);
  const useStore = defineStore("store", {
    state() {
      return {
        // ####################
        // 元件相關狀態
        // ####################
        isDarkMode: false,
        isToolbarsShow: false,
        isPopupShow: {
          sheet: false,
          font: false,
          settings: false,
          menu: false
        },
        // ####################
        // 偏好設定相關狀態
        // ####################
        agreeToArchiveSheet: true,
        // ####################
        // 譜面相關狀態
        // ####################
        transpose: 0,
        /** 在 `StoreHandler` 裡賦值 */
        originalCapo: 0,
        /** 在 `StoreHandler` 裡賦值,HTML 格式 */
        originalKey: "",
        /** `font-size` 的變化值 */
        fontSizeDelta: 0,
        /** 在 `StoreHandler` 裡賦值,單位為 px */
        originalFontSize: 0,
        /** 在 `StoreHandler` 裡賦值,單位為 px */
        originalLineHeight: 0
      };
    },
    persist: {
      key: "plus91-preferences",
      storage: MonkeyStorage,
      deserialize: lib.parse,
      serialize: lib.stringify,
      paths: ["isDarkMode", "agreeToArchiveSheet"],
      beforeRestore() {
        console.log("[91 Plus] 讀取偏好設置中");
      },
      afterRestore() {
        console.log("[91 Plus] 偏好設置讀取完畢");
      },
      debug: true
    },
    getters: {
      currentCapo() {
        return this.originalCapo + this.transpose;
      },
      currentKey() {
        return new Chord(this.originalKey).transpose(-this.transpose).toFormattedString();
      }
    },
    actions: {
      toggleToolbars() {
        if (this.isToolbarsShow) {
          this.closePopups();
        }
        this.isToolbarsShow = !this.isToolbarsShow;
      },
      closePopups() {
        for (const popup in this.isPopupShow) {
          this.isPopupShow[popup] = false;
        }
      },
      /** @param {'sheet'|'settings'|'menu'} name */
      openPopup(name) {
        for (const popup in this.isPopupShow) {
          if (popup === name) {
            this.isPopupShow[popup] = !this.isPopupShow[popup];
          } else {
            this.isPopupShow[popup] = false;
          }
        }
      },
      plusTranspose(numberToPlus) {
        let newTranspose = this.transpose + numberToPlus;
        const newCapo = this.originalCapo + newTranspose;
        if (newCapo === 12 || newCapo === -12) {
          newTranspose = -this.originalCapo;
        }
        this.transpose = newTranspose;
      }
    }
  });
  const _hoisted_1$8 = { class: "material-symbols-rounded" };
  const _sfc_main$9 = {
    __name: "ToolbarIcon",
    props: {
      icon: String,
      color: {
        type: String,
        default: "#fffe"
      }
    },
    setup(__props) {
      vue.useCssVars((_ctx) => ({
        "46f2ba82": __props.color
      }));
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createElementBlock("span", _hoisted_1$8, vue.toDisplayString(__props.icon), 1);
      };
    }
  };
  const ToolbarIcon = /* @__PURE__ */ _export_sfc(_sfc_main$9, [["__scopeId", "data-v-db75303e"]]);
  const _hoisted_1$7 = { id: "plus91-sheet-popup" };
  const _hoisted_2$6 = { class: "sheet-popup-container" };
  const _hoisted_3$2 = { class: "transpose-button-group" };
  const _hoisted_4$1 = { class: "text-capo" };
  const _hoisted_5$1 = ["innerHTML"];
  const _hoisted_6$1 = { class: "transpose-range-container" };
  const _hoisted_7 = ["value"];
  const _sfc_main$8 = {
    __name: "SheetPopup",
    setup(__props) {
      const store = useStore();
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "slide-and-fade" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1$7, [
              vue.createElementVNode("div", _hoisted_2$6, [
                vue.createElementVNode("div", _hoisted_3$2, [
                  vue.createElementVNode("button", {
                    class: "capo-button decrease",
                    onClick: _cache[0] || (_cache[0] = () => {
                      vue.unref(store).plusTranspose(-1);
                    })
                  }, [
                    vue.createVNode(ToolbarIcon, {
                      icon: "arrow_left",
                      color: "black"
                    })
                  ]),
                  vue.createElementVNode("button", {
                    class: "capo-button info",
                    onClick: _cache[1] || (_cache[1] = () => {
                      vue.unref(store).transpose = 0;
                    })
                  }, [
                    vue.createTextVNode(" CAPO:"),
                    vue.createElementVNode("span", _hoisted_4$1, vue.toDisplayString(vue.unref(store).currentCapo), 1),
                    vue.createTextVNode(" ("),
                    vue.createElementVNode("span", {
                      class: "text-key",
                      innerHTML: vue.unref(store).currentKey
                    }, null, 8, _hoisted_5$1),
                    vue.createTextVNode(") ")
                  ]),
                  vue.createElementVNode("button", {
                    class: "capo-button increase",
                    onClick: _cache[2] || (_cache[2] = () => {
                      vue.unref(store).plusTranspose(1);
                    })
                  }, [
                    vue.createVNode(ToolbarIcon, {
                      icon: "arrow_right",
                      color: "black"
                    })
                  ])
                ]),
                vue.createElementVNode("div", _hoisted_6$1, [
                  vue.createElementVNode("input", {
                    type: "range",
                    min: "-11",
                    max: "11",
                    value: vue.unref(store).currentCapo,
                    onInput: _cache[3] || (_cache[3] = ($event) => {
                      vue.unref(store).transpose = $event.target.value - vue.unref(store).originalCapo;
                    })
                  }, null, 40, _hoisted_7)
                ])
              ])
            ], 512), [
              [vue.vShow, vue.unref(store).isPopupShow.sheet]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const SheetPopup = /* @__PURE__ */ _export_sfc(_sfc_main$8, [["__scopeId", "data-v-95b1456e"]]);
  const _hoisted_1$6 = { id: "plus91-font-popup" };
  const _hoisted_2$5 = { class: "font-popup-container" };
  const _hoisted_3$1 = { class: "font-button-group" };
  const _sfc_main$7 = {
    __name: "FontSizePopup",
    setup(__props) {
      const store = useStore();
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "slide-and-fade" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1$6, [
              vue.createElementVNode("div", _hoisted_2$5, [
                vue.createElementVNode("div", _hoisted_3$1, [
                  vue.createElementVNode("button", {
                    class: "capo-button decrease",
                    onClick: _cache[0] || (_cache[0] = () => {
                      vue.unref(store).fontSizeDelta--;
                    })
                  }, [
                    vue.createVNode(ToolbarIcon, {
                      icon: "arrow_left",
                      color: "black"
                    })
                  ]),
                  vue.createElementVNode("button", {
                    class: "capo-button info",
                    onClick: _cache[1] || (_cache[1] = () => {
                      vue.unref(store).fontSizeDelta = 0;
                    })
                  }, vue.toDisplayString(vue.unref(store).originalFontSize + vue.unref(store).fontSizeDelta) + "px ", 1),
                  vue.createElementVNode("button", {
                    class: "capo-button increase",
                    onClick: _cache[2] || (_cache[2] = () => {
                      vue.unref(store).fontSizeDelta++;
                    })
                  }, [
                    vue.createVNode(ToolbarIcon, {
                      icon: "arrow_right",
                      color: "black"
                    })
                  ])
                ])
              ])
            ], 512), [
              [vue.vShow, vue.unref(store).isPopupShow.font]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const FontSizePopup = /* @__PURE__ */ _export_sfc(_sfc_main$7, [["__scopeId", "data-v-f2a3726b"]]);
  const _withScopeId = (n) => (vue.pushScopeId("data-v-430d5768"), n = n(), vue.popScopeId(), n);
  const _hoisted_1$5 = { id: "plus91-settings-popup" };
  const _hoisted_2$4 = { class: "settings-popup-container" };
  const _hoisted_3 = { class: "setting-item" };
  const _hoisted_4 = /* @__PURE__ */ _withScopeId(() => /* @__PURE__ */ vue.createElementVNode("span", null, "深色模式", -1));
  const _hoisted_5 = { class: "setting-item" };
  const _hoisted_6 = /* @__PURE__ */ _withScopeId(() => /* @__PURE__ */ vue.createElementVNode("span", null, "協助測試雲端備份樂譜功能", -1));
  const _sfc_main$6 = {
    __name: "SettingsPopup",
    setup(__props) {
      const store = useStore();
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "slide-and-fade" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1$5, [
              vue.createElementVNode("div", _hoisted_2$4, [
                vue.createElementVNode("label", _hoisted_3, [
                  _hoisted_4,
                  vue.withDirectives(vue.createElementVNode("input", {
                    type: "checkbox",
                    "onUpdate:modelValue": _cache[0] || (_cache[0] = ($event) => vue.unref(store).isDarkMode = $event)
                  }, null, 512), [
                    [vue.vModelCheckbox, vue.unref(store).isDarkMode]
                  ])
                ]),
                vue.createElementVNode("label", _hoisted_5, [
                  _hoisted_6,
                  vue.withDirectives(vue.createElementVNode("input", {
                    type: "checkbox",
                    "onUpdate:modelValue": _cache[1] || (_cache[1] = ($event) => vue.unref(store).agreeToArchiveSheet = $event)
                  }, null, 512), [
                    [vue.vModelCheckbox, vue.unref(store).agreeToArchiveSheet]
                  ])
                ])
              ])
            ], 512), [
              [vue.vShow, vue.unref(store).isPopupShow.settings]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const SettingsPopup = /* @__PURE__ */ _export_sfc(_sfc_main$6, [["__scopeId", "data-v-430d5768"]]);
  const _hoisted_1$4 = { class: "icon-button" };
  const _hoisted_2$3 = { class: "button-text" };
  const _sfc_main$5 = {
    __name: "MenuButton",
    props: {
      icon: String,
      name: String,
      color: String
    },
    setup(__props) {
      vue.useCssVars((_ctx) => ({
        "045d7cb5": __props.color
      }));
      const props = __props;
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createElementBlock("div", _hoisted_1$4, [
          vue.createVNode(ToolbarIcon, {
            icon: props.icon,
            color: props.color
          }, null, 8, ["icon", "color"]),
          vue.createElementVNode("div", _hoisted_2$3, vue.toDisplayString(props.name), 1)
        ]);
      };
    }
  };
  const MenuButton = /* @__PURE__ */ _export_sfc(_sfc_main$5, [["__scopeId", "data-v-29985f23"]]);
  class ChordSheetDocument {
    constructor() {
      this.el = {
        mtitle: document.getElementById("mtitle"),
        tkinfo: document.querySelector(".tkinfo"),
        capoSelect: document.querySelector(".capo .select"),
        tinfo: document.querySelector(".tinfo"),
        tone_z: document.getElementById("tone_z")
      };
    }
    getId() {
      const urlParams = new URLSearchParams(window.location.search);
      return Number(urlParams.get("id"));
    }
    getTitle() {
      return this.el.mtitle.innerText.trim();
    }
    getKey() {
      var _a;
      const match = (_a = this.el.tkinfo) == null ? void 0 : _a.innerText.match(new RegExp("(?<=原調:)\\w*"));
      return match ? match[0].trim() : "";
    }
    getPlay() {
      var _a;
      const match = (_a = this.el.capoSelect) == null ? void 0 : _a.innerText.split(/\s*\/\s*/);
      return match ? match[1].trim() : "";
    }
    getCapo() {
      var _a;
      const match = (_a = this.el.capoSelect) == null ? void 0 : _a.innerText.split(/\s*\/\s*/);
      return match ? Number(match[0]) : 0;
    }
    getSinger() {
      var _a;
      const match = (_a = this.el.tinfo) == null ? void 0 : _a.innerText.match(new RegExp("(?<=演唱:).*(?=\\n|$)"));
      return match ? match[0].trim() : "";
    }
    getComposer() {
      var _a;
      const match = (_a = this.el.tinfo) == null ? void 0 : _a.innerText.match(new RegExp("(?<=曲:).*?(?=詞:|$)"));
      return match ? match[0].trim() : "";
    }
    getLyricist() {
      var _a;
      const match = (_a = this.el.tinfo) == null ? void 0 : _a.innerText.match(new RegExp("(?<=詞:).*?(?=曲:|$)"));
      return match ? match[0].trim() : "";
    }
    getBpm() {
      var _a;
      const match = (_a = this.el.tkinfo) == null ? void 0 : _a.innerText.match(/\d+/);
      return match ? Number(match[0]) : 0;
    }
    getSheetText() {
      const formattedChordSheet = this.el.tone_z.innerText.replaceAll(/\s+?\n/g, "\n").replaceAll("\n\n", "\n").trim().replaceAll(/\s+/g, (match) => {
        return `{%${match.length}%}`;
      });
      return formattedChordSheet;
    }
  }
  const _hoisted_1$3 = { id: "plus91-menu-popup" };
  const _hoisted_2$2 = { class: "menu-popup-container" };
  const _sfc_main$4 = {
    __name: "MenuPopup",
    setup(__props) {
      const store = useStore();
      const searchOnYoutube = () => {
        const chordSheetDocument = new ChordSheetDocument();
        const title = chordSheetDocument.getTitle();
        const artist = chordSheetDocument.getSinger();
        const url = `https://www.youtube.com/results?search_query=${title}+${artist}`;
        window.open(url, "_blank").focus();
      };
      const goToGithubPage = () => {
        const url = "https://github.com/DonkeyBear/91Plus/blob/main/README.md";
        window.open(url, "_blank").focus();
      };
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "slide-and-fade" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1$3, [
              vue.createElementVNode("div", _hoisted_2$2, [
                vue.createVNode(MenuButton, {
                  icon: "video_library",
                  name: "搜尋 YouTube",
                  color: "gray",
                  onClick: searchOnYoutube
                }),
                vue.createVNode(MenuButton, {
                  icon: "info",
                  name: "關於 91 Plus",
                  color: "gray",
                  onClick: goToGithubPage
                })
              ])
            ], 512), [
              [vue.vShow, vue.unref(store).isPopupShow.menu]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const MenuPopup = /* @__PURE__ */ _export_sfc(_sfc_main$4, [["__scopeId", "data-v-f742366d"]]);
  const _hoisted_1$2 = { id: "plus91-footer" };
  const _hoisted_2$1 = { class: "footer-container" };
  const _sfc_main$3 = {
    __name: "Footer",
    props: {
      active: Boolean
    },
    setup(__props) {
      const store = useStore();
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "slide" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1$2, [
              vue.createElementVNode("div", _hoisted_2$1, [
                vue.createVNode(ToolbarIcon, {
                  icon: "music_note",
                  onClick: _cache[0] || (_cache[0] = ($event) => vue.unref(store).openPopup("sheet"))
                }),
                vue.createVNode(ToolbarIcon, {
                  icon: "format_size",
                  onClick: _cache[1] || (_cache[1] = ($event) => vue.unref(store).openPopup("font"))
                }),
                vue.createVNode(ToolbarIcon, {
                  icon: "settings",
                  onClick: _cache[2] || (_cache[2] = ($event) => vue.unref(store).openPopup("settings"))
                }),
                vue.createVNode(ToolbarIcon, {
                  icon: "menu",
                  onClick: _cache[3] || (_cache[3] = ($event) => vue.unref(store).openPopup("menu"))
                }),
                vue.createVNode(SheetPopup),
                vue.createVNode(FontSizePopup),
                vue.createVNode(SettingsPopup),
                vue.createVNode(MenuPopup)
              ])
            ], 512), [
              [vue.vShow, __props.active]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const Footer = /* @__PURE__ */ _export_sfc(_sfc_main$3, [["__scopeId", "data-v-d937ce2c"]]);
  const _hoisted_1$1 = { id: "plus91-header" };
  const _hoisted_2 = { class: "header-container" };
  const _sfc_main$2 = {
    __name: "Header",
    props: {
      active: Boolean
    },
    setup(__props) {
      const searchText = vue.ref("");
      const search = () => {
        if (!searchText.value) {
          return;
        }
        const url = `https://www.91pu.com.tw/plus/search.php?keyword=${searchText.value}`;
        window.open(url, "_blank").focus();
      };
      const backToPreviousPage = () => {
        history.back();
      };
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "slide" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1$1, [
              vue.createElementVNode("div", _hoisted_2, [
                vue.createVNode(ToolbarIcon, {
                  icon: "arrow_back_ios_new",
                  onClick: backToPreviousPage
                }),
                vue.withDirectives(vue.createElementVNode("input", {
                  type: "text",
                  placeholder: "91 Plus",
                  "onUpdate:modelValue": _cache[0] || (_cache[0] = ($event) => searchText.value = $event),
                  onKeydown: vue.withKeys(search, ["enter"])
                }, null, 544), [
                  [
                    vue.vModelText,
                    searchText.value,
                    void 0,
                    { trim: true }
                  ]
                ]),
                vue.createVNode(ToolbarIcon, {
                  icon: "search",
                  onClick: _cache[1] || (_cache[1] = ($event) => search())
                })
              ])
            ], 512), [
              [vue.vShow, __props.active]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const Header = /* @__PURE__ */ _export_sfc(_sfc_main$2, [["__scopeId", "data-v-183b97c5"]]);
  const _hoisted_1 = { id: "dark-mode-overlay" };
  const _sfc_main$1 = {
    __name: "DarkModeOverlay",
    props: {
      active: Boolean
    },
    setup(__props) {
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createBlock(vue.Transition, { name: "fade" }, {
          default: vue.withCtx(() => [
            vue.withDirectives(vue.createElementVNode("div", _hoisted_1, null, 512), [
              [vue.vShow, __props.active]
            ])
          ]),
          _: 1
        });
      };
    }
  };
  const DarkModeOverlay = /* @__PURE__ */ _export_sfc(_sfc_main$1, [["__scopeId", "data-v-a07a2507"]]);
  const _sfc_main = {
    __name: "App",
    setup(__props) {
      const store = useStore();
      return (_ctx, _cache) => {
        return vue.openBlock(), vue.createElementBlock(vue.Fragment, null, [
          vue.createVNode(TriggerOverlay, {
            onClick: vue.unref(store).toggleToolbars
          }, null, 8, ["onClick"]),
          vue.createVNode(Header, {
            active: vue.unref(store).isToolbarsShow
          }, null, 8, ["active"]),
          vue.createVNode(Footer, {
            active: vue.unref(store).isToolbarsShow
          }, null, 8, ["active"]),
          vue.createVNode(DarkModeOverlay, {
            active: vue.unref(store).isDarkMode
          }, null, 8, ["active"])
        ], 64);
      };
    }
  };
  class ChordSheetElement {
    /** @param {HTMLElement} chordSheetElement  */
    constructor(chordSheetElement) {
      /** @param {NodeList} nodeList */
      __privateAdd(this, _unformat);
      this.chordSheetElement = chordSheetElement;
    }
    /**
     * 將 Header 和譜上的和弦移調,並實質修改於 DOM
     * @param {number} delta 相對於當前調的移調值
     */
    static transposeSheet(delta) {
      $("#tone_z .tf").each(function() {
        const chord = new Chord($(this).text());
        const newChordHTML = chord.transpose(-delta).toFormattedString();
        $(this).html(newChordHTML);
      });
    }
    /** @returns {ChordSheetElement} */
    formatUnderlines() {
      const underlineEl = this.chordSheetElement.querySelectorAll("u");
      const doubleUnderlineEl = this.chordSheetElement.querySelectorAll("abbr");
      underlineEl.forEach((el) => {
        el.innerText = `{_${el.innerText}_}`;
      });
      doubleUnderlineEl.forEach((el) => {
        el.innerText = `{=${el.innerText}=}`;
      });
      return this;
    }
    /** @returns {ChordSheetElement} */
    unformatUnderlines() {
      const underlineEl = this.chordSheetElement.querySelectorAll("u");
      const doubleUnderlineEl = this.chordSheetElement.querySelectorAll("abbr");
      __privateMethod(this, _unformat, unformat_fn).call(this, underlineEl);
      __privateMethod(this, _unformat, unformat_fn).call(this, doubleUnderlineEl);
      return this;
    }
  }
  _unformat = new WeakSet();
  unformat_fn = function(nodeList) {
    nodeList.forEach((el) => {
      el.innerHTML = el.innerText.replaceAll(/{_|{=|=}|_}/g, "").replaceAll(
        /[a-zA-Z0-9#/]+/g,
        /* html */
        `<span class="tf">$&</span>`
      );
    });
  };
  function redirect() {
    const currentUrl = window.location.href;
    if (/\/song\//.test(currentUrl)) {
      const sheetId = currentUrl.match(new RegExp("(?<=\\/)\\d+(?=\\.)"))[0];
      const newUrl = `https://www.91pu.com.tw/m/tone.shtml?id=${sheetId}`;
      window.location.replace(newUrl);
    }
  }
  function injectGtag() {
    const newScript = document.createElement("script");
    newScript.src = "https://www.googletagmanager.com/gtag/js?id=G-JF4S3HZY31";
    newScript.async = true;
    document.head.appendChild(newScript);
    newScript.onload = () => {
      window.dataLayer = window.dataLayer || [];
      function gtag() {
        window.dataLayer.push(arguments);
      }
      gtag("js", /* @__PURE__ */ new Date());
      gtag("config", "G-JF4S3HZY31");
    };
  }
  function injectIconFont() {
    const materialSymbols = document.createElement("link");
    materialSymbols.rel = "stylesheet";
    materialSymbols.href = "https://fonts.googleapis.com/css2?family=Material+Symbols+Rounded:opsz,wght,FILL,GRAD@24,500,0,0";
    document.head.appendChild(materialSymbols);
  }
  function getQueryParams() {
    const url = new URL(window.location.href);
    const params = {
      transpose: +url.searchParams.get("transpose"),
      darkMode: !!url.searchParams.get("darkmode")
    };
    return params;
  }
  function changeTitle() {
    const newTitle = $("#mtitle").text().trim();
    document.title = `${newTitle} | 91+`;
  }
  function archiveChordSheet() {
    const sheet = document.getElementById("tone_z");
    const chordSheetDocument = new ChordSheetDocument();
    try {
      const chordSheetElement = new ChordSheetElement(sheet);
      chordSheetElement.formatUnderlines();
      const formBody = {
        id: chordSheetDocument.getId(),
        title: chordSheetDocument.getTitle(),
        key: chordSheetDocument.getKey(),
        play: chordSheetDocument.getPlay(),
        capo: chordSheetDocument.getCapo(),
        singer: chordSheetDocument.getSinger(),
        composer: chordSheetDocument.getComposer(),
        lyricist: chordSheetDocument.getLyricist(),
        bpm: chordSheetDocument.getBpm(),
        sheet_text: chordSheetDocument.getSheetText()
      };
      chordSheetElement.unformatUnderlines();
      fetch("https://91-plus-plus-api.fly.dev/archive", {
        method: "POST",
        headers: {
          "Content-Type": "application/json"
        },
        body: JSON.stringify(formBody)
      }).then((response) => {
        console.log("[91 Plus] 雲端樂譜備份成功:", response);
      }).catch((error) => {
        console.error("[91 Plus] 雲端樂譜備份失敗:", error);
      });
    } catch {
      console.warn("[91 Plus] 樂譜解析失敗,無法備份");
      fetch(
        `https://91-plus-plus-api.fly.dev/report?id=${chordSheetDocument.getId()}`
      );
    }
  }
  function initMutationObserver() {
    return new MutationObserver((records, observer) => {
      const isMutationDone = !!document.querySelector("#tone_z").childElementCount;
      if (!isMutationDone) {
        return;
      }
      $("body").trigger("mutation.done");
      observer.disconnect();
    }).observe(document.body, { childList: true, subtree: true });
  }
  function onDomReady(callback) {
    $("body").on("mutation.done", callback);
  }
  class StoreHandler {
    constructor() {
      /** 當 `#store.transpose` 變動時,將譜面上的和弦進行移調 */
      __privateAdd(this, _watchTranspose);
      __privateAdd(this, _watchFontSize);
      // 命 `#store` 為私有屬性,在建立實例時再賦值,避免衝突
      __privateAdd(this, _store, void 0);
      __privateSet(this, _store, useStore());
    }
    initState() {
      const capoSelected = $(".capo .select").eq(0).text().trim();
      const originalCapo = +capoSelected.split(/\s*\/\s*/)[0];
      const originalKey = capoSelected.split(/\s*\/\s*/)[1];
      __privateGet(this, _store).originalCapo = originalCapo;
      __privateGet(this, _store).originalKey = originalKey;
      const fontSize = +$("#tone_z").css("font-size").match(/^\d+/)[0];
      const lineHeight = +$("#tone_z > p").css("line-height").match(/^\d+/)[0];
      __privateGet(this, _store).originalFontSize = fontSize;
      __privateGet(this, _store).originalLineHeight = lineHeight;
      const params = getQueryParams();
      if (params.transpose) {
        __privateGet(this, _store).transpose = params.transpose;
      }
    }
    start() {
      __privateMethod(this, _watchTranspose, watchTranspose_fn).call(this);
      __privateMethod(this, _watchFontSize, watchFontSize_fn).call(this);
      return this;
    }
  }
  _store = new WeakMap();
  _watchTranspose = new WeakSet();
  watchTranspose_fn = function() {
    vue.watch(() => {
      return __privateGet(this, _store).transpose;
    }, (newValue, oldValue) => {
      ChordSheetElement.transposeSheet(newValue - oldValue);
    });
  };
  _watchFontSize = new WeakSet();
  watchFontSize_fn = function() {
    vue.watch(() => {
      return __privateGet(this, _store).fontSizeDelta;
    }, (newValue) => {
      const oFontSize = __privateGet(this, _store).originalFontSize;
      const oLineHeight = __privateGet(this, _store).originalLineHeight;
      $("#tone_z").css("font-size", `${oFontSize + newValue}px`);
      $("#tone_z > p").css("line-height", `${oLineHeight + newValue}px`);
    });
  };
  function init() {
    redirect();
    injectGtag();
    injectIconFont();
    initMutationObserver();
    const storeHandler = new StoreHandler().start();
    onDomReady(() => {
      changeTitle();
      storeHandler.initState();
      const store = useStore();
      if (store.agreeToArchiveSheet) {
        archiveChordSheet();
      }
    });
  }
  const pinia = createPinia();
  pinia.use(src_default);
  vue.createApp(_sfc_main).use(pinia).mount(
    (() => {
      const app = document.createElement("div");
      app.id = "vue-91plus";
      document.body.append(app);
      return app;
    })()
  );
  init();

})(Vue);

QingJ © 2025

镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址