vue3-router-tab 1.0.4 → 1.0.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,36 +1,36 @@
1
1
  import './vue3-router-tab.css';
2
- import { defineComponent as oe, inject as z, computed as S, unref as Oe, provide as U, ref as J, watch as x, h as Ve, getCurrentInstance as ae, reactive as Ce, shallowRef as Ie, nextTick as se, onMounted as _e, onBeforeUnmount as Ke, resolveComponent as Ne, createElementBlock as A, openBlock as T, createElementVNode as I, createCommentVNode as K, renderSlot as re, createVNode as j, TransitionGroup as $e, mergeProps as Q, withCtx as M, Fragment as le, renderList as ce, withModifiers as B, normalizeClass as ue, createTextVNode as Le, toDisplayString as fe, Transition as de, createBlock as W, KeepAlive as De, resolveDynamicComponent as pe, normalizeStyle as je } from "vue";
3
- import { defineStore as Me } from "pinia";
2
+ import { defineComponent as ae, inject as z, computed as S, unref as Ve, provide as U, ref as J, watch as x, h as Ie, getCurrentInstance as se, reactive as _e, shallowRef as Ke, nextTick as re, onMounted as Ae, onBeforeUnmount as Ne, resolveComponent as $e, createElementBlock as A, openBlock as T, createElementVNode as I, createCommentVNode as K, renderSlot as le, createVNode as j, TransitionGroup as Le, mergeProps as Q, withCtx as M, Fragment as ce, renderList as ue, withModifiers as B, normalizeClass as fe, createTextVNode as De, toDisplayString as de, Transition as pe, createBlock as W, KeepAlive as je, resolveDynamicComponent as be, normalizeStyle as Me } from "vue";
3
+ import { defineStore as Be } from "pinia";
4
4
  /*!
5
5
  * vue-router v4.5.1
6
6
  * (c) 2025 Eduardo San Martin Morote
7
7
  * @license MIT
8
8
  */
9
- const Be = typeof document < "u", Ge = Object.assign, Ue = Array.isArray;
10
- function ze(e) {
9
+ const Ge = typeof document < "u", Ue = Object.assign, ze = Array.isArray;
10
+ function Je(e) {
11
11
  const n = Array.from(arguments).slice(1);
12
12
  console.warn.apply(console, ["[Vue Router warn]: " + e].concat(n));
13
13
  }
14
- function Je(e, n) {
14
+ function He(e, n) {
15
15
  return (e.aliasOf || e) === (n.aliasOf || n);
16
16
  }
17
- var be;
17
+ var ve;
18
18
  (function(e) {
19
19
  e.pop = "pop", e.push = "push";
20
- })(be || (be = {}));
21
- var ve;
20
+ })(ve || (ve = {}));
21
+ var he;
22
22
  (function(e) {
23
23
  e.back = "back", e.forward = "forward", e.unknown = "";
24
- })(ve || (ve = {}));
24
+ })(he || (he = {}));
25
25
  Symbol(process.env.NODE_ENV !== "production" ? "navigation failure" : "");
26
- var he;
26
+ var me;
27
27
  (function(e) {
28
28
  e[e.aborted = 4] = "aborted", e[e.cancelled = 8] = "cancelled", e[e.duplicated = 16] = "duplicated";
29
- })(he || (he = {}));
30
- const He = Symbol(process.env.NODE_ENV !== "production" ? "router view location matched" : ""), me = Symbol(process.env.NODE_ENV !== "production" ? "router view depth" : "");
29
+ })(me || (me = {}));
30
+ const qe = Symbol(process.env.NODE_ENV !== "production" ? "router view location matched" : ""), ye = Symbol(process.env.NODE_ENV !== "production" ? "router view depth" : "");
31
31
  Symbol(process.env.NODE_ENV !== "production" ? "router" : "");
32
32
  Symbol(process.env.NODE_ENV !== "production" ? "route location" : "");
33
- const ye = Symbol(process.env.NODE_ENV !== "production" ? "router view location" : ""), qe = /* @__PURE__ */ oe({
33
+ const ge = Symbol(process.env.NODE_ENV !== "production" ? "router view location" : ""), Xe = /* @__PURE__ */ ae({
34
34
  name: "RouterView",
35
35
  // #674 we manually inherit them
36
36
  inheritAttrs: !1,
@@ -45,62 +45,62 @@ const ye = Symbol(process.env.NODE_ENV !== "production" ? "router view location"
45
45
  // https://github.com/vuejs/router/issues/1315
46
46
  compatConfig: { MODE: 3 },
47
47
  setup(e, { attrs: n, slots: a }) {
48
- process.env.NODE_ENV !== "production" && Ye();
49
- const t = z(ye), r = S(() => e.route || t.value), u = z(me, 0), d = S(() => {
50
- let h = Oe(u);
51
- const { matched: b } = r.value;
48
+ process.env.NODE_ENV !== "production" && Fe();
49
+ const t = z(ge), i = S(() => e.route || t.value), u = z(ye, 0), d = S(() => {
50
+ let h = Ve(u);
51
+ const { matched: b } = i.value;
52
52
  let m;
53
53
  for (; (m = b[h]) && !m.components; )
54
54
  h++;
55
55
  return h;
56
- }), f = S(() => r.value.matched[d.value]);
57
- U(me, S(() => d.value + 1)), U(He, f), U(ye, r);
56
+ }), f = S(() => i.value.matched[d.value]);
57
+ U(ye, S(() => d.value + 1)), U(qe, f), U(ge, i);
58
58
  const p = J();
59
59
  return x(() => [p.value, f.value, e.name], ([h, b, m], [k, y, C]) => {
60
60
  b && (b.instances[m] = h, y && y !== b && h && h === k && (b.leaveGuards.size || (b.leaveGuards = y.leaveGuards), b.updateGuards.size || (b.updateGuards = y.updateGuards))), h && b && // if there is no instance but to and from are the same this might be
61
61
  // the first visit
62
- (!y || !Je(b, y) || !k) && (b.enterCallbacks[m] || []).forEach((_) => _(h));
62
+ (!y || !He(b, y) || !k) && (b.enterCallbacks[m] || []).forEach((_) => _(h));
63
63
  }, { flush: "post" }), () => {
64
- const h = r.value, b = e.name, m = f.value, k = m && m.components[b];
64
+ const h = i.value, b = e.name, m = f.value, k = m && m.components[b];
65
65
  if (!k)
66
- return ge(a.default, { Component: k, route: h });
67
- const y = m.props[b], C = y ? y === !0 ? h.params : typeof y == "function" ? y(h) : y : null, g = Ve(k, Ge({}, C, n, {
66
+ return we(a.default, { Component: k, route: h });
67
+ const y = m.props[b], C = y ? y === !0 ? h.params : typeof y == "function" ? y(h) : y : null, g = Ie(k, Ue({}, C, n, {
68
68
  onVnodeUnmounted: (E) => {
69
69
  E.component.isUnmounted && (m.instances[b] = null);
70
70
  },
71
71
  ref: p
72
72
  }));
73
- if (process.env.NODE_ENV !== "production" && Be && g.ref) {
73
+ if (process.env.NODE_ENV !== "production" && Ge && g.ref) {
74
74
  const E = {
75
75
  depth: d.value,
76
76
  name: m.name,
77
77
  path: m.path,
78
78
  meta: m.meta
79
79
  };
80
- (Ue(g.ref) ? g.ref.map((P) => P.i) : [g.ref.i]).forEach((P) => {
80
+ (ze(g.ref) ? g.ref.map((P) => P.i) : [g.ref.i]).forEach((P) => {
81
81
  P.__vrv_devtools = E;
82
82
  });
83
83
  }
84
84
  return (
85
85
  // pass the vnode to the slot as a prop.
86
86
  // h and <component :is="..."> both accept vnodes
87
- ge(a.default, { Component: g, route: h }) || g
87
+ we(a.default, { Component: g, route: h }) || g
88
88
  );
89
89
  };
90
90
  }
91
91
  });
92
- function ge(e, n) {
92
+ function we(e, n) {
93
93
  if (!e)
94
94
  return null;
95
95
  const a = e(n);
96
96
  return a.length === 1 ? a[0] : a;
97
97
  }
98
- const Xe = qe;
99
- function Ye() {
100
- const e = ae(), n = e.parent && e.parent.type.name, a = e.parent && e.parent.subTree && e.parent.subTree.type;
98
+ const Ye = Xe;
99
+ function Fe() {
100
+ const e = se(), n = e.parent && e.parent.type.name, a = e.parent && e.parent.subTree && e.parent.subTree.type;
101
101
  if (n && (n === "KeepAlive" || n.includes("Transition")) && typeof a == "object" && a.name === "RouterView") {
102
102
  const t = n === "KeepAlive" ? "keep-alive" : "transition";
103
- ze(`<router-view> can no longer be used directly inside <transition> or <keep-alive>.
103
+ Je(`<router-view> can no longer be used directly inside <transition> or <keep-alive>.
104
104
  Use slot props instead:
105
105
 
106
106
  <router-view v-slot="{ Component }">
@@ -110,7 +110,7 @@ Use slot props instead:
110
110
  </router-view>`);
111
111
  }
112
112
  }
113
- function Fe(e = {}) {
113
+ function Qe(e = {}) {
114
114
  return {
115
115
  initialTabs: e.initialTabs ?? [],
116
116
  keepAlive: e.keepAlive ?? !0,
@@ -126,7 +126,7 @@ function N(e, n) {
126
126
  throw new Error(`[RouterTabs] Unable to resolve route: ${String(n)}`);
127
127
  return a;
128
128
  }
129
- const Qe = {
129
+ const We = {
130
130
  path: (e) => e.path,
131
131
  fullpath: (e) => e.fullPath,
132
132
  fullname: (e) => e.fullPath,
@@ -139,32 +139,32 @@ function $(e) {
139
139
  const a = n(e);
140
140
  if (typeof a == "string" && a.length) return a;
141
141
  } else if (typeof n == "string" && n.length) {
142
- const a = Qe[n.toLowerCase()];
142
+ const a = We[n.toLowerCase()];
143
143
  return a ? a(e) : n;
144
144
  }
145
145
  return e.fullPath;
146
146
  }
147
- function te(e, n) {
147
+ function ne(e, n) {
148
148
  const a = e.meta?.keepAlive;
149
149
  return typeof a == "boolean" ? a : n;
150
150
  }
151
- function ne(e, n) {
151
+ function oe(e, n) {
152
152
  const a = e.meta?.reuse;
153
153
  return typeof a == "boolean" ? a : n;
154
154
  }
155
- function Ae(e) {
155
+ function Se(e) {
156
156
  const n = e.meta ?? {}, a = {};
157
157
  return "title" in n && (a.title = n.title), "tips" in n && (a.tips = n.tips), "icon" in n && (a.icon = n.icon), "closable" in n && (a.closable = n.closable), "tabClass" in n && (a.tabClass = n.tabClass), "target" in n && (a.target = n.target), "href" in n && (a.href = n.href), a;
158
158
  }
159
159
  function G(e, n, a) {
160
- const t = Ae(e);
160
+ const t = Se(e);
161
161
  return {
162
162
  id: $(e),
163
163
  to: e.fullPath,
164
164
  fullPath: e.fullPath,
165
165
  matched: e,
166
- alive: te(e, a),
167
- reusable: ne(e, !1),
166
+ alive: ne(e, a),
167
+ reusable: oe(e, !1),
168
168
  closable: t.closable ?? !0,
169
169
  ...t,
170
170
  ...n
@@ -182,17 +182,17 @@ function Z(e, n, a, t) {
182
182
  e.push(n);
183
183
  }
184
184
  }
185
- function we(e, n, a) {
185
+ function Te(e, n, a) {
186
186
  if (!n || n <= 0) return;
187
- const t = e.filter((r) => r.alive);
187
+ const t = e.filter((i) => i.alive);
188
188
  for (; t.length > n; ) {
189
- const r = t.shift();
190
- if (!r || r.id === a) continue;
191
- const u = e.findIndex((d) => d.id === r.id);
189
+ const i = t.shift();
190
+ if (!i || i.id === a) continue;
191
+ const u = e.findIndex((d) => d.id === i.id);
192
192
  u > -1 && (e[u].alive = !1);
193
193
  }
194
194
  }
195
- function We(e) {
195
+ function Ze(e) {
196
196
  return {
197
197
  to: e.to,
198
198
  title: e.title,
@@ -202,91 +202,91 @@ function We(e) {
202
202
  closable: e.closable
203
203
  };
204
204
  }
205
- function Ze(e) {
205
+ function et(e) {
206
206
  const n = {};
207
207
  return "title" in e && (n.title = e.title), "tips" in e && (n.tips = e.tips), "icon" in e && (n.icon = e.icon), "tabClass" in e && (n.tabClass = e.tabClass), "closable" in e && (n.closable = e.closable), n;
208
208
  }
209
- function et(e, n = {}) {
210
- const a = Fe(n), t = Ce([]), r = J(null), u = Ie(), d = J(null), f = S(() => t.filter((i) => i.alive).map((i) => i.id));
209
+ function tt(e, n = {}) {
210
+ const a = Qe(n), t = _e([]), i = J(null), u = Ke(), d = J(null), f = S(() => t.filter((s) => s.alive).map((s) => s.id));
211
211
  let p = !1;
212
- function h(i) {
213
- const s = typeof i.matched == "object" ? i : N(e, i);
212
+ function h(s) {
213
+ const r = typeof s.matched == "object" ? s : N(e, s);
214
214
  return {
215
- key: $(s),
216
- fullPath: s.fullPath,
217
- alive: te(s, a.keepAlive),
218
- reusable: ne(s, !1),
219
- matched: s
215
+ key: $(r),
216
+ fullPath: r.fullPath,
217
+ alive: ne(r, a.keepAlive),
218
+ reusable: oe(r, !1),
219
+ matched: r
220
220
  };
221
221
  }
222
- function b(i) {
223
- const s = $(i);
224
- let l = t.find((w) => w.id === s);
225
- return l ? (l.fullPath = i.fullPath, l.to = i.fullPath, l.matched = i, l.alive = te(i, a.keepAlive), l.reusable = ne(i, l.reusable), Object.assign(l, Ae(i)), l) : (l = G(i, {}, a.keepAlive), Z(t, l, a.appendPosition, r.value), we(t, a.maxAlive, r.value), l);
222
+ function b(s) {
223
+ const r = $(s);
224
+ let l = t.find((w) => w.id === r);
225
+ return l ? (l.fullPath = s.fullPath, l.to = s.fullPath, l.matched = s, l.alive = ne(s, a.keepAlive), l.reusable = oe(s, l.reusable), Object.assign(l, Se(s)), l) : (l = G(s, {}, a.keepAlive), Z(t, l, a.appendPosition, i.value), Te(t, a.maxAlive, i.value), l);
226
226
  }
227
- async function m(i, s = !1, l = !0) {
228
- const w = N(e, i), O = $(w), V = r.value === O;
229
- l === "sameTab" && (l = V), l && await _(O, !0), await e[s ? "replace" : "push"](w), V && await L();
227
+ async function m(s, r = !1, l = !0) {
228
+ const w = N(e, s), O = $(w), V = i.value === O;
229
+ l === "sameTab" && (l = V), l && await _(O, !0), await e[r ? "replace" : "push"](w), V && await L();
230
230
  }
231
- function k(i) {
232
- const s = t.findIndex((w) => w.id === i), l = t[s] || t[s - 1] || t[0];
231
+ function k(s) {
232
+ const r = t.findIndex((w) => w.id === s), l = t[r] || t[r - 1] || t[0];
233
233
  return l ? l.to : a.defaultRoute;
234
234
  }
235
- async function y(i = r.value, s = {}) {
236
- if (i) {
237
- if (!s.force && a.keepLastTab && t.length === 1)
235
+ async function y(s = i.value, r = {}) {
236
+ if (s) {
237
+ if (!r.force && a.keepLastTab && t.length === 1)
238
238
  throw new Error("[RouterTabs] Unable to close the final tab when keepLastTab is true.");
239
- if (await C(i, { force: s.force }), s.redirect !== null)
240
- if (r.value === i) {
241
- const l = s.redirect ?? k(i);
239
+ if (await C(s, { force: r.force }), r.redirect !== null)
240
+ if (i.value === s) {
241
+ const l = r.redirect ?? k(s);
242
242
  l && await e.replace(l);
243
- } else s.redirect && await e.replace(s.redirect);
243
+ } else r.redirect && await e.replace(r.redirect);
244
244
  }
245
245
  }
246
- async function C(i, s = {}) {
247
- const l = t.findIndex((w) => w.id === i);
248
- l !== -1 && (t.splice(l, 1), d.value === i && (d.value = null), r.value === i && (r.value = null, u.value = void 0));
246
+ async function C(s, r = {}) {
247
+ const l = t.findIndex((w) => w.id === s);
248
+ l !== -1 && (t.splice(l, 1), d.value === s && (d.value = null), i.value === s && (i.value = null, u.value = void 0));
249
249
  }
250
- async function _(i = r.value ?? void 0, s = !1) {
251
- i && (d.value = i, await se(), s || await se(), d.value = null);
250
+ async function _(s = i.value ?? void 0, r = !1) {
251
+ s && (d.value = s, await re(), r || await re(), d.value = null);
252
252
  }
253
- async function g(i = !1) {
254
- for (const s of t)
255
- await _(s.id, i);
253
+ async function g(s = !1) {
254
+ for (const r of t)
255
+ await _(r.id, s);
256
256
  }
257
- async function E(i = a.defaultRoute) {
258
- t.splice(0, t.length), r.value = null, u.value = void 0;
259
- for (const s of a.initialTabs) {
260
- const l = N(e, s.to), w = G(l, s, a.keepAlive);
257
+ async function E(s = a.defaultRoute) {
258
+ t.splice(0, t.length), i.value = null, u.value = void 0;
259
+ for (const r of a.initialTabs) {
260
+ const l = N(e, r.to), w = G(l, r, a.keepAlive);
261
261
  t.push(w);
262
262
  }
263
- await e.replace(i);
263
+ await e.replace(s);
264
264
  }
265
265
  async function L() {
266
- const i = r.value;
267
- i && await _(i, !0);
266
+ const s = i.value;
267
+ s && await _(s, !0);
268
268
  }
269
- function P(i) {
270
- return typeof i.matched == "object" ? $(i) : $(N(e, i));
269
+ function P(s) {
270
+ return typeof s.matched == "object" ? $(s) : $(N(e, s));
271
271
  }
272
272
  function q() {
273
- const i = t.find((s) => s.id === r.value);
273
+ const s = t.find((r) => r.id === i.value);
274
274
  return {
275
- tabs: t.map(We),
276
- active: i ? i.to : null
275
+ tabs: t.map(Ze),
276
+ active: s ? s.to : null
277
277
  };
278
278
  }
279
- async function X(i) {
280
- p = !0, t.splice(0, t.length), r.value = null, u.value = void 0;
281
- const s = i?.tabs ?? [];
282
- for (const w of s)
279
+ async function X(s) {
280
+ p = !0, t.splice(0, t.length), i.value = null, u.value = void 0;
281
+ const r = s?.tabs ?? [];
282
+ for (const w of r)
283
283
  try {
284
- const O = N(e, w.to), V = Ze(w), D = G(O, V, a.keepAlive);
284
+ const O = N(e, w.to), V = et(w), D = G(O, V, a.keepAlive);
285
285
  Z(t, D, "last", null);
286
286
  } catch {
287
287
  }
288
288
  p = !1;
289
- const l = i?.active ?? s[s.length - 1]?.to ?? a.defaultRoute;
289
+ const l = s?.active ?? r[r.length - 1]?.to ?? a.defaultRoute;
290
290
  if (l)
291
291
  try {
292
292
  await e.replace(l);
@@ -295,19 +295,19 @@ function et(e, n = {}) {
295
295
  }
296
296
  return x(
297
297
  () => e.currentRoute.value,
298
- (i) => {
298
+ (s) => {
299
299
  if (p) return;
300
- const s = b(i);
301
- r.value = s.id, u.value = s, we(t, a.maxAlive, r.value);
300
+ const r = b(s);
301
+ i.value = r.id, u.value = r, Te(t, a.maxAlive, i.value);
302
302
  },
303
303
  { immediate: !0 }
304
- ), a.initialTabs.length && a.initialTabs.forEach((i) => {
305
- const s = N(e, i.to), l = G(s, i, a.keepAlive);
304
+ ), a.initialTabs.length && a.initialTabs.forEach((s) => {
305
+ const r = N(e, s.to), l = G(r, s, a.keepAlive);
306
306
  Z(t, l, "last", null);
307
307
  }), {
308
308
  options: a,
309
309
  tabs: t,
310
- activeId: r,
310
+ activeId: i,
311
311
  current: u,
312
312
  includeKeys: f,
313
313
  refreshingKey: d,
@@ -324,12 +324,12 @@ function et(e, n = {}) {
324
324
  hydrate: X
325
325
  };
326
326
  }
327
- function Te(e) {
327
+ function ke(e) {
328
328
  return e ? typeof e == "string" ? { name: e } : e : {};
329
329
  }
330
- const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStorage" in window, tt = oe({
330
+ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStorage" in window, nt = ae({
331
331
  name: "RouterTab",
332
- components: { RouterView: Xe },
332
+ components: { RouterView: Ye },
333
333
  props: {
334
334
  tabs: {
335
335
  type: Array,
@@ -373,13 +373,13 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
373
373
  }
374
374
  },
375
375
  setup(e) {
376
- const n = ae();
376
+ const n = se();
377
377
  if (!n)
378
378
  throw new Error("[RouterTab] component must be used within a Vue application context.");
379
379
  const a = n.appContext.app.config.globalProperties.$router;
380
380
  if (!a)
381
381
  throw new Error("[RouterTab] Vue Router is required. Make sure to call app.use(router) before RouterTab.");
382
- const t = et(a, {
382
+ const t = tt(a, {
383
383
  initialTabs: e.tabs,
384
384
  keepAlive: e.keepAlive,
385
385
  maxAlive: e.maxAlive,
@@ -388,7 +388,7 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
388
388
  defaultRoute: e.defaultPage
389
389
  });
390
390
  U(H, t), n.appContext.config.globalProperties.$tabs = t;
391
- const r = S(() => Te(e.tabTransition)), u = S(() => Te(e.pageTransition)), d = Ce({
391
+ const i = S(() => ke(e.tabTransition)), u = S(() => ke(e.pageTransition)), d = _e({
392
392
  visible: !1,
393
393
  target: null,
394
394
  position: { x: 0, y: 0 }
@@ -442,7 +442,7 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
442
442
  handler: async ({ target: o }) => {
443
443
  await t.closeTab(o.id);
444
444
  },
445
- enable: ({ target: o }) => i(o)
445
+ enable: ({ target: o }) => s(o)
446
446
  },
447
447
  closeLefts: {
448
448
  label: "Close to the Left",
@@ -473,18 +473,18 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
473
473
  e.contextmenu && (d.visible = !0, d.target = o, d.position.x = c.clientX, d.position.y = c.clientY, document.addEventListener("click", g, { once: !0 }));
474
474
  }
475
475
  function L(o, c) {
476
- const v = typeof o == "string" ? { id: o } : o, R = _[v.id], Pe = v.label ?? R?.label ?? String(v.id), Y = v.visible ?? R?.visible ?? !0;
476
+ const v = typeof o == "string" ? { id: o } : o, R = _[v.id], xe = v.label ?? R?.label ?? String(v.id), Y = v.visible ?? R?.visible ?? !0;
477
477
  if (!(typeof Y == "function" ? Y(c) : Y !== !1)) return null;
478
- const F = v.enable ?? R?.enable ?? !0, xe = typeof F == "function" ? F(c) : F !== !1, ie = v.handler ?? R?.handler;
478
+ const F = v.enable ?? R?.enable ?? !0, Ee = typeof F == "function" ? F(c) : F !== !1, ie = v.handler ?? R?.handler;
479
479
  if (!ie) return null;
480
- const Ee = async () => {
480
+ const Oe = async () => {
481
481
  await Promise.resolve(ie(c));
482
482
  };
483
483
  return {
484
484
  id: String(v.id),
485
- label: Pe,
486
- disabled: !xe,
487
- action: Ee
485
+ label: xe,
486
+ disabled: !Ee,
487
+ action: Oe
488
488
  };
489
489
  }
490
490
  const P = S(() => {
@@ -498,10 +498,10 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
498
498
  function X(o) {
499
499
  return typeof o.title == "string" ? o.title : Array.isArray(o.title) && o.title.length ? String(o.title[0]) : o.fullPath;
500
500
  }
501
- function i(o) {
501
+ function s(o) {
502
502
  return !(o.closable === !1 || t.options.keepLastTab && t.tabs.length <= 1);
503
503
  }
504
- async function s(o) {
504
+ async function r(o) {
505
505
  await t.closeTab(o.id);
506
506
  }
507
507
  function l(o) {
@@ -512,7 +512,7 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
512
512
  "router-tab__item",
513
513
  {
514
514
  "is-active": t.activeId.value === o.id,
515
- "is-closable": i(o)
515
+ "is-closable": s(o)
516
516
  },
517
517
  o.tabClass
518
518
  ];
@@ -543,9 +543,9 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
543
543
  } catch {
544
544
  }
545
545
  }
546
- _e(() => {
546
+ Ae(() => {
547
547
  document.addEventListener("keydown", g), V();
548
- }), Ke(() => {
548
+ }), Ne(() => {
549
549
  document.removeEventListener("keydown", g), n.appContext.config.globalProperties.$tabs = null, D();
550
550
  }), x(
551
551
  () => e.keepAlive,
@@ -583,48 +583,48 @@ const H = Symbol("RouterTabsContext"), ee = typeof window < "u" && "sessionStora
583
583
  },
584
584
  { deep: !0 }
585
585
  );
586
- const Se = t.includeKeys;
586
+ const Pe = t.includeKeys;
587
587
  return {
588
588
  controller: t,
589
589
  tabs: t.tabs,
590
- includeKeys: Se,
591
- tabTransitionProps: r,
590
+ includeKeys: Pe,
591
+ tabTransitionProps: i,
592
592
  pageTransitionProps: u,
593
593
  buildTabClass: w,
594
594
  activate: l,
595
- close: s,
595
+ close: r,
596
596
  context: d,
597
597
  menuItems: P,
598
598
  handleMenuAction: q,
599
599
  showContextMenu: E,
600
600
  hideContextMenu: g,
601
601
  tabTitle: X,
602
- isClosable: i,
602
+ isClosable: s,
603
603
  isRefreshing: O
604
604
  };
605
605
  }
606
- }), nt = (e, n) => {
606
+ }), ot = (e, n) => {
607
607
  const a = e.__vccOpts || e;
608
- for (const [t, r] of n)
609
- a[t] = r;
608
+ for (const [t, i] of n)
609
+ a[t] = i;
610
610
  return a;
611
- }, ot = { class: "router-tab" }, at = { class: "router-tab__header" }, it = { class: "router-tab__slot-start" }, st = { class: "router-tab__scroll" }, rt = ["onClick", "onAuxclick", "onContextmenu"], lt = ["title"], ct = ["onClick"], ut = { class: "router-tab__slot-end" }, ft = { class: "router-tab__container" }, dt = ["aria-disabled", "onClick"];
612
- function pt(e, n, a, t, r, u) {
613
- const d = Ne("RouterView");
614
- return T(), A("div", ot, [
615
- I("header", at, [
611
+ }, at = { class: "router-tab" }, st = { class: "router-tab__header" }, it = { class: "router-tab__slot-start" }, rt = { class: "router-tab__scroll" }, lt = ["onClick", "onAuxclick", "onContextmenu"], ct = ["title"], ut = ["onClick"], ft = { class: "router-tab__slot-end" }, dt = { class: "router-tab__container" }, pt = ["aria-disabled", "onClick"];
612
+ function bt(e, n, a, t, i, u) {
613
+ const d = $e("RouterView");
614
+ return T(), A("div", at, [
615
+ I("header", st, [
616
616
  I("div", it, [
617
- re(e.$slots, "start")
617
+ le(e.$slots, "start")
618
618
  ]),
619
- I("div", st, [
620
- j($e, Q({
619
+ I("div", rt, [
620
+ j(Le, Q({
621
621
  tag: "ul",
622
622
  class: "router-tab__nav"
623
623
  }, e.tabTransitionProps), {
624
624
  default: M(() => [
625
- (T(!0), A(le, null, ce(e.tabs, (f) => (T(), A("li", {
625
+ (T(!0), A(ce, null, ue(e.tabs, (f) => (T(), A("li", {
626
626
  key: f.id,
627
- class: ue(e.buildTabClass(f)),
627
+ class: fe(e.buildTabClass(f)),
628
628
  onClick: (p) => e.activate(f),
629
629
  onAuxclick: B((p) => e.close(f), ["middle", "prevent"]),
630
630
  onContextmenu: B((p) => e.showContextMenu(f, p), ["prevent"])
@@ -635,35 +635,35 @@ function pt(e, n, a, t, r, u) {
635
635
  }, [
636
636
  f.icon ? (T(), A("i", {
637
637
  key: 0,
638
- class: ue(["router-tab__item-icon", f.icon])
638
+ class: fe(["router-tab__item-icon", f.icon])
639
639
  }, null, 2)) : K("", !0),
640
- Le(" " + fe(e.tabTitle(f)), 1)
641
- ], 8, lt),
640
+ De(" " + de(e.tabTitle(f)), 1)
641
+ ], 8, ct),
642
642
  e.isClosable(f) ? (T(), A("a", {
643
643
  key: 0,
644
644
  class: "router-tab__item-close",
645
645
  onClick: B((p) => e.close(f), ["stop"])
646
- }, null, 8, ct)) : K("", !0)
647
- ], 42, rt))), 128))
646
+ }, null, 8, ut)) : K("", !0)
647
+ ], 42, lt))), 128))
648
648
  ]),
649
649
  _: 1
650
650
  }, 16)
651
651
  ]),
652
- I("div", ut, [
653
- re(e.$slots, "end")
652
+ I("div", ft, [
653
+ le(e.$slots, "end")
654
654
  ])
655
655
  ]),
656
- I("div", ft, [
656
+ I("div", dt, [
657
657
  j(d, null, {
658
658
  default: M(({ Component: f, route: p }) => [
659
- j(de, Q(e.pageTransitionProps, { appear: "" }), {
659
+ j(pe, Q(e.pageTransitionProps, { appear: "" }), {
660
660
  default: M(() => [
661
- e.controller.options.keepAlive ? (T(), W(De, {
661
+ e.controller.options.keepAlive ? (T(), W(je, {
662
662
  key: 0,
663
663
  include: e.includeKeys,
664
664
  max: e.controller.options.maxAlive || void 0
665
665
  }, [
666
- e.isRefreshing(p) ? K("", !0) : (T(), W(pe(f), {
666
+ e.isRefreshing(p) ? K("", !0) : (T(), W(be(f), {
667
667
  key: e.controller.getRouteKey(p),
668
668
  class: "router-tab-page"
669
669
  }))
@@ -671,9 +671,9 @@ function pt(e, n, a, t, r, u) {
671
671
  ]),
672
672
  _: 2
673
673
  }, 1040),
674
- j(de, Q(e.pageTransitionProps, { appear: "" }), {
674
+ j(pe, Q(e.pageTransitionProps, { appear: "" }), {
675
675
  default: M(() => [
676
- !e.controller.options.keepAlive || e.isRefreshing(p) ? (T(), W(pe(f), {
676
+ !e.controller.options.keepAlive || e.isRefreshing(p) ? (T(), W(be(f), {
677
677
  key: e.controller.getRouteKey(p) + (e.isRefreshing(p) ? "-refresh" : ""),
678
678
  class: "router-tab-page"
679
679
  })) : K("", !0)
@@ -687,36 +687,36 @@ function pt(e, n, a, t, r, u) {
687
687
  e.context.visible && e.context.target ? (T(), A("div", {
688
688
  key: 0,
689
689
  class: "router-tab__contextmenu",
690
- style: je({ left: e.context.position.x + "px", top: e.context.position.y + "px" })
690
+ style: Me({ left: e.context.position.x + "px", top: e.context.position.y + "px" })
691
691
  }, [
692
- (T(!0), A(le, null, ce(e.menuItems, (f) => (T(), A("a", {
692
+ (T(!0), A(ce, null, ue(e.menuItems, (f) => (T(), A("a", {
693
693
  key: f.id,
694
694
  class: "router-tab__contextmenu-item",
695
695
  "aria-disabled": f.disabled,
696
696
  onClick: B((p) => e.handleMenuAction(f), ["prevent"])
697
- }, fe(f.label), 9, dt))), 128))
697
+ }, de(f.label), 9, pt))), 128))
698
698
  ], 4)) : K("", !0)
699
699
  ]);
700
700
  }
701
- const ke = /* @__PURE__ */ nt(tt, [["render", pt]]);
702
- function bt(e = {}) {
701
+ const Re = /* @__PURE__ */ ot(nt, [["render", bt]]);
702
+ function vt(e = {}) {
703
703
  const { optional: n = !1 } = e, a = z(H, null);
704
704
  if (a) return a;
705
705
  const t = z("$tabs", null);
706
706
  if (t) return t;
707
- const u = ae()?.appContext.config.globalProperties.$tabs;
707
+ const u = se()?.appContext.config.globalProperties.$tabs;
708
708
  if (u) return u;
709
709
  if (!n)
710
710
  throw new Error("[RouterTabs] useRouterTabs must be used within <router-tab>.");
711
711
  return null;
712
712
  }
713
- const vt = "router-tabs:persistent";
714
- function ht(e) {
713
+ const ht = "router-tabs:persistent";
714
+ function mt(e) {
715
715
  return typeof window > "u" ? null : e === void 0 ? window.localStorage ?? null : e;
716
716
  }
717
- function mt(e) {
718
- const n = ht(e.storage), a = e.storageKey ?? vt;
719
- return Me(e.storeId ?? "routerTabs", {
717
+ function yt(e) {
718
+ const n = mt(e.storage), a = e.storageKey ?? ht;
719
+ return Be(e.storeId ?? "routerTabs", {
720
720
  state: () => ({
721
721
  snapshot: null
722
722
  }),
@@ -742,17 +742,29 @@ function mt(e) {
742
742
  }
743
743
  });
744
744
  }
745
- function yt(e = {}) {
746
- const n = bt(), t = (e.store ?? mt(e))(), r = J(!1);
747
- return _e(async () => {
745
+ function gt(e = {}) {
746
+ const n = vt({ optional: !0 });
747
+ if (!n)
748
+ throw new Error("[RouterTabs] Pinia helper must be used inside <router-tab>.");
749
+ const t = (e.store ?? yt(e))(), i = J(!1);
750
+ return Ae(async () => {
748
751
  t.load();
749
752
  const u = t.snapshot;
750
- if (u)
753
+ if (u && u.tabs?.length)
751
754
  try {
752
- r.value = !0, await n.hydrate(u);
755
+ i.value = !0, await n.hydrate(u);
753
756
  } finally {
754
- r.value = !1, t.setSnapshot(n.snapshot());
757
+ i.value = !1;
755
758
  }
759
+ else
760
+ try {
761
+ i.value = !0;
762
+ const d = e.fallbackRoute ?? n.options.defaultRoute;
763
+ await n.reset(d);
764
+ } finally {
765
+ i.value = !1;
766
+ }
767
+ t.setSnapshot(n.snapshot());
756
768
  }), x(
757
769
  () => ({
758
770
  tabs: n.tabs.map((u) => ({
@@ -766,44 +778,50 @@ function yt(e = {}) {
766
778
  active: n.activeId.value
767
779
  }),
768
780
  () => {
769
- r.value || t.setSnapshot(n.snapshot());
781
+ i.value || t.setSnapshot(n.snapshot());
770
782
  },
771
783
  { deep: !0 }
772
784
  ), t;
773
785
  }
774
- const gt = {
775
- class: "router-tabs-pinia",
786
+ const wt = {
787
+ class: "router-tabs",
776
788
  "aria-hidden": "true"
777
- }, Rt = /* @__PURE__ */ oe({
789
+ }, te = /* @__PURE__ */ ae({
790
+ name: "RouterTabs",
778
791
  __name: "RouterTabsPinia",
779
792
  props: {
780
793
  storeId: {},
781
794
  storageKey: {},
782
795
  storage: {},
796
+ fallbackRoute: {},
783
797
  store: { type: [Function, Object] }
784
798
  },
785
799
  setup(e) {
786
- return yt(e), (a, t) => (T(), A("span", gt));
800
+ return gt(e), (a, t) => (T(), A("span", wt));
787
801
  }
788
- }), Re = {
802
+ }), Ce = {
789
803
  install(e) {
790
- Re._installed || (Re._installed = !0, e.component(ke.name, ke), Object.defineProperty(e.config.globalProperties, "$tabs", {
804
+ if (Ce._installed) return;
805
+ Ce._installed = !0;
806
+ const n = Re.name || "RouterTab", a = te.name || "RouterTabs";
807
+ e.component(n, Re), e.component(a, te), a !== "router-tabs" && e.component("router-tabs", te), Object.defineProperty(e.config.globalProperties, "$tabs", {
791
808
  configurable: !0,
792
809
  enumerable: !1,
793
810
  get() {
794
811
  return e._context.provides[H];
795
812
  },
796
- set(n) {
797
- n && e.provide(H, n);
813
+ set(t) {
814
+ t && e.provide(H, t);
798
815
  }
799
- }));
816
+ });
800
817
  }
801
818
  };
802
819
  export {
803
- ke as RouterTab,
804
- Rt as RouterTabsPinia,
805
- Re as default,
820
+ Re as RouterTab,
821
+ te as RouterTabs,
822
+ te as RouterTabsPinia,
823
+ Ce as default,
806
824
  H as routerTabsKey,
807
- bt as useRouterTabs,
808
- yt as useRouterTabsPiniaPersistence
825
+ vt as useRouterTabs,
826
+ gt as useRouterTabsPiniaPersistence
809
827
  };
@@ -0,0 +1,12 @@
1
+ (function(v,t){typeof exports=="object"&&typeof module<"u"?t(exports,require("vue"),require("pinia")):typeof define=="function"&&define.amd?define(["exports","vue","pinia"],t):(v=typeof globalThis<"u"?globalThis:v||self,t(v["vue3-router-tab"]={},v.Vue,v.pinia))})(this,(function(v,t,re){"use strict";/*!
2
+ * vue-router v4.5.1
3
+ * (c) 2025 Eduardo San Martin Morote
4
+ * @license MIT
5
+ */const se=typeof document<"u",le=Object.assign,ce=Array.isArray;function ue(e){const o=Array.from(arguments).slice(1);console.warn.apply(console,["[Vue Router warn]: "+e].concat(o))}function fe(e,o){return(e.aliasOf||e)===(o.aliasOf||o)}var F;(function(e){e.pop="pop",e.push="push"})(F||(F={}));var X;(function(e){e.back="back",e.forward="forward",e.unknown=""})(X||(X={})),Symbol(process.env.NODE_ENV!=="production"?"navigation failure":"");var Y;(function(e){e[e.aborted=4]="aborted",e[e.cancelled=8]="cancelled",e[e.duplicated=16]="duplicated"})(Y||(Y={}));const de=Symbol(process.env.NODE_ENV!=="production"?"router view location matched":""),Q=Symbol(process.env.NODE_ENV!=="production"?"router view depth":"");Symbol(process.env.NODE_ENV!=="production"?"router":""),Symbol(process.env.NODE_ENV!=="production"?"route location":"");const W=Symbol(process.env.NODE_ENV!=="production"?"router view location":""),pe=t.defineComponent({name:"RouterView",inheritAttrs:!1,props:{name:{type:String,default:"default"},route:Object},compatConfig:{MODE:3},setup(e,{attrs:o,slots:i}){process.env.NODE_ENV!=="production"&&me();const n=t.inject(W),s=t.computed(()=>e.route||n.value),f=t.inject(Q,0),p=t.computed(()=>{let y=t.unref(f);const{matched:m}=s.value;let g;for(;(g=m[y])&&!g.components;)y++;return y}),d=t.computed(()=>s.value.matched[p.value]);t.provide(Q,t.computed(()=>p.value+1)),t.provide(de,d),t.provide(W,s);const b=t.ref();return t.watch(()=>[b.value,d.value,e.name],([y,m,g],[R,w,S])=>{m&&(m.instances[g]=y,w&&w!==m&&y&&y===R&&(m.leaveGuards.size||(m.leaveGuards=w.leaveGuards),m.updateGuards.size||(m.updateGuards=w.updateGuards))),y&&m&&(!w||!fe(m,w)||!R)&&(m.enterCallbacks[g]||[]).forEach(C=>C(y))},{flush:"post"}),()=>{const y=s.value,m=e.name,g=d.value,R=g&&g.components[m];if(!R)return Z(i.default,{Component:R,route:y});const w=g.props[m],S=w?w===!0?y.params:typeof w=="function"?w(y):w:null,C=E=>{E.component.isUnmounted&&(g.instances[m]=null)},T=t.h(R,le({},S,o,{onVnodeUnmounted:C,ref:b}));if(process.env.NODE_ENV!=="production"&&se&&T.ref){const E={depth:p.value,name:g.name,path:g.path,meta:g.meta};(ce(T.ref)?T.ref.map(A=>A.i):[T.ref.i]).forEach(A=>{A.__vrv_devtools=E})}return Z(i.default,{Component:T,route:y})||T}}});function Z(e,o){if(!e)return null;const i=e(o);return i.length===1?i[0]:i}const be=pe;function me(){const e=t.getCurrentInstance(),o=e.parent&&e.parent.type.name,i=e.parent&&e.parent.subTree&&e.parent.subTree.type;if(o&&(o==="KeepAlive"||o.includes("Transition"))&&typeof i=="object"&&i.name==="RouterView"){const n=o==="KeepAlive"?"keep-alive":"transition";ue(`<router-view> can no longer be used directly inside <transition> or <keep-alive>.
6
+ Use slot props instead:
7
+
8
+ <router-view v-slot="{ Component }">
9
+ <${n}>
10
+ <component :is="Component" />
11
+ </${n}>
12
+ </router-view>`)}}function he(e={}){return{initialTabs:e.initialTabs??[],keepAlive:e.keepAlive??!0,maxAlive:e.maxAlive??0,keepLastTab:e.keepLastTab??!0,appendPosition:e.appendPosition??"last",defaultRoute:e.defaultRoute??"/"}}function V(e,o){const i=e.resolve(o);if(!i||!i.matched.length)throw new Error(`[RouterTabs] Unable to resolve route: ${String(o)}`);return i}const ye={path:e=>e.path,fullpath:e=>e.fullPath,fullname:e=>e.fullPath,full:e=>e.fullPath,name:e=>e.name?String(e.name):e.fullPath};function N(e){const o=e.meta?.key;if(typeof o=="function"){const i=o(e);if(typeof i=="string"&&i.length)return i}else if(typeof o=="string"&&o.length){const i=ye[o.toLowerCase()];return i?i(e):o}return e.fullPath}function j(e,o){const i=e.meta?.keepAlive;return typeof i=="boolean"?i:o}function M(e,o){const i=e.meta?.reuse;return typeof i=="boolean"?i:o}function ee(e){const o=e.meta??{},i={};return"title"in o&&(i.title=o.title),"tips"in o&&(i.tips=o.tips),"icon"in o&&(i.icon=o.icon),"closable"in o&&(i.closable=o.closable),"tabClass"in o&&(i.tabClass=o.tabClass),"target"in o&&(i.target=o.target),"href"in o&&(i.href=o.href),i}function $(e,o,i){const n=ee(e);return{id:N(e),to:e.fullPath,fullPath:e.fullPath,matched:e,alive:j(e,i),reusable:M(e,!1),closable:n.closable??!0,...n,...o}}function L(e,o,i,n){if(!e.find(f=>f.id===o.id)){if(i==="next"&&n){const f=e.findIndex(p=>p.id===n);if(f>-1){e.splice(f+1,0,o);return}}e.push(o)}}function te(e,o,i){if(!o||o<=0)return;const n=e.filter(s=>s.alive);for(;n.length>o;){const s=n.shift();if(!s||s.id===i)continue;const f=e.findIndex(p=>p.id===s.id);f>-1&&(e[f].alive=!1)}}function ge(e){return{to:e.to,title:e.title,tips:e.tips,icon:e.icon,tabClass:e.tabClass,closable:e.closable}}function we(e){const o={};return"title"in e&&(o.title=e.title),"tips"in e&&(o.tips=e.tips),"icon"in e&&(o.icon=e.icon),"tabClass"in e&&(o.tabClass=e.tabClass),"closable"in e&&(o.closable=e.closable),o}function Te(e,o={}){const i=he(o),n=t.reactive([]),s=t.ref(null),f=t.shallowRef(),p=t.ref(null),d=t.computed(()=>n.filter(r=>r.alive).map(r=>r.id));let b=!1;function y(r){const l=typeof r.matched=="object"?r:V(e,r);return{key:N(l),fullPath:l.fullPath,alive:j(l,i.keepAlive),reusable:M(l,!1),matched:l}}function m(r){const l=N(r);let c=n.find(k=>k.id===l);return c?(c.fullPath=r.fullPath,c.to=r.fullPath,c.matched=r,c.alive=j(r,i.keepAlive),c.reusable=M(r,c.reusable),Object.assign(c,ee(r)),c):(c=$(r,{},i.keepAlive),L(n,c,i.appendPosition,s.value),te(n,i.maxAlive,s.value),c)}async function g(r,l=!1,c=!0){const k=V(e,r),P=N(k),x=s.value===P;c==="sameTab"&&(c=x),c&&await C(P,!0),await e[l?"replace":"push"](k),x&&await O()}function R(r){const l=n.findIndex(k=>k.id===r),c=n[l]||n[l-1]||n[0];return c?c.to:i.defaultRoute}async function w(r=s.value,l={}){if(r){if(!l.force&&i.keepLastTab&&n.length===1)throw new Error("[RouterTabs] Unable to close the final tab when keepLastTab is true.");if(await S(r,{force:l.force}),l.redirect!==null)if(s.value===r){const c=l.redirect??R(r);c&&await e.replace(c)}else l.redirect&&await e.replace(l.redirect)}}async function S(r,l={}){const c=n.findIndex(k=>k.id===r);c!==-1&&(n.splice(c,1),p.value===r&&(p.value=null),s.value===r&&(s.value=null,f.value=void 0))}async function C(r=s.value??void 0,l=!1){r&&(p.value=r,await t.nextTick(),l||await t.nextTick(),p.value=null)}async function T(r=!1){for(const l of n)await C(l.id,r)}async function E(r=i.defaultRoute){n.splice(0,n.length),s.value=null,f.value=void 0;for(const l of i.initialTabs){const c=V(e,l.to),k=$(c,l,i.keepAlive);n.push(k)}await e.replace(r)}async function O(){const r=s.value;r&&await C(r,!0)}function A(r){return typeof r.matched=="object"?N(r):N(V(e,r))}function U(){const r=n.find(l=>l.id===s.value);return{tabs:n.map(ge),active:r?r.to:null}}async function J(r){b=!0,n.splice(0,n.length),s.value=null,f.value=void 0;const l=r?.tabs??[];for(const k of l)try{const P=V(e,k.to),x=we(k),K=$(P,x,i.keepAlive);L(n,K,"last",null)}catch{}b=!1;const c=r?.active??l[l.length-1]?.to??i.defaultRoute;if(c)try{await e.replace(c)}catch{}}return t.watch(()=>e.currentRoute.value,r=>{if(b)return;const l=m(r);s.value=l.id,f.value=l,te(n,i.maxAlive,s.value)},{immediate:!0}),i.initialTabs.length&&i.initialTabs.forEach(r=>{const l=V(e,r.to),c=$(l,r,i.keepAlive);L(n,c,"last",null)}),{options:i,tabs:n,activeId:s,current:f,includeKeys:d,refreshingKey:p,openTab:g,closeTab:w,removeTab:S,refreshTab:C,refreshAll:T,reset:E,reload:O,getRouteKey:A,matchRoute:y,snapshot:U,hydrate:J}}function ne(e){return e?typeof e=="string"?{name:e}:e:{}}const B=Symbol("RouterTabsContext"),D=typeof window<"u"&&"sessionStorage"in window,ke=t.defineComponent({name:"RouterTab",components:{RouterView:be},props:{tabs:{type:Array,default:()=>[]},keepAlive:{type:Boolean,default:!0},maxAlive:{type:Number,default:0},keepLastTab:{type:Boolean,default:!0},append:{type:String,default:"last"},defaultPage:{type:[String,Object],default:"/"},tabTransition:{type:[String,Object],default:"router-tab-zoom"},pageTransition:{type:[String,Object],default:()=>({name:"router-tab-swap",mode:"out-in"})},contextmenu:{type:[Boolean,Array],default:!0},storage:{type:[Boolean,String],default:!1}},setup(e){const o=t.getCurrentInstance();if(!o)throw new Error("[RouterTab] component must be used within a Vue application context.");const i=o.appContext.app.config.globalProperties.$router;if(!i)throw new Error("[RouterTab] Vue Router is required. Make sure to call app.use(router) before RouterTab.");const n=Te(i,{initialTabs:e.tabs,keepAlive:e.keepAlive,maxAlive:e.maxAlive,keepLastTab:e.keepLastTab,appendPosition:e.append,defaultRoute:e.defaultPage});t.provide(B,n),o.appContext.config.globalProperties.$tabs=n;const s=t.computed(()=>ne(e.tabTransition)),f=t.computed(()=>ne(e.pageTransition)),p=t.reactive({visible:!1,target:null,position:{x:0,y:0}}),d=t.computed(()=>!e.storage||!D?null:typeof e.storage=="string"?e.storage:`router-tabs:${(i.options?.history?.base??"")||"default"}`);let b=!!d.value;const y=["refresh","refreshAll","close","closeLefts","closeRights","closeOthers"];function m(a){return n.tabs.findIndex(u=>u.id===a)}function g(a){const u=m(a.id);return u>0?n.tabs.slice(0,u):[]}function R(a){const u=m(a.id);return u>-1?n.tabs.slice(u+1):[]}function w(a){return n.tabs.filter(u=>u.id!==a.id)}async function S(a,u){const h=a.filter(_=>_.closable!==!1);if(h.length){for(const _ of h)n.activeId.value===_.id?await n.closeTab(_.id,{redirect:u.to,force:!0}):await n.removeTab(_.id,{force:!0});n.activeId.value!==u.id&&await n.openTab(u.to,!0,!1)}}const C={refresh:{label:"Refresh",handler:async({target:a})=>{await n.refreshTab(a.id,!0)}},refreshAll:{label:"Refresh All",handler:async()=>{await n.refreshAll(!0)}},close:{label:"Close",handler:async({target:a})=>{await n.closeTab(a.id)},enable:({target:a})=>r(a)},closeLefts:{label:"Close to the Left",handler:async({target:a})=>{await S(g(a),a)},enable:({target:a})=>g(a).some(u=>u.closable!==!1)},closeRights:{label:"Close to the Right",handler:async({target:a})=>{await S(R(a),a)},enable:({target:a})=>R(a).some(u=>u.closable!==!1)},closeOthers:{label:"Close Others",handler:async({target:a})=>{await S(w(a),a)},enable:({target:a})=>w(a).some(u=>u.closable!==!1)}};function T(){p.visible=!1,p.target=null}function E(a,u){e.contextmenu&&(p.visible=!0,p.target=a,p.position.x=u.clientX,p.position.y=u.clientY,document.addEventListener("click",T,{once:!0}))}function O(a,u){const h=typeof a=="string"?{id:a}:a,_=C[h.id],Me=h.label??_?.label??String(h.id),q=h.visible??_?.visible??!0;if(!(typeof q=="function"?q(u):q!==!1))return null;const H=h.enable??_?.enable??!0,Le=typeof H=="function"?H(u):H!==!1,ie=h.handler??_?.handler;if(!ie)return null;const De=async()=>{await Promise.resolve(ie(u))};return{id:String(h.id),label:Me,disabled:!Le,action:De}}const A=t.computed(()=>{if(!p.visible||!p.target||e.contextmenu===!1)return[];const a=Array.isArray(e.contextmenu)?e.contextmenu:y,u={target:p.target,controller:n};return a.map(h=>O(h,u)).filter(h=>!!h)});async function U(a){a.disabled||(T(),await a.action())}function J(a){return typeof a.title=="string"?a.title:Array.isArray(a.title)&&a.title.length?String(a.title[0]):a.fullPath}function r(a){return!(a.closable===!1||n.options.keepLastTab&&n.tabs.length<=1)}async function l(a){await n.closeTab(a.id)}function c(a){n.activeId.value!==a.id&&n.openTab(a.to,!1)}function k(a){return["router-tab__item",{"is-active":n.activeId.value===a.id,"is-closable":r(a)},a.tabClass]}function P(a){return n.refreshingKey.value===n.getRouteKey(a)}async function x(){const a=d.value;if(!a||!D)return;const u=window.sessionStorage.getItem(a);if(u)try{const h=JSON.parse(u);if(!h||!Array.isArray(h.tabs))return;b=!0,await n.hydrate(h)}catch{}finally{b=!1,K()}}function K(){const a=d.value;if(!(!a||!D||b))try{const u=n.snapshot();window.sessionStorage.setItem(a,JSON.stringify(u))}catch{}}t.onMounted(()=>{document.addEventListener("keydown",T),x()}),t.onBeforeUnmount(()=>{document.removeEventListener("keydown",T),o.appContext.config.globalProperties.$tabs=null,K()}),t.watch(()=>e.keepAlive,a=>{n.options.keepAlive=a}),t.watch(()=>n.activeId.value,()=>T()),t.watch(()=>e.contextmenu,a=>{a||T()}),t.watch(()=>A.value.length,a=>{p.visible&&a===0&&T()}),t.watch(()=>({key:d.value,tabs:n.tabs.map(a=>({to:a.to,title:a.title,tips:a.tips,icon:a.icon,tabClass:a.tabClass,closable:a.closable})),active:n.activeId.value}),()=>{K()},{deep:!0});const je=n.includeKeys;return{controller:n,tabs:n.tabs,includeKeys:je,tabTransitionProps:s,pageTransitionProps:f,buildTabClass:k,activate:c,close:l,context:p,menuItems:A,handleMenuAction:U,showContextMenu:E,hideContextMenu:T,tabTitle:J,isClosable:r,isRefreshing:P}}}),ve=(e,o)=>{const i=e.__vccOpts||e;for(const[n,s]of o)i[n]=s;return i},Re={class:"router-tab"},Ce={class:"router-tab__header"},_e={class:"router-tab__slot-start"},Se={class:"router-tab__scroll"},Ae=["onClick","onAuxclick","onContextmenu"],Ee=["title"],Pe=["onClick"],Ve={class:"router-tab__slot-end"},Ne={class:"router-tab__container"},xe=["aria-disabled","onClick"];function Be(e,o,i,n,s,f){const p=t.resolveComponent("RouterView");return t.openBlock(),t.createElementBlock("div",Re,[t.createElementVNode("header",Ce,[t.createElementVNode("div",_e,[t.renderSlot(e.$slots,"start")]),t.createElementVNode("div",Se,[t.createVNode(t.TransitionGroup,t.mergeProps({tag:"ul",class:"router-tab__nav"},e.tabTransitionProps),{default:t.withCtx(()=>[(t.openBlock(!0),t.createElementBlock(t.Fragment,null,t.renderList(e.tabs,d=>(t.openBlock(),t.createElementBlock("li",{key:d.id,class:t.normalizeClass(e.buildTabClass(d)),onClick:b=>e.activate(d),onAuxclick:t.withModifiers(b=>e.close(d),["middle","prevent"]),onContextmenu:t.withModifiers(b=>e.showContextMenu(d,b),["prevent"])},[t.createElementVNode("span",{class:"router-tab__item-title",title:e.tabTitle(d)},[d.icon?(t.openBlock(),t.createElementBlock("i",{key:0,class:t.normalizeClass(["router-tab__item-icon",d.icon])},null,2)):t.createCommentVNode("",!0),t.createTextVNode(" "+t.toDisplayString(e.tabTitle(d)),1)],8,Ee),e.isClosable(d)?(t.openBlock(),t.createElementBlock("a",{key:0,class:"router-tab__item-close",onClick:t.withModifiers(b=>e.close(d),["stop"])},null,8,Pe)):t.createCommentVNode("",!0)],42,Ae))),128))]),_:1},16)]),t.createElementVNode("div",Ve,[t.renderSlot(e.$slots,"end")])]),t.createElementVNode("div",Ne,[t.createVNode(p,null,{default:t.withCtx(({Component:d,route:b})=>[t.createVNode(t.Transition,t.mergeProps(e.pageTransitionProps,{appear:""}),{default:t.withCtx(()=>[e.controller.options.keepAlive?(t.openBlock(),t.createBlock(t.KeepAlive,{key:0,include:e.includeKeys,max:e.controller.options.maxAlive||void 0},[e.isRefreshing(b)?t.createCommentVNode("",!0):(t.openBlock(),t.createBlock(t.resolveDynamicComponent(d),{key:e.controller.getRouteKey(b),class:"router-tab-page"}))],1032,["include","max"])):t.createCommentVNode("",!0)]),_:2},1040),t.createVNode(t.Transition,t.mergeProps(e.pageTransitionProps,{appear:""}),{default:t.withCtx(()=>[!e.controller.options.keepAlive||e.isRefreshing(b)?(t.openBlock(),t.createBlock(t.resolveDynamicComponent(d),{key:e.controller.getRouteKey(b)+(e.isRefreshing(b)?"-refresh":""),class:"router-tab-page"})):t.createCommentVNode("",!0)]),_:2},1040)]),_:1})]),e.context.visible&&e.context.target?(t.openBlock(),t.createElementBlock("div",{key:0,class:"router-tab__contextmenu",style:t.normalizeStyle({left:e.context.position.x+"px",top:e.context.position.y+"px"})},[(t.openBlock(!0),t.createElementBlock(t.Fragment,null,t.renderList(e.menuItems,d=>(t.openBlock(),t.createElementBlock("a",{key:d.id,class:"router-tab__contextmenu-item","aria-disabled":d.disabled,onClick:t.withModifiers(b=>e.handleMenuAction(d),["prevent"])},t.toDisplayString(d.label),9,xe))),128))],4)):t.createCommentVNode("",!0)])}const z=ve(ke,[["render",Be]]);function oe(e={}){const{optional:o=!1}=e,i=t.inject(B,null);if(i)return i;const n=t.inject("$tabs",null);if(n)return n;const f=t.getCurrentInstance()?.appContext.config.globalProperties.$tabs;if(f)return f;if(!o)throw new Error("[RouterTabs] useRouterTabs must be used within <router-tab>.");return null}const Ie="router-tabs:persistent";function Oe(e){return typeof window>"u"?null:e===void 0?window.localStorage??null:e}function Ke(e){const o=Oe(e.storage),i=e.storageKey??Ie;return re.defineStore(e.storeId??"routerTabs",{state:()=>({snapshot:null}),actions:{load(){if(!(!o||this.snapshot))try{const n=o.getItem(i);n&&(this.snapshot=JSON.parse(n))}catch{}},setSnapshot(n){if(this.snapshot=n,!!o)try{n&&n.tabs.length?o.setItem(i,JSON.stringify(n)):o.removeItem(i)}catch{}},clear(){this.setSnapshot(null)}}})}function ae(e={}){const o=oe({optional:!0});if(!o)throw new Error("[RouterTabs] Pinia helper must be used inside <router-tab>.");const n=(e.store??Ke(e))(),s=t.ref(!1);return t.onMounted(async()=>{n.load();const f=n.snapshot;if(f&&f.tabs?.length)try{s.value=!0,await o.hydrate(f)}finally{s.value=!1}else try{s.value=!0;const p=e.fallbackRoute??o.options.defaultRoute;await o.reset(p)}finally{s.value=!1}n.setSnapshot(o.snapshot())}),t.watch(()=>({tabs:o.tabs.map(f=>({to:f.to,title:f.title,tips:f.tips,icon:f.icon,tabClass:f.tabClass,closable:f.closable})),active:o.activeId.value}),()=>{s.value||n.setSnapshot(o.snapshot())},{deep:!0}),n}const $e={class:"router-tabs","aria-hidden":"true"},I=t.defineComponent({name:"RouterTabs",__name:"RouterTabsPinia",props:{storeId:{},storageKey:{},storage:{},fallbackRoute:{},store:{type:[Function,Object]}},setup(e){return ae(e),(i,n)=>(t.openBlock(),t.createElementBlock("span",$e))}}),G={install(e){if(G._installed)return;G._installed=!0;const o=z.name||"RouterTab",i=I.name||"RouterTabs";e.component(o,z),e.component(i,I),i!=="router-tabs"&&e.component("router-tabs",I),Object.defineProperty(e.config.globalProperties,"$tabs",{configurable:!0,enumerable:!1,get(){return e._context.provides[B]},set(n){n&&e.provide(B,n)}})}};v.RouterTab=z,v.RouterTabs=I,v.RouterTabsPinia=I,v.default=G,v.routerTabsKey=B,v.useRouterTabs=oe,v.useRouterTabsPiniaPersistence=ae,Object.defineProperties(v,{__esModule:{value:!0},[Symbol.toStringTag]:{value:"Module"}})}));
package/package.json CHANGED
@@ -1,21 +1,23 @@
1
1
  {
2
2
  "name": "vue3-router-tab",
3
- "version": "1.0.4",
3
+ "version": "1.0.6",
4
4
  "type": "module",
5
5
  "files": [
6
6
  "dist",
7
7
  "lib",
8
8
  "index.d.ts"
9
9
  ],
10
- "main": "dist/vue3-router-tab.cjs.js",
11
- "module": "dist/vue3-router-tab.es.js",
10
+ "main": "dist/vue3-router-tab.umd.cjs",
11
+ "module": "dist/vue3-router-tab.js",
12
12
  "exports": {
13
13
  ".": {
14
14
  "types": "./index.d.ts",
15
- "import": "./dist/vue3-router-tab.es.js",
16
- "require": "./dist/vue3-router-tab.cjs.js"
15
+ "default": "./dist/vue3-router-tab.js",
16
+ "import": "./dist/vue3-router-tab.js",
17
+ "require": "./dist/vue3-router-tab.umd.cjs"
17
18
  },
18
- "./style": "./dist/vue3-router-tab.css"
19
+ "./style": "./dist/vue3-router-tab.css",
20
+ "./package.json": "./package.json"
19
21
  },
20
22
  "scripts": {
21
23
  "build": "vite build"
@@ -40,9 +42,6 @@
40
42
  "router",
41
43
  "tabs",
42
44
  "tab",
43
- "pinia",
44
- "persistence",
45
- "tab persistence",
46
45
  "router-tab"
47
46
  ],
48
47
  "license": "MIT",
@@ -1,12 +0,0 @@
1
- "use strict";Object.defineProperties(exports,{__esModule:{value:!0},[Symbol.toStringTag]:{value:"Module"}});const t=require("vue"),le=require("pinia");/*!
2
- * vue-router v4.5.1
3
- * (c) 2025 Eduardo San Martin Morote
4
- * @license MIT
5
- */const ce=typeof document<"u",ue=Object.assign,fe=Array.isArray;function de(e){const o=Array.from(arguments).slice(1);console.warn.apply(console,["[Vue Router warn]: "+e].concat(o))}function pe(e,o){return(e.aliasOf||e)===(o.aliasOf||o)}var H;(function(e){e.pop="pop",e.push="push"})(H||(H={}));var F;(function(e){e.back="back",e.forward="forward",e.unknown=""})(F||(F={}));Symbol(process.env.NODE_ENV!=="production"?"navigation failure":"");var X;(function(e){e[e.aborted=4]="aborted",e[e.cancelled=8]="cancelled",e[e.duplicated=16]="duplicated"})(X||(X={}));const be=Symbol(process.env.NODE_ENV!=="production"?"router view location matched":""),Y=Symbol(process.env.NODE_ENV!=="production"?"router view depth":"");Symbol(process.env.NODE_ENV!=="production"?"router":"");Symbol(process.env.NODE_ENV!=="production"?"route location":"");const Q=Symbol(process.env.NODE_ENV!=="production"?"router view location":""),ve=t.defineComponent({name:"RouterView",inheritAttrs:!1,props:{name:{type:String,default:"default"},route:Object},compatConfig:{MODE:3},setup(e,{attrs:o,slots:r}){process.env.NODE_ENV!=="production"&&he();const n=t.inject(Q),l=t.computed(()=>e.route||n.value),f=t.inject(Y,0),p=t.computed(()=>{let h=t.unref(f);const{matched:v}=l.value;let y;for(;(y=v[h])&&!y.components;)h++;return h}),d=t.computed(()=>l.value.matched[p.value]);t.provide(Y,t.computed(()=>p.value+1)),t.provide(be,d),t.provide(Q,l);const b=t.ref();return t.watch(()=>[b.value,d.value,e.name],([h,v,y],[T,g,_])=>{v&&(v.instances[y]=h,g&&g!==v&&h&&h===T&&(v.leaveGuards.size||(v.leaveGuards=g.leaveGuards),v.updateGuards.size||(v.updateGuards=g.updateGuards))),h&&v&&(!g||!pe(v,g)||!T)&&(v.enterCallbacks[y]||[]).forEach(C=>C(h))},{flush:"post"}),()=>{const h=l.value,v=e.name,y=d.value,T=y&&y.components[v];if(!T)return W(r.default,{Component:T,route:h});const g=y.props[v],_=g?g===!0?h.params:typeof g=="function"?g(h):g:null,C=A=>{A.component.isUnmounted&&(y.instances[v]=null)},w=t.h(T,ue({},_,o,{onVnodeUnmounted:C,ref:b}));if(process.env.NODE_ENV!=="production"&&ce&&w.ref){const A={depth:p.value,name:y.name,path:y.path,meta:y.meta};(fe(w.ref)?w.ref.map(S=>S.i):[w.ref.i]).forEach(S=>{S.__vrv_devtools=A})}return W(r.default,{Component:w,route:h})||w}}});function W(e,o){if(!e)return null;const r=e(o);return r.length===1?r[0]:r}const me=ve;function he(){const e=t.getCurrentInstance(),o=e.parent&&e.parent.type.name,r=e.parent&&e.parent.subTree&&e.parent.subTree.type;if(o&&(o==="KeepAlive"||o.includes("Transition"))&&typeof r=="object"&&r.name==="RouterView"){const n=o==="KeepAlive"?"keep-alive":"transition";de(`<router-view> can no longer be used directly inside <transition> or <keep-alive>.
6
- Use slot props instead:
7
-
8
- <router-view v-slot="{ Component }">
9
- <${n}>
10
- <component :is="Component" />
11
- </${n}>
12
- </router-view>`)}}function ye(e={}){return{initialTabs:e.initialTabs??[],keepAlive:e.keepAlive??!0,maxAlive:e.maxAlive??0,keepLastTab:e.keepLastTab??!0,appendPosition:e.appendPosition??"last",defaultRoute:e.defaultRoute??"/"}}function V(e,o){const r=e.resolve(o);if(!r||!r.matched.length)throw new Error(`[RouterTabs] Unable to resolve route: ${String(o)}`);return r}const ge={path:e=>e.path,fullpath:e=>e.fullPath,fullname:e=>e.fullPath,full:e=>e.fullPath,name:e=>e.name?String(e.name):e.fullPath};function x(e){const o=e.meta?.key;if(typeof o=="function"){const r=o(e);if(typeof r=="string"&&r.length)return r}else if(typeof o=="string"&&o.length){const r=ge[o.toLowerCase()];return r?r(e):o}return e.fullPath}function z(e,o){const r=e.meta?.keepAlive;return typeof r=="boolean"?r:o}function G(e,o){const r=e.meta?.reuse;return typeof r=="boolean"?r:o}function te(e){const o=e.meta??{},r={};return"title"in o&&(r.title=o.title),"tips"in o&&(r.tips=o.tips),"icon"in o&&(r.icon=o.icon),"closable"in o&&(r.closable=o.closable),"tabClass"in o&&(r.tabClass=o.tabClass),"target"in o&&(r.target=o.target),"href"in o&&(r.href=o.href),r}function O(e,o,r){const n=te(e);return{id:x(e),to:e.fullPath,fullPath:e.fullPath,matched:e,alive:z(e,r),reusable:G(e,!1),closable:n.closable??!0,...n,...o}}function L(e,o,r,n){if(!e.find(f=>f.id===o.id)){if(r==="next"&&n){const f=e.findIndex(p=>p.id===n);if(f>-1){e.splice(f+1,0,o);return}}e.push(o)}}function Z(e,o,r){if(!o||o<=0)return;const n=e.filter(l=>l.alive);for(;n.length>o;){const l=n.shift();if(!l||l.id===r)continue;const f=e.findIndex(p=>p.id===l.id);f>-1&&(e[f].alive=!1)}}function we(e){return{to:e.to,title:e.title,tips:e.tips,icon:e.icon,tabClass:e.tabClass,closable:e.closable}}function ke(e){const o={};return"title"in e&&(o.title=e.title),"tips"in e&&(o.tips=e.tips),"icon"in e&&(o.icon=e.icon),"tabClass"in e&&(o.tabClass=e.tabClass),"closable"in e&&(o.closable=e.closable),o}function Te(e,o={}){const r=ye(o),n=t.reactive([]),l=t.ref(null),f=t.shallowRef(),p=t.ref(null),d=t.computed(()=>n.filter(i=>i.alive).map(i=>i.id));let b=!1;function h(i){const s=typeof i.matched=="object"?i:V(e,i);return{key:x(s),fullPath:s.fullPath,alive:z(s,r.keepAlive),reusable:G(s,!1),matched:s}}function v(i){const s=x(i);let c=n.find(k=>k.id===s);return c?(c.fullPath=i.fullPath,c.to=i.fullPath,c.matched=i,c.alive=z(i,r.keepAlive),c.reusable=G(i,c.reusable),Object.assign(c,te(i)),c):(c=O(i,{},r.keepAlive),L(n,c,r.appendPosition,l.value),Z(n,r.maxAlive,l.value),c)}async function y(i,s=!1,c=!0){const k=V(e,i),E=x(k),P=l.value===E;c==="sameTab"&&(c=P),c&&await C(E,!0),await e[s?"replace":"push"](k),P&&await N()}function T(i){const s=n.findIndex(k=>k.id===i),c=n[s]||n[s-1]||n[0];return c?c.to:r.defaultRoute}async function g(i=l.value,s={}){if(i){if(!s.force&&r.keepLastTab&&n.length===1)throw new Error("[RouterTabs] Unable to close the final tab when keepLastTab is true.");if(await _(i,{force:s.force}),s.redirect!==null)if(l.value===i){const c=s.redirect??T(i);c&&await e.replace(c)}else s.redirect&&await e.replace(s.redirect)}}async function _(i,s={}){const c=n.findIndex(k=>k.id===i);c!==-1&&(n.splice(c,1),p.value===i&&(p.value=null),l.value===i&&(l.value=null,f.value=void 0))}async function C(i=l.value??void 0,s=!1){i&&(p.value=i,await t.nextTick(),s||await t.nextTick(),p.value=null)}async function w(i=!1){for(const s of n)await C(s.id,i)}async function A(i=r.defaultRoute){n.splice(0,n.length),l.value=null,f.value=void 0;for(const s of r.initialTabs){const c=V(e,s.to),k=O(c,s,r.keepAlive);n.push(k)}await e.replace(i)}async function N(){const i=l.value;i&&await C(i,!0)}function S(i){return typeof i.matched=="object"?x(i):x(V(e,i))}function K(){const i=n.find(s=>s.id===l.value);return{tabs:n.map(we),active:i?i.to:null}}async function $(i){b=!0,n.splice(0,n.length),l.value=null,f.value=void 0;const s=i?.tabs??[];for(const k of s)try{const E=V(e,k.to),P=ke(k),B=O(E,P,r.keepAlive);L(n,B,"last",null)}catch{}b=!1;const c=i?.active??s[s.length-1]?.to??r.defaultRoute;if(c)try{await e.replace(c)}catch{}}return t.watch(()=>e.currentRoute.value,i=>{if(b)return;const s=v(i);l.value=s.id,f.value=s,Z(n,r.maxAlive,l.value)},{immediate:!0}),r.initialTabs.length&&r.initialTabs.forEach(i=>{const s=V(e,i.to),c=O(s,i,r.keepAlive);L(n,c,"last",null)}),{options:r,tabs:n,activeId:l,current:f,includeKeys:d,refreshingKey:p,openTab:y,closeTab:g,removeTab:_,refreshTab:C,refreshAll:w,reset:A,reload:N,getRouteKey:S,matchRoute:h,snapshot:K,hydrate:$}}function ee(e){return e?typeof e=="string"?{name:e}:e:{}}const I=Symbol("RouterTabsContext"),D=typeof window<"u"&&"sessionStorage"in window,Ce=t.defineComponent({name:"RouterTab",components:{RouterView:me},props:{tabs:{type:Array,default:()=>[]},keepAlive:{type:Boolean,default:!0},maxAlive:{type:Number,default:0},keepLastTab:{type:Boolean,default:!0},append:{type:String,default:"last"},defaultPage:{type:[String,Object],default:"/"},tabTransition:{type:[String,Object],default:"router-tab-zoom"},pageTransition:{type:[String,Object],default:()=>({name:"router-tab-swap",mode:"out-in"})},contextmenu:{type:[Boolean,Array],default:!0},storage:{type:[Boolean,String],default:!1}},setup(e){const o=t.getCurrentInstance();if(!o)throw new Error("[RouterTab] component must be used within a Vue application context.");const r=o.appContext.app.config.globalProperties.$router;if(!r)throw new Error("[RouterTab] Vue Router is required. Make sure to call app.use(router) before RouterTab.");const n=Te(r,{initialTabs:e.tabs,keepAlive:e.keepAlive,maxAlive:e.maxAlive,keepLastTab:e.keepLastTab,appendPosition:e.append,defaultRoute:e.defaultPage});t.provide(I,n),o.appContext.config.globalProperties.$tabs=n;const l=t.computed(()=>ee(e.tabTransition)),f=t.computed(()=>ee(e.pageTransition)),p=t.reactive({visible:!1,target:null,position:{x:0,y:0}}),d=t.computed(()=>!e.storage||!D?null:typeof e.storage=="string"?e.storage:`router-tabs:${(r.options?.history?.base??"")||"default"}`);let b=!!d.value;const h=["refresh","refreshAll","close","closeLefts","closeRights","closeOthers"];function v(a){return n.tabs.findIndex(u=>u.id===a)}function y(a){const u=v(a.id);return u>0?n.tabs.slice(0,u):[]}function T(a){const u=v(a.id);return u>-1?n.tabs.slice(u+1):[]}function g(a){return n.tabs.filter(u=>u.id!==a.id)}async function _(a,u){const m=a.filter(R=>R.closable!==!1);if(m.length){for(const R of m)n.activeId.value===R.id?await n.closeTab(R.id,{redirect:u.to,force:!0}):await n.removeTab(R.id,{force:!0});n.activeId.value!==u.id&&await n.openTab(u.to,!0,!1)}}const C={refresh:{label:"Refresh",handler:async({target:a})=>{await n.refreshTab(a.id,!0)}},refreshAll:{label:"Refresh All",handler:async()=>{await n.refreshAll(!0)}},close:{label:"Close",handler:async({target:a})=>{await n.closeTab(a.id)},enable:({target:a})=>i(a)},closeLefts:{label:"Close to the Left",handler:async({target:a})=>{await _(y(a),a)},enable:({target:a})=>y(a).some(u=>u.closable!==!1)},closeRights:{label:"Close to the Right",handler:async({target:a})=>{await _(T(a),a)},enable:({target:a})=>T(a).some(u=>u.closable!==!1)},closeOthers:{label:"Close Others",handler:async({target:a})=>{await _(g(a),a)},enable:({target:a})=>g(a).some(u=>u.closable!==!1)}};function w(){p.visible=!1,p.target=null}function A(a,u){e.contextmenu&&(p.visible=!0,p.target=a,p.position.x=u.clientX,p.position.y=u.clientY,document.addEventListener("click",w,{once:!0}))}function N(a,u){const m=typeof a=="string"?{id:a}:a,R=C[m.id],re=m.label??R?.label??String(m.id),M=m.visible??R?.visible??!0;if(!(typeof M=="function"?M(u):M!==!1))return null;const j=m.enable??R?.enable??!0,ie=typeof j=="function"?j(u):j!==!1,q=m.handler??R?.handler;if(!q)return null;const se=async()=>{await Promise.resolve(q(u))};return{id:String(m.id),label:re,disabled:!ie,action:se}}const S=t.computed(()=>{if(!p.visible||!p.target||e.contextmenu===!1)return[];const a=Array.isArray(e.contextmenu)?e.contextmenu:h,u={target:p.target,controller:n};return a.map(m=>N(m,u)).filter(m=>!!m)});async function K(a){a.disabled||(w(),await a.action())}function $(a){return typeof a.title=="string"?a.title:Array.isArray(a.title)&&a.title.length?String(a.title[0]):a.fullPath}function i(a){return!(a.closable===!1||n.options.keepLastTab&&n.tabs.length<=1)}async function s(a){await n.closeTab(a.id)}function c(a){n.activeId.value!==a.id&&n.openTab(a.to,!1)}function k(a){return["router-tab__item",{"is-active":n.activeId.value===a.id,"is-closable":i(a)},a.tabClass]}function E(a){return n.refreshingKey.value===n.getRouteKey(a)}async function P(){const a=d.value;if(!a||!D)return;const u=window.sessionStorage.getItem(a);if(u)try{const m=JSON.parse(u);if(!m||!Array.isArray(m.tabs))return;b=!0,await n.hydrate(m)}catch{}finally{b=!1,B()}}function B(){const a=d.value;if(!(!a||!D||b))try{const u=n.snapshot();window.sessionStorage.setItem(a,JSON.stringify(u))}catch{}}t.onMounted(()=>{document.addEventListener("keydown",w),P()}),t.onBeforeUnmount(()=>{document.removeEventListener("keydown",w),o.appContext.config.globalProperties.$tabs=null,B()}),t.watch(()=>e.keepAlive,a=>{n.options.keepAlive=a}),t.watch(()=>n.activeId.value,()=>w()),t.watch(()=>e.contextmenu,a=>{a||w()}),t.watch(()=>S.value.length,a=>{p.visible&&a===0&&w()}),t.watch(()=>({key:d.value,tabs:n.tabs.map(a=>({to:a.to,title:a.title,tips:a.tips,icon:a.icon,tabClass:a.tabClass,closable:a.closable})),active:n.activeId.value}),()=>{B()},{deep:!0});const ae=n.includeKeys;return{controller:n,tabs:n.tabs,includeKeys:ae,tabTransitionProps:l,pageTransitionProps:f,buildTabClass:k,activate:c,close:s,context:p,menuItems:S,handleMenuAction:K,showContextMenu:A,hideContextMenu:w,tabTitle:$,isClosable:i,isRefreshing:E}}}),Re=(e,o)=>{const r=e.__vccOpts||e;for(const[n,l]of o)r[n]=l;return r},_e={class:"router-tab"},Se={class:"router-tab__header"},Ae={class:"router-tab__slot-start"},Ee={class:"router-tab__scroll"},Pe=["onClick","onAuxclick","onContextmenu"],Ve=["title"],xe=["onClick"],Ne={class:"router-tab__slot-end"},Be={class:"router-tab__container"},Ie=["aria-disabled","onClick"];function Oe(e,o,r,n,l,f){const p=t.resolveComponent("RouterView");return t.openBlock(),t.createElementBlock("div",_e,[t.createElementVNode("header",Se,[t.createElementVNode("div",Ae,[t.renderSlot(e.$slots,"start")]),t.createElementVNode("div",Ee,[t.createVNode(t.TransitionGroup,t.mergeProps({tag:"ul",class:"router-tab__nav"},e.tabTransitionProps),{default:t.withCtx(()=>[(t.openBlock(!0),t.createElementBlock(t.Fragment,null,t.renderList(e.tabs,d=>(t.openBlock(),t.createElementBlock("li",{key:d.id,class:t.normalizeClass(e.buildTabClass(d)),onClick:b=>e.activate(d),onAuxclick:t.withModifiers(b=>e.close(d),["middle","prevent"]),onContextmenu:t.withModifiers(b=>e.showContextMenu(d,b),["prevent"])},[t.createElementVNode("span",{class:"router-tab__item-title",title:e.tabTitle(d)},[d.icon?(t.openBlock(),t.createElementBlock("i",{key:0,class:t.normalizeClass(["router-tab__item-icon",d.icon])},null,2)):t.createCommentVNode("",!0),t.createTextVNode(" "+t.toDisplayString(e.tabTitle(d)),1)],8,Ve),e.isClosable(d)?(t.openBlock(),t.createElementBlock("a",{key:0,class:"router-tab__item-close",onClick:t.withModifiers(b=>e.close(d),["stop"])},null,8,xe)):t.createCommentVNode("",!0)],42,Pe))),128))]),_:1},16)]),t.createElementVNode("div",Ne,[t.renderSlot(e.$slots,"end")])]),t.createElementVNode("div",Be,[t.createVNode(p,null,{default:t.withCtx(({Component:d,route:b})=>[t.createVNode(t.Transition,t.mergeProps(e.pageTransitionProps,{appear:""}),{default:t.withCtx(()=>[e.controller.options.keepAlive?(t.openBlock(),t.createBlock(t.KeepAlive,{key:0,include:e.includeKeys,max:e.controller.options.maxAlive||void 0},[e.isRefreshing(b)?t.createCommentVNode("",!0):(t.openBlock(),t.createBlock(t.resolveDynamicComponent(d),{key:e.controller.getRouteKey(b),class:"router-tab-page"}))],1032,["include","max"])):t.createCommentVNode("",!0)]),_:2},1040),t.createVNode(t.Transition,t.mergeProps(e.pageTransitionProps,{appear:""}),{default:t.withCtx(()=>[!e.controller.options.keepAlive||e.isRefreshing(b)?(t.openBlock(),t.createBlock(t.resolveDynamicComponent(d),{key:e.controller.getRouteKey(b)+(e.isRefreshing(b)?"-refresh":""),class:"router-tab-page"})):t.createCommentVNode("",!0)]),_:2},1040)]),_:1})]),e.context.visible&&e.context.target?(t.openBlock(),t.createElementBlock("div",{key:0,class:"router-tab__contextmenu",style:t.normalizeStyle({left:e.context.position.x+"px",top:e.context.position.y+"px"})},[(t.openBlock(!0),t.createElementBlock(t.Fragment,null,t.renderList(e.menuItems,d=>(t.openBlock(),t.createElementBlock("a",{key:d.id,class:"router-tab__contextmenu-item","aria-disabled":d.disabled,onClick:t.withModifiers(b=>e.handleMenuAction(d),["prevent"])},t.toDisplayString(d.label),9,Ie))),128))],4)):t.createCommentVNode("",!0)])}const U=Re(Ce,[["render",Oe]]);function ne(e={}){const{optional:o=!1}=e,r=t.inject(I,null);if(r)return r;const n=t.inject("$tabs",null);if(n)return n;const f=t.getCurrentInstance()?.appContext.config.globalProperties.$tabs;if(f)return f;if(!o)throw new Error("[RouterTabs] useRouterTabs must be used within <router-tab>.");return null}const Ke="router-tabs:persistent";function $e(e){return typeof window>"u"?null:e===void 0?window.localStorage??null:e}function Me(e){const o=$e(e.storage),r=e.storageKey??Ke;return le.defineStore(e.storeId??"routerTabs",{state:()=>({snapshot:null}),actions:{load(){if(!(!o||this.snapshot))try{const n=o.getItem(r);n&&(this.snapshot=JSON.parse(n))}catch{}},setSnapshot(n){if(this.snapshot=n,!!o)try{n&&n.tabs.length?o.setItem(r,JSON.stringify(n)):o.removeItem(r)}catch{}},clear(){this.setSnapshot(null)}}})}function oe(e={}){const o=ne(),n=(e.store??Me(e))(),l=t.ref(!1);return t.onMounted(async()=>{n.load();const f=n.snapshot;if(f)try{l.value=!0,await o.hydrate(f)}finally{l.value=!1,n.setSnapshot(o.snapshot())}}),t.watch(()=>({tabs:o.tabs.map(f=>({to:f.to,title:f.title,tips:f.tips,icon:f.icon,tabClass:f.tabClass,closable:f.closable})),active:o.activeId.value}),()=>{l.value||n.setSnapshot(o.snapshot())},{deep:!0}),n}const je={class:"router-tabs-pinia","aria-hidden":"true"},Le=t.defineComponent({__name:"RouterTabsPinia",props:{storeId:{},storageKey:{},storage:{},store:{type:[Function,Object]}},setup(e){return oe(e),(r,n)=>(t.openBlock(),t.createElementBlock("span",je))}}),J={install(e){J._installed||(J._installed=!0,e.component(U.name,U),Object.defineProperty(e.config.globalProperties,"$tabs",{configurable:!0,enumerable:!1,get(){return e._context.provides[I]},set(o){o&&e.provide(I,o)}}))}};exports.RouterTab=U;exports.RouterTabsPinia=Le;exports.default=J;exports.routerTabsKey=I;exports.useRouterTabs=ne;exports.useRouterTabsPiniaPersistence=oe;