@vue-skuilder/common-ui 0.2.34 → 0.2.36

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.
Files changed (207) hide show
  1. package/dist/_virtual/_@oxc-project_runtime@0.115.0/helpers/defineProperty.mjs +13 -0
  2. package/dist/_virtual/_@oxc-project_runtime@0.115.0/helpers/toPrimitive.mjs +15 -0
  3. package/dist/_virtual/_@oxc-project_runtime@0.115.0/helpers/toPropertyKey.mjs +10 -0
  4. package/dist/_virtual/_@oxc-project_runtime@0.115.0/helpers/typeof.mjs +12 -0
  5. package/dist/_virtual/_plugin-vue_export-helper.mjs +9 -0
  6. package/dist/_virtual/_rolldown/runtime.mjs +7 -0
  7. package/dist/admin/admin.css +1 -1
  8. package/dist/admin/common-ui-admin.es.js +1074 -473
  9. package/dist/admin/common-ui-admin.es.js.map +1 -1
  10. package/dist/admin/components/EChart.vue.d.ts +14 -0
  11. package/dist/admin/components/EChart.vue.d.ts.map +1 -0
  12. package/dist/admin/components/LearnerDiagnostics.vue.d.ts +3 -3
  13. package/dist/admin/components/LearnerDiagnostics.vue.d.ts.map +1 -1
  14. package/dist/admin/components/LearnerTagElo.vue.d.ts +14 -0
  15. package/dist/admin/components/LearnerTagElo.vue.d.ts.map +1 -0
  16. package/dist/admin/index.d.ts +1 -0
  17. package/dist/admin/index.d.ts.map +1 -1
  18. package/dist/assets/index.css +2 -1
  19. package/dist/components/CardBrowser.mjs +63 -0
  20. package/dist/components/CardBrowser.mjs.map +1 -0
  21. package/dist/components/CardBrowser.vue_vue_type_script_lang.mjs +50 -0
  22. package/dist/components/CardBrowser.vue_vue_type_script_lang.mjs.map +1 -0
  23. package/dist/components/CardHistoryViewer.mjs +70 -0
  24. package/dist/components/CardHistoryViewer.mjs.map +1 -0
  25. package/dist/components/CardHistoryViewer.vue_vue_type_script_lang.mjs +108 -0
  26. package/dist/components/CardHistoryViewer.vue_vue_type_script_lang.mjs.map +1 -0
  27. package/dist/components/CardSearch.mjs +26 -0
  28. package/dist/components/CardSearch.mjs.map +1 -0
  29. package/dist/components/CardSearch.vue_vue_type_script_lang.mjs +17 -0
  30. package/dist/components/CardSearch.vue_vue_type_script_lang.mjs.map +1 -0
  31. package/dist/components/CardSearchResults.mjs +32 -0
  32. package/dist/components/CardSearchResults.mjs.map +1 -0
  33. package/dist/components/CardSearchResults.vue_vue_type_script_lang.mjs +71 -0
  34. package/dist/components/CardSearchResults.vue_vue_type_script_lang.mjs.map +1 -0
  35. package/dist/components/CourseCardBrowser.mjs +175 -0
  36. package/dist/components/CourseCardBrowser.mjs.map +1 -0
  37. package/dist/components/CourseCardBrowser.vue.d.ts +3 -3
  38. package/dist/components/CourseCardBrowser.vue_vue_type_script_lang.mjs +173 -0
  39. package/dist/components/CourseCardBrowser.vue_vue_type_script_lang.mjs.map +1 -0
  40. package/dist/components/CourseInformation.mjs +132 -0
  41. package/dist/components/CourseInformation.mjs.map +1 -0
  42. package/dist/components/CourseInformation.vue.d.ts +3 -3
  43. package/dist/components/CourseInformation.vue_vue_type_script_lang.mjs +56 -0
  44. package/dist/components/CourseInformation.vue_vue_type_script_lang.mjs.map +1 -0
  45. package/dist/components/CourseTagFilterWidget.mjs +114 -0
  46. package/dist/components/CourseTagFilterWidget.mjs.map +1 -0
  47. package/dist/components/CourseTagFilterWidget.vue_vue_type_script_lang.mjs +65 -0
  48. package/dist/components/CourseTagFilterWidget.vue_vue_type_script_lang.mjs.map +1 -0
  49. package/dist/components/HeatMap.mjs +40 -0
  50. package/dist/components/HeatMap.mjs.map +1 -0
  51. package/dist/components/HeatMap.vue_vue_type_script_lang.mjs +211 -0
  52. package/dist/components/HeatMap.vue_vue_type_script_lang.mjs.map +1 -0
  53. package/dist/components/PaginatingToolbar.mjs +94 -0
  54. package/dist/components/PaginatingToolbar.mjs.map +1 -0
  55. package/dist/components/PaginatingToolbar.vue.d.ts +3 -3
  56. package/dist/components/PaginatingToolbar.vue_vue_type_script_lang.mjs +36 -0
  57. package/dist/components/PaginatingToolbar.vue_vue_type_script_lang.mjs.map +1 -0
  58. package/dist/components/SessionControllerDebug.mjs +130 -0
  59. package/dist/components/SessionControllerDebug.mjs.map +1 -0
  60. package/dist/components/SessionControllerDebug.vue_vue_type_script_lang.mjs +45 -0
  61. package/dist/components/SessionControllerDebug.vue_vue_type_script_lang.mjs.map +1 -0
  62. package/dist/components/SkMouseTrap.mjs +66 -0
  63. package/dist/components/SkMouseTrap.mjs.map +1 -0
  64. package/dist/components/SkMouseTrap.vue_vue_type_script_lang.mjs +31 -0
  65. package/dist/components/SkMouseTrap.vue_vue_type_script_lang.mjs.map +1 -0
  66. package/dist/components/SkMouseTrapToolTip.mjs +28 -0
  67. package/dist/components/SkMouseTrapToolTip.mjs.map +1 -0
  68. package/dist/components/SkMouseTrapToolTip.vue.d.ts +1 -1
  69. package/dist/components/SkMouseTrapToolTip.vue_vue_type_script_lang.mjs +91 -0
  70. package/dist/components/SkMouseTrapToolTip.vue_vue_type_script_lang.mjs.map +1 -0
  71. package/dist/components/SnackbarService.mjs +24 -0
  72. package/dist/components/SnackbarService.mjs.map +1 -0
  73. package/dist/components/SnackbarService.vue_vue_type_script_lang.mjs +34 -0
  74. package/dist/components/SnackbarService.vue_vue_type_script_lang.mjs.map +1 -0
  75. package/dist/components/SnackbarService2.mjs +40 -0
  76. package/dist/components/SnackbarService2.mjs.map +1 -0
  77. package/dist/components/StudySession.mjs +123 -0
  78. package/dist/components/StudySession.mjs.map +1 -0
  79. package/dist/components/StudySession.vue_vue_type_script_lang.mjs +280 -0
  80. package/dist/components/StudySession.vue_vue_type_script_lang.mjs.map +1 -0
  81. package/dist/components/StudySessionTimer.mjs +50 -0
  82. package/dist/components/StudySessionTimer.mjs.map +1 -0
  83. package/dist/components/StudySessionTimer.vue_vue_type_script_lang.mjs +43 -0
  84. package/dist/components/StudySessionTimer.vue_vue_type_script_lang.mjs.map +1 -0
  85. package/dist/components/TagsInput.mjs +45 -0
  86. package/dist/components/TagsInput.mjs.map +1 -0
  87. package/dist/components/TagsInput.vue_vue_type_script_lang.mjs +117 -0
  88. package/dist/components/TagsInput.vue_vue_type_script_lang.mjs.map +1 -0
  89. package/dist/components/UserTagPreferences.mjs +205 -0
  90. package/dist/components/UserTagPreferences.mjs.map +1 -0
  91. package/dist/components/UserTagPreferences.vue_vue_type_script_lang.mjs +139 -0
  92. package/dist/components/UserTagPreferences.vue_vue_type_script_lang.mjs.map +1 -0
  93. package/dist/components/auth/RequestPasswordReset.mjs +96 -0
  94. package/dist/components/auth/RequestPasswordReset.mjs.map +1 -0
  95. package/dist/components/auth/RequestPasswordReset.vue_vue_type_script_lang.mjs +47 -0
  96. package/dist/components/auth/RequestPasswordReset.vue_vue_type_script_lang.mjs.map +1 -0
  97. package/dist/components/auth/ResetPassword.mjs +129 -0
  98. package/dist/components/auth/ResetPassword.mjs.map +1 -0
  99. package/dist/components/auth/ResetPassword.vue_vue_type_script_lang.mjs +69 -0
  100. package/dist/components/auth/ResetPassword.vue_vue_type_script_lang.mjs.map +1 -0
  101. package/dist/components/auth/UserChip.mjs +9 -0
  102. package/dist/components/auth/UserChip.mjs.map +1 -0
  103. package/dist/components/auth/UserChip.vue_vue_type_script_setup_true_lang.mjs +213 -0
  104. package/dist/components/auth/UserChip.vue_vue_type_script_setup_true_lang.mjs.map +1 -0
  105. package/dist/components/auth/UserLogin.mjs +9 -0
  106. package/dist/components/auth/UserLogin.mjs.map +1 -0
  107. package/dist/components/auth/UserLogin.vue_vue_type_script_setup_true_lang.mjs +155 -0
  108. package/dist/components/auth/UserLogin.vue_vue_type_script_setup_true_lang.mjs.map +1 -0
  109. package/dist/components/auth/UserLoginAndRegistrationContainer.mjs +9 -0
  110. package/dist/components/auth/UserLoginAndRegistrationContainer.mjs.map +1 -0
  111. package/dist/components/auth/UserLoginAndRegistrationContainer.vue_vue_type_script_setup_true_lang.mjs +126 -0
  112. package/dist/components/auth/UserLoginAndRegistrationContainer.vue_vue_type_script_setup_true_lang.mjs.map +1 -0
  113. package/dist/components/auth/UserRegistration.mjs +147 -0
  114. package/dist/components/auth/UserRegistration.mjs.map +1 -0
  115. package/dist/components/auth/UserRegistration.vue_vue_type_script_lang.mjs +130 -0
  116. package/dist/components/auth/UserRegistration.vue_vue_type_script_lang.mjs.map +1 -0
  117. package/dist/components/auth/VerifyEmail.mjs +118 -0
  118. package/dist/components/auth/VerifyEmail.mjs.map +1 -0
  119. package/dist/components/auth/VerifyEmail.vue_vue_type_script_lang.mjs +59 -0
  120. package/dist/components/auth/VerifyEmail.vue_vue_type_script_lang.mjs.map +1 -0
  121. package/dist/components/cardRendering/AudioAutoPlayer.mjs +9 -0
  122. package/dist/components/cardRendering/AudioAutoPlayer.mjs.map +1 -0
  123. package/dist/components/cardRendering/AudioAutoPlayer.vue_vue_type_script_setup_true_lang.mjs +69 -0
  124. package/dist/components/cardRendering/AudioAutoPlayer.vue_vue_type_script_setup_true_lang.mjs.map +1 -0
  125. package/dist/components/cardRendering/CardLoader.mjs +31 -0
  126. package/dist/components/cardRendering/CardLoader.mjs.map +1 -0
  127. package/dist/components/cardRendering/CardLoader.vue_vue_type_script_lang.mjs +75 -0
  128. package/dist/components/cardRendering/CardLoader.vue_vue_type_script_lang.mjs.map +1 -0
  129. package/dist/components/cardRendering/CardViewer.mjs +39 -0
  130. package/dist/components/cardRendering/CardViewer.mjs.map +1 -0
  131. package/dist/components/cardRendering/CardViewer.vue_vue_type_script_lang.mjs +66 -0
  132. package/dist/components/cardRendering/CardViewer.vue_vue_type_script_lang.mjs.map +1 -0
  133. package/dist/components/cardRendering/CodeBlockRenderer.mjs +8 -0
  134. package/dist/components/cardRendering/CodeBlockRenderer.mjs.map +1 -0
  135. package/dist/components/cardRendering/CodeBlockRenderer.vue_vue_type_script_setup_true_lang.mjs +44 -0
  136. package/dist/components/cardRendering/CodeBlockRenderer.vue_vue_type_script_setup_true_lang.mjs.map +1 -0
  137. package/dist/components/cardRendering/MarkdownRenderer.mjs +21 -0
  138. package/dist/components/cardRendering/MarkdownRenderer.mjs.map +1 -0
  139. package/dist/components/cardRendering/MarkdownRenderer.vue_vue_type_script_lang.mjs +24 -0
  140. package/dist/components/cardRendering/MarkdownRenderer.vue_vue_type_script_lang.mjs.map +1 -0
  141. package/dist/components/cardRendering/MarkdownRendererHelpers.mjs +79 -0
  142. package/dist/components/cardRendering/MarkdownRendererHelpers.mjs.map +1 -0
  143. package/dist/components/cardRendering/MdTokenRenderer.mjs +9 -0
  144. package/dist/components/cardRendering/MdTokenRenderer.mjs.map +1 -0
  145. package/dist/components/cardRendering/MdTokenRenderer.vue_vue_type_script_setup_true_lang.mjs +176 -0
  146. package/dist/components/cardRendering/MdTokenRenderer.vue_vue_type_script_setup_true_lang.mjs.map +1 -0
  147. package/dist/components/studentInputs/BaseUserInput.mjs +54 -0
  148. package/dist/components/studentInputs/BaseUserInput.mjs.map +1 -0
  149. package/dist/components/studentInputs/MultipleChoiceOption.mjs +26 -0
  150. package/dist/components/studentInputs/MultipleChoiceOption.mjs.map +1 -0
  151. package/dist/components/studentInputs/MultipleChoiceOption.vue_vue_type_script_lang.mjs +76 -0
  152. package/dist/components/studentInputs/MultipleChoiceOption.vue_vue_type_script_lang.mjs.map +1 -0
  153. package/dist/components/studentInputs/RadioMultipleChoice.mjs +33 -0
  154. package/dist/components/studentInputs/RadioMultipleChoice.mjs.map +1 -0
  155. package/dist/components/studentInputs/RadioMultipleChoice.vue_vue_type_script_lang.mjs +105 -0
  156. package/dist/components/studentInputs/RadioMultipleChoice.vue_vue_type_script_lang.mjs.map +1 -0
  157. package/dist/components/studentInputs/TrueFalse.mjs +19 -0
  158. package/dist/components/studentInputs/TrueFalse.mjs.map +1 -0
  159. package/dist/components/studentInputs/TrueFalse.vue_vue_type_script_lang.mjs +21 -0
  160. package/dist/components/studentInputs/TrueFalse.vue_vue_type_script_lang.mjs.map +1 -0
  161. package/dist/components/studentInputs/UserInputNumber.mjs +33 -0
  162. package/dist/components/studentInputs/UserInputNumber.mjs.map +1 -0
  163. package/dist/components/studentInputs/UserInputNumber.vue_vue_type_script_lang.mjs +25 -0
  164. package/dist/components/studentInputs/UserInputNumber.vue_vue_type_script_lang.mjs.map +1 -0
  165. package/dist/components/studentInputs/UserInputString.mjs +22 -0
  166. package/dist/components/studentInputs/UserInputString.mjs.map +1 -0
  167. package/dist/components/studentInputs/UserInputString.vue_vue_type_script_lang.mjs +23 -0
  168. package/dist/components/studentInputs/UserInputString.vue_vue_type_script_lang.mjs.map +1 -0
  169. package/dist/components/studentInputs/fillInInput.mjs +25 -0
  170. package/dist/components/studentInputs/fillInInput.mjs.map +1 -0
  171. package/dist/components/studentInputs/fillInInput.vue_vue_type_script_lang.mjs +26 -0
  172. package/dist/components/studentInputs/fillInInput.vue_vue_type_script_lang.mjs.map +1 -0
  173. package/dist/composables/CompositionViewable.mjs +65 -0
  174. package/dist/composables/CompositionViewable.mjs.map +1 -0
  175. package/dist/composables/Displayable.mjs +36 -0
  176. package/dist/composables/Displayable.mjs.map +1 -0
  177. package/dist/composables/useAuthUI.mjs +38 -0
  178. package/dist/composables/useAuthUI.mjs.map +1 -0
  179. package/dist/composables/useEntitlements.mjs +58 -0
  180. package/dist/composables/useEntitlements.mjs.map +1 -0
  181. package/dist/index.mjs +49 -0
  182. package/dist/plugins/pinia.mjs +12 -0
  183. package/dist/plugins/pinia.mjs.map +1 -0
  184. package/dist/services/authAPI.mjs +159 -0
  185. package/dist/services/authAPI.mjs.map +1 -0
  186. package/dist/stores/useAuthStore.mjs +68 -0
  187. package/dist/stores/useAuthStore.mjs.map +1 -0
  188. package/dist/stores/useCardPreviewModeStore.mjs +20 -0
  189. package/dist/stores/useCardPreviewModeStore.mjs.map +1 -0
  190. package/dist/stores/useConfigStore.mjs +60 -0
  191. package/dist/stores/useConfigStore.mjs.map +1 -0
  192. package/dist/utils/SkldrMouseTrap.mjs +48 -0
  193. package/dist/utils/SkldrMouseTrap.mjs.map +1 -0
  194. package/dist/utils/passwordValidation.mjs +12 -0
  195. package/dist/utils/passwordValidation.mjs.map +1 -0
  196. package/package.json +8 -8
  197. package/src/admin/components/EChart.vue +59 -0
  198. package/src/admin/components/LearnerDiagnostics.vue +8 -4
  199. package/src/admin/components/LearnerTagElo.vue +563 -0
  200. package/src/admin/index.ts +1 -0
  201. package/dist/MarkdownRenderer-U_iPiA2x.mjs +0 -4966
  202. package/dist/MarkdownRenderer-U_iPiA2x.mjs.map +0 -1
  203. package/dist/assets/MarkdownRenderer.css +0 -1
  204. package/dist/common-ui.es.js +0 -5090
  205. package/dist/common-ui.es.js.map +0 -1
  206. package/dist/common-ui.umd.js +0 -77
  207. package/dist/common-ui.umd.js.map +0 -1
@@ -1,20 +1,25 @@
1
- import { Fragment as e, computed as t, createBlock as n, createCommentVNode as r, createElementBlock as i, createElementVNode as a, createTextVNode as o, createVNode as s, defineComponent as c, nextTick as l, normalizeClass as u, normalizeStyle as d, onMounted as f, openBlock as p, ref as m, renderList as h, resolveComponent as g, shallowRef as _, toDisplayString as v, unref as y, watch as b, withCtx as x, withKeys as S } from "vue";
2
- import { SESSION_FLAGS as C, cardDossiers as w, dumpFileName as T, eloLedger as E, fetchLearnerDump as D, fmtAnswer as O, fmtDelta as k, fmtDuration as A, fmtScore as j, fromDump as M, isSkillTag as N, parseLearnerDump as P, pipelineRunStats as F, recordPerformance as I, regulatorText as L, runCardSource as R, runText as ee, scoredTagDeltas as te, selectedBySource as z, servedTags as B, sessionDetail as V, sessionText as ne, shortTag as H, summarizeSessions as re } from "@vue-skuilder/db/diagnostics";
3
- import { PIPELINE_STAGES as U, planPipeline as ie } from "@vue-skuilder/db";
1
+ import { Fragment as e, computed as t, createBlock as n, createCommentVNode as r, createElementBlock as i, createElementVNode as a, createTextVNode as o, createVNode as s, defineComponent as c, nextTick as l, normalizeClass as u, normalizeStyle as d, onBeforeUnmount as f, onMounted as p, openBlock as m, ref as h, renderList as g, resolveComponent as _, shallowRef as v, toDisplayString as y, unref as b, watch as x, withCtx as S, withKeys as C } from "vue";
2
+ import { SESSION_FLAGS as w, cardDossiers as T, dumpFileName as E, eloLedger as D, fetchLearnerDump as O, fmtAnswer as k, fmtDelta as A, fmtDuration as j, fmtScore as M, fromDump as N, isSkillTag as P, matchesTagBatch as F, parseLearnerDump as I, pipelineRunStats as L, recordPerformance as R, regulatorText as z, runCardSource as B, runText as V, scoredTagDeltas as H, selectedBySource as U, servedTags as ee, sessionDetail as te, sessionText as ne, shortTag as W, summarizeSessions as re, tagEloView as ie } from "@vue-skuilder/db/diagnostics";
3
+ import { useTheme as ae } from "vuetify";
4
+ import { init as oe, use as se } from "echarts/core";
5
+ import { LineChart as ce, ScatterChart as le } from "echarts/charts";
6
+ import { DataZoomComponent as ue, GridComponent as de, LegendComponent as fe, MarkLineComponent as pe, TooltipComponent as me } from "echarts/components";
7
+ import { CanvasRenderer as he } from "echarts/renderers";
8
+ import { PIPELINE_STAGES as ge, planPipeline as _e } from "@vue-skuilder/db";
4
9
  //#region \0rolldown/runtime.js
5
- var ae = Object.defineProperty, __name = (e, t) => ae(e, "name", {
10
+ var ve = Object.defineProperty, __name = (e, t) => ve(e, "name", {
6
11
  value: t,
7
12
  configurable: !0
8
13
  });
9
14
  //#endregion
10
15
  //#region src/admin/composables/useLearnerDataset.ts
11
16
  function useLearnerDataset() {
12
- let e = _(null), t = _(null), n = m(!1), r = m(null);
17
+ let e = v(null), t = v(null), n = h(!1), r = h(null);
13
18
  async function load(i, a) {
14
19
  n.value = !0, r.value = null;
15
20
  try {
16
21
  let n = await i();
17
- t.value = M(n, a), e.value = n;
22
+ t.value = N(n, a), e.value = n;
18
23
  } catch (e) {
19
24
  r.value = e instanceof Error ? e.message : String(e);
20
25
  } finally {
@@ -22,13 +27,13 @@ function useLearnerDataset() {
22
27
  }
23
28
  }
24
29
  function loadFromCouch(e) {
25
- return load(() => D({
30
+ return load(() => O({
26
31
  ...e,
27
32
  auth: { kind: "cookie" }
28
33
  }), e.courseId);
29
34
  }
30
35
  function loadFromFile(e, t) {
31
- return load(async () => P(await e.text()), t);
36
+ return load(async () => I(await e.text()), t);
32
37
  }
33
38
  return {
34
39
  dump: e,
@@ -41,14 +46,14 @@ function useLearnerDataset() {
41
46
  }
42
47
  function downloadLearnerDump(e) {
43
48
  let t = new Blob([JSON.stringify(e, null, 2)], { type: "application/json" }), n = URL.createObjectURL(t), r = document.createElement("a");
44
- r.href = n, r.download = T(e), r.click(), URL.revokeObjectURL(n);
49
+ r.href = n, r.download = E(e), r.click(), URL.revokeObjectURL(n);
45
50
  }
46
51
  //#endregion
47
52
  //#region src/admin/components/LearnerDatasetSource.vue?vue&type=script&setup=true&lang.ts
48
- var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
53
+ var ye = { class: "d-flex flex-wrap align-center ga-2" }, be = {
49
54
  key: 1,
50
55
  class: "d-flex flex-wrap align-center ga-2 mt-3"
51
- }, ce = /* @__PURE__ */ c({
56
+ }, xe = /* @__PURE__ */ c({
52
57
  __name: "LearnerDatasetSource",
53
58
  props: {
54
59
  couchUrl: {},
@@ -58,8 +63,8 @@ var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
58
63
  },
59
64
  emits: ["loaded"],
60
65
  setup(c, { emit: l }) {
61
- let u = c, d = l, { dump: h, dataset: _, loading: C, error: w, loadFromCouch: T, loadFromFile: E } = useLearnerDataset(), D = m(u.initialUsername ?? ""), O = m(null), k = t(() => {
62
- let e = _.value?.sessions ?? [];
66
+ let u = c, d = l, { dump: f, dataset: g, loading: v, error: w, loadFromCouch: T, loadFromFile: E } = useLearnerDataset(), D = h(u.initialUsername ?? ""), O = h(null), k = t(() => {
67
+ let e = g.value?.sessions ?? [];
63
68
  return e.length ? `${e[0].startTime.slice(0, 10)} .. ${e[e.length - 1].startTime.slice(0, 10)}` : "";
64
69
  });
65
70
  function loadLive() {
@@ -73,16 +78,16 @@ var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
73
78
  let t = e.target, n = t.files?.[0];
74
79
  n && E(n, u.courseId), t.value = "";
75
80
  }
76
- return b(_, (e) => {
77
- e && h.value && d("loaded", e, h.value);
78
- }), f(() => {
81
+ return x(g, (e) => {
82
+ e && f.value && d("loaded", e, f.value);
83
+ }), p(() => {
79
84
  u.autoload && loadLive();
80
85
  }), (t, c) => {
81
- let l = g("v-text-field"), u = g("v-btn"), d = g("v-alert"), f = g("v-spacer"), m = g("v-card-text"), b = g("v-card");
82
- return p(), n(b, { variant: "outlined" }, {
83
- default: x(() => [s(m, null, {
84
- default: x(() => [
85
- a("div", oe, [
86
+ let l = _("v-text-field"), u = _("v-btn"), d = _("v-alert"), p = _("v-spacer"), h = _("v-card-text"), x = _("v-card");
87
+ return m(), n(x, { variant: "outlined" }, {
88
+ default: S(() => [s(h, null, {
89
+ default: S(() => [
90
+ a("div", ye, [
86
91
  s(l, {
87
92
  modelValue: D.value,
88
93
  "onUpdate:modelValue": c[0] || (c[0] = (e) => D.value = e),
@@ -91,15 +96,15 @@ var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
91
96
  "hide-details": "",
92
97
  style: { "max-width": "16rem" },
93
98
  disabled: !t.couchUrl || !t.courseId,
94
- onKeydown: S(loadLive, ["enter"])
99
+ onKeydown: C(loadLive, ["enter"])
95
100
  }, null, 8, ["modelValue", "disabled"]),
96
101
  s(u, {
97
102
  color: "primary",
98
- loading: y(C),
103
+ loading: b(v),
99
104
  disabled: !t.couchUrl || !t.courseId || !D.value,
100
105
  onClick: loadLive
101
106
  }, {
102
- default: x(() => c[3] || (c[3] = [o(" Load ")])),
107
+ default: S(() => c[3] || (c[3] = [o(" Load ")])),
103
108
  _: 1
104
109
  }, 8, ["loading", "disabled"]),
105
110
  c[5] || (c[5] = a("span", { class: "text-medium-emphasis mx-2" }, "or", -1)),
@@ -108,7 +113,7 @@ var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
108
113
  "prepend-icon": "mdi-file-upload-outline",
109
114
  onClick: c[1] || (c[1] = (e) => O.value?.click())
110
115
  }, {
111
- default: x(() => c[4] || (c[4] = [o(" Open dump file ")])),
116
+ default: S(() => c[4] || (c[4] = [o(" Open dump file ")])),
112
117
  _: 1
113
118
  }),
114
119
  a("input", {
@@ -120,32 +125,32 @@ var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
120
125
  onChange: onFile
121
126
  }, null, 544)
122
127
  ]),
123
- y(w) ? (p(), n(d, {
128
+ b(w) ? (m(), n(d, {
124
129
  key: 0,
125
130
  type: "error",
126
131
  variant: "tonal",
127
132
  density: "compact",
128
133
  class: "mt-3"
129
134
  }, {
130
- default: x(() => [o(v(y(w)), 1)]),
135
+ default: S(() => [o(y(b(w)), 1)]),
131
136
  _: 1
132
137
  })) : r("", !0),
133
- y(_) && y(h) ? (p(), i("div", se, [
138
+ b(g) && b(f) ? (m(), i("div", be, [
134
139
  a("span", null, [
135
- a("strong", null, v(y(_).username), 1),
136
- o(" · " + v(y(_).sessions.length) + " sessions ", 1),
137
- k.value ? (p(), i(e, { key: 0 }, [o("(" + v(k.value) + ")", 1)], 64)) : r("", !0),
138
- o(" · " + v(y(_).cardHistories.length) + " cards seen · as of " + v(y(_).asOf.slice(0, 16)) + "Z ", 1),
139
- y(_).cards ? r("", !0) : (p(), i(e, { key: 1 }, [o("· no course slice")], 64))
140
+ a("strong", null, y(b(g).username), 1),
141
+ o(" · " + y(b(g).sessions.length) + " sessions ", 1),
142
+ k.value ? (m(), i(e, { key: 0 }, [o("(" + y(k.value) + ")", 1)], 64)) : r("", !0),
143
+ o(" · " + y(b(g).cardHistories.length) + " cards seen · as of " + y(b(g).asOf.slice(0, 16)) + "Z ", 1),
144
+ b(g).cards ? r("", !0) : (m(), i(e, { key: 1 }, [o("· no course slice")], 64))
140
145
  ]),
141
- s(f),
146
+ s(p),
142
147
  s(u, {
143
148
  variant: "text",
144
149
  size: "small",
145
150
  "prepend-icon": "mdi-download",
146
- onClick: c[2] || (c[2] = (e) => y(downloadLearnerDump)(y(h)))
151
+ onClick: c[2] || (c[2] = (e) => b(downloadLearnerDump)(b(f)))
147
152
  }, {
148
- default: x(() => c[6] || (c[6] = [o(" Save dump ")])),
153
+ default: S(() => c[6] || (c[6] = [o(" Save dump ")])),
149
154
  _: 1
150
155
  })
151
156
  ])) : r("", !0)
@@ -156,7 +161,7 @@ var oe = { class: "d-flex flex-wrap align-center ga-2" }, se = {
156
161
  });
157
162
  };
158
163
  }
159
- }), W = {
164
+ }), G = {
160
165
  churned: {
161
166
  icon: "mdi-autorenew",
162
167
  color: "warning"
@@ -203,7 +208,7 @@ function shortId(e, t = 28) {
203
208
  return e.length > t ? `…${e.slice(-(t - 2))}` : e;
204
209
  }
205
210
  function useCopy() {
206
- let e = m(null), t = null;
211
+ let e = h(null), t = null;
207
212
  async function copy(n, r) {
208
213
  try {
209
214
  await navigator.clipboard.writeText(n), e.value = r, t && clearTimeout(t), t = setTimeout(() => e.value = null, 1400);
@@ -218,22 +223,22 @@ function useCopy() {
218
223
  }
219
224
  //#endregion
220
225
  //#region src/admin/components/CardDossierDetail.vue?vue&type=script&setup=true&lang.ts
221
- var G = {
226
+ var Se = {
222
227
  key: 0,
223
228
  class: "text-caption mb-2"
224
- }, le = { class: "text-medium-emphasis" }, ue = { class: "d-flex flex-wrap mb-2 ga-1" }, de = {
229
+ }, Ce = { class: "text-medium-emphasis" }, we = { class: "d-flex flex-wrap mb-2 ga-1" }, Te = {
225
230
  key: 0,
226
231
  class: "text-caption text-disabled"
227
- }, fe = { class: "text-caption text-medium-emphasis mb-2" }, pe = {
232
+ }, Ee = { class: "text-caption text-medium-emphasis mb-2" }, De = {
228
233
  key: 0,
229
234
  class: "text-error"
230
- }, me = { class: "text-no-wrap" }, he = {
235
+ }, Oe = { class: "text-no-wrap" }, ke = {
231
236
  key: 2,
232
237
  class: "text-disabled"
233
- }, ge = {
238
+ }, Ae = {
234
239
  class: "text-truncate",
235
240
  style: { "max-width": "200px" }
236
- }, _e = /* @__PURE__ */ c({
241
+ }, je = /* @__PURE__ */ c({
237
242
  __name: "CardDossierDetail",
238
243
  props: {
239
244
  dossier: {},
@@ -241,34 +246,34 @@ var G = {
241
246
  },
242
247
  setup(t) {
243
248
  function perf(e) {
244
- let t = I(e);
249
+ let t = R(e);
245
250
  return t === null ? "—" : t.toFixed(2);
246
251
  }
247
252
  function fmtInterval(e) {
248
253
  return e ? e < 3600 ? `${Math.round(e / 60)}m` : e < 86400 ? `${Math.round(e / 3600)}h` : `${Math.round(e / 86400)}d` : "none";
249
254
  }
250
255
  return (t, c) => {
251
- let l = g("v-chip"), d = g("v-icon"), f = g("v-table");
252
- return p(), i("div", null, [
253
- t.dossier.card && Object.keys(t.dossier.card.data).length ? (p(), i("div", G, [(p(!0), i(e, null, h(t.dossier.card.data, (e, t) => (p(), i("span", {
256
+ let l = _("v-chip"), d = _("v-icon"), f = _("v-table");
257
+ return m(), i("div", null, [
258
+ t.dossier.card && Object.keys(t.dossier.card.data).length ? (m(), i("div", Se, [(m(!0), i(e, null, g(t.dossier.card.data, (e, t) => (m(), i("span", {
254
259
  key: t,
255
260
  class: "mr-3"
256
- }, [a("span", le, v(t) + ":", 1), o(" " + v(y(O)(e, 60)), 1)]))), 128))])) : r("", !0),
257
- a("div", ue, [(p(!0), i(e, null, h(t.dossier.card?.tags ?? [], (e) => (p(), n(l, {
261
+ }, [a("span", Ce, y(t) + ":", 1), o(" " + y(b(k)(e, 60)), 1)]))), 128))])) : r("", !0),
262
+ a("div", we, [(m(!0), i(e, null, g(t.dossier.card?.tags ?? [], (e) => (m(), n(l, {
258
263
  key: e,
259
264
  size: "x-small",
260
265
  variant: "outlined",
261
- color: y(N)(t.interpreters, e) ? "primary" : void 0
266
+ color: b(P)(t.interpreters, e) ? "primary" : void 0
262
267
  }, {
263
- default: x(() => [o(v(e), 1)]),
268
+ default: S(() => [o(y(e), 1)]),
264
269
  _: 2
265
- }, 1032, ["color"]))), 128)), t.dossier.card ? r("", !0) : (p(), i("span", de, "no course data in this dataset"))]),
266
- a("div", fe, [o(" lapses " + v(t.dossier.lapses) + " · streak " + v(t.dossier.streak) + " · best interval " + v(fmtInterval(t.dossier.bestIntervalSeconds)) + " · ", 1), t.dossier.pendingReview ? (p(), i(e, { key: 0 }, [o(" next review " + v(y(fmtTime)(t.dossier.pendingReview.reviewTime)) + " ", 1), t.dossier.pendingReview.overdue ? (p(), i("span", pe, "(overdue)")) : r("", !0)], 64)) : (p(), i(e, { key: 1 }, [o("no review scheduled")], 64))]),
270
+ }, 1032, ["color"]))), 128)), t.dossier.card ? r("", !0) : (m(), i("span", Te, "no course data in this dataset"))]),
271
+ a("div", Ee, [o(" lapses " + y(t.dossier.lapses) + " · streak " + y(t.dossier.streak) + " · best interval " + y(fmtInterval(t.dossier.bestIntervalSeconds)) + " · ", 1), t.dossier.pendingReview ? (m(), i(e, { key: 0 }, [o(" next review " + y(b(fmtTime)(t.dossier.pendingReview.reviewTime)) + " ", 1), t.dossier.pendingReview.overdue ? (m(), i("span", De, "(overdue)")) : r("", !0)], 64)) : (m(), i(e, { key: 1 }, [o("no review scheduled")], 64))]),
267
272
  s(f, {
268
273
  density: "compact",
269
274
  class: "sk-record-table"
270
275
  }, {
271
- default: x(() => [c[2] || (c[2] = a("thead", null, [a("tr", null, [
276
+ default: S(() => [c[2] || (c[2] = a("thead", null, [a("tr", null, [
272
277
  a("th", null, "#"),
273
278
  a("th", null, "When"),
274
279
  a("th", null, "Result"),
@@ -276,31 +281,31 @@ var G = {
276
281
  a("th", null, "Prior att."),
277
282
  a("th", null, "Time"),
278
283
  a("th", null, "Answer")
279
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(t.dossier.records, (e, t) => (p(), i("tr", {
284
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(t.dossier.records, (e, t) => (m(), i("tr", {
280
285
  key: t,
281
286
  class: u(e.isCorrect === !1 ? "sk-fail-row" : "")
282
287
  }, [
283
- a("td", null, v(t + 1), 1),
284
- a("td", me, v(y(fmtTime)(e.timeStamp)), 1),
285
- a("td", null, [e.isCorrect === !0 ? (p(), n(d, {
288
+ a("td", null, y(t + 1), 1),
289
+ a("td", Oe, y(b(fmtTime)(e.timeStamp)), 1),
290
+ a("td", null, [e.isCorrect === !0 ? (m(), n(d, {
286
291
  key: 0,
287
292
  size: "small",
288
293
  color: "success"
289
294
  }, {
290
- default: x(() => c[0] || (c[0] = [o("mdi-check")])),
295
+ default: S(() => c[0] || (c[0] = [o("mdi-check")])),
291
296
  _: 1
292
- })) : e.isCorrect === !1 ? (p(), n(d, {
297
+ })) : e.isCorrect === !1 ? (m(), n(d, {
293
298
  key: 1,
294
299
  size: "small",
295
300
  color: "error"
296
301
  }, {
297
- default: x(() => c[1] || (c[1] = [o("mdi-close")])),
302
+ default: S(() => c[1] || (c[1] = [o("mdi-close")])),
298
303
  _: 1
299
- })) : (p(), i("span", he, "—"))]),
300
- a("td", null, v(perf(e)), 1),
301
- a("td", null, v(e.priorAttemps ?? "—"), 1),
302
- a("td", null, v(((e.timeSpent ?? 0) / 1e3).toFixed(1)) + "s", 1),
303
- a("td", ge, v(y(O)(e.userAnswer)), 1)
304
+ })) : (m(), i("span", ke, "—"))]),
305
+ a("td", null, y(perf(e)), 1),
306
+ a("td", null, y(e.priorAttemps ?? "—"), 1),
307
+ a("td", null, y(((e.timeSpent ?? 0) / 1e3).toFixed(1)) + "s", 1),
308
+ a("td", Ae, y(b(k)(e.userAnswer)), 1)
304
309
  ], 2))), 128))])]),
305
310
  _: 1
306
311
  })
@@ -311,13 +316,13 @@ var G = {
311
316
  let n = e.__vccOpts || e;
312
317
  for (let [e, r] of t) n[e] = r;
313
318
  return n;
314
- }, "default"), q = /* @__PURE__ */ K(_e, [["__scopeId", "data-v-76b0a622"]]), ve = { class: "text-caption text-medium-emphasis mb-4" }, ye = { class: "text-h6" }, be = { class: "text-caption" }, xe = { class: "d-flex align-center flex-wrap mb-3 ga-3" }, Se = {
319
+ }, "default"), q = /* @__PURE__ */ K(je, [["__scopeId", "data-v-76b0a622"]]), Me = { class: "text-caption text-medium-emphasis mb-4" }, Ne = { class: "text-h6" }, Pe = { class: "text-caption" }, Fe = { class: "d-flex align-center flex-wrap mb-3 ga-3" }, Ie = {
315
320
  class: "d-flex align-center flex-wrap ga-2",
316
321
  style: { width: "100%" }
317
- }, Ce = { class: "text-body-2 font-weight-medium" }, we = { class: "text-caption text-medium-emphasis" }, Te = {
322
+ }, Le = { class: "text-body-2 font-weight-medium" }, Re = { class: "text-caption text-medium-emphasis" }, ze = {
318
323
  key: 2,
319
324
  class: "text-caption"
320
- }, Ee = {
325
+ }, Be = {
321
326
  key: 0,
322
327
  class: "ml-1 text-disabled"
323
328
  }, J = /* @__PURE__ */ K(/* @__PURE__ */ c({
@@ -328,7 +333,7 @@ var G = {
328
333
  focus: {}
329
334
  },
330
335
  setup(c) {
331
- let d = c, f = t(() => w(d.dataset)), _ = m("all"), S = m(""), C = m([]), T = m(null), E = t(() => ({
336
+ let d = c, f = t(() => T(d.dataset)), p = h("all"), v = h(""), C = h([]), w = h(null), E = t(() => ({
332
337
  stuck: f.value.filter((e) => e.stuck).length,
333
338
  failed: f.value.filter((e) => e.fails > 0).length,
334
339
  frozen: f.value.filter((e) => e.frozenElo).length
@@ -350,7 +355,7 @@ var G = {
350
355
  },
351
356
  {
352
357
  label: "time on cards",
353
- value: A(f.value.reduce((e, t) => e + t.totalTimeMs, 0) / 1e3),
358
+ value: j(f.value.reduce((e, t) => e + t.totalTimeMs, 0) / 1e3),
354
359
  color: "grey"
355
360
  },
356
361
  {
@@ -365,8 +370,8 @@ var G = {
365
370
  }
366
371
  ]), O = t(() => {
367
372
  let e = f.value;
368
- _.value === "stuck" ? e = e.filter((e) => e.stuck) : _.value === "failed" ? e = e.filter((e) => e.fails > 0) : _.value === "frozen" && (e = e.filter((e) => e.frozenElo));
369
- let t = S.value?.trim().toLowerCase();
373
+ p.value === "stuck" ? e = e.filter((e) => e.stuck) : p.value === "failed" ? e = e.filter((e) => e.fails > 0) : p.value === "frozen" && (e = e.filter((e) => e.frozenElo));
374
+ let t = v.value?.trim().toLowerCase();
370
375
  return t && (e = e.filter((e) => e.cardId.toLowerCase().includes(t) || (e.card?.questionType ?? "").toLowerCase().includes(t) || (e.card?.tags ?? []).some((e) => e.toLowerCase().includes(t)) || Object.values(e.card?.data ?? {}).some((e) => typeof e == "string" && e.toLowerCase().includes(t)))), e;
371
376
  });
372
377
  function headline(e) {
@@ -374,23 +379,23 @@ var G = {
374
379
  return typeof t == "string" ? t : "";
375
380
  }
376
381
  async function applyFocus(e) {
377
- !e || !f.value.some((t) => t.cardId === e) || (_.value = "all", S.value = e, C.value = [e], await l(), document.querySelector(`[data-card="${CSS.escape(e)}"]`)?.scrollIntoView({
382
+ !e || !f.value.some((t) => t.cardId === e) || (p.value = "all", v.value = e, C.value = [e], await l(), document.querySelector(`[data-card="${CSS.escape(e)}"]`)?.scrollIntoView({
378
383
  behavior: "smooth",
379
384
  block: "center"
380
- }), T.value = e, setTimeout(() => {
381
- T.value === e && (T.value = null);
385
+ }), w.value = e, setTimeout(() => {
386
+ w.value === e && (w.value = null);
382
387
  }, 2200));
383
388
  }
384
- return b(() => d.focus, (e) => void applyFocus(e), { immediate: !0 }), (t, c) => {
385
- let l = g("v-icon"), d = g("v-card"), m = g("v-col"), b = g("v-row"), w = g("v-btn"), k = g("v-btn-toggle"), j = g("v-text-field"), M = g("v-alert"), N = g("v-spacer"), P = g("v-chip"), F = g("v-expansion-panel-title"), I = g("v-expansion-panel-text"), L = g("v-expansion-panel"), R = g("v-expansion-panels");
386
- return p(), i("div", null, [
387
- a("p", ve, [
389
+ return x(() => d.focus, (e) => void applyFocus(e), { immediate: !0 }), (t, c) => {
390
+ let l = _("v-icon"), d = _("v-card"), h = _("v-col"), x = _("v-row"), T = _("v-btn"), k = _("v-btn-toggle"), A = _("v-text-field"), M = _("v-alert"), N = _("v-spacer"), P = _("v-chip"), F = _("v-expansion-panel-title"), I = _("v-expansion-panel-text"), L = _("v-expansion-panel"), R = _("v-expansion-panels");
391
+ return m(), i("div", null, [
392
+ a("p", Me, [
388
393
  c[5] || (c[5] = o(" Every card the learner has met, most painful first (time sunk × failures), with its pending review and current card ELO. ")),
389
394
  s(l, {
390
395
  size: "x-small",
391
396
  color: "error"
392
397
  }, {
393
- default: x(() => c[3] || (c[3] = [o("mdi-sync-alert")])),
398
+ default: S(() => c[3] || (c[3] = [o("mdi-sync-alert")])),
394
399
  _: 1
395
400
  }),
396
401
  c[6] || (c[6] = o(" is a failed card holding an overdue review; ")),
@@ -398,88 +403,88 @@ var G = {
398
403
  size: "x-small",
399
404
  color: "warning"
400
405
  }, {
401
- default: x(() => c[4] || (c[4] = [o("mdi-snowflake")])),
406
+ default: S(() => c[4] || (c[4] = [o("mdi-snowflake")])),
402
407
  _: 1
403
408
  }),
404
409
  c[7] || (c[7] = o(" is a repeatedly failed card whose ELO has fewer updates than failures. "))
405
410
  ]),
406
- s(b, {
411
+ s(x, {
407
412
  dense: "",
408
413
  class: "mb-2"
409
414
  }, {
410
- default: x(() => [(p(!0), i(e, null, h(D.value, (e) => (p(), n(m, {
415
+ default: S(() => [(m(!0), i(e, null, g(D.value, (e) => (m(), n(h, {
411
416
  key: e.label,
412
417
  cols: "6",
413
418
  sm: "4",
414
419
  md: "2"
415
420
  }, {
416
- default: x(() => [s(d, {
421
+ default: S(() => [s(d, {
417
422
  variant: "tonal",
418
423
  color: e.color,
419
424
  class: "pa-2 text-center"
420
425
  }, {
421
- default: x(() => [a("div", ye, v(e.value), 1), a("div", be, v(e.label), 1)]),
426
+ default: S(() => [a("div", Ne, y(e.value), 1), a("div", Pe, y(e.label), 1)]),
422
427
  _: 2
423
428
  }, 1032, ["color"])]),
424
429
  _: 2
425
430
  }, 1024))), 128))]),
426
431
  _: 1
427
432
  }),
428
- a("div", xe, [s(k, {
429
- modelValue: _.value,
430
- "onUpdate:modelValue": c[0] || (c[0] = (e) => _.value = e),
433
+ a("div", Fe, [s(k, {
434
+ modelValue: p.value,
435
+ "onUpdate:modelValue": c[0] || (c[0] = (e) => p.value = e),
431
436
  density: "compact",
432
437
  color: "primary",
433
438
  variant: "outlined"
434
439
  }, {
435
- default: x(() => [
436
- s(w, {
440
+ default: S(() => [
441
+ s(T, {
437
442
  value: "all",
438
443
  size: "small"
439
444
  }, {
440
- default: x(() => [o("All (" + v(f.value.length) + ")", 1)]),
445
+ default: S(() => [o("All (" + y(f.value.length) + ")", 1)]),
441
446
  _: 1
442
447
  }),
443
- s(w, {
448
+ s(T, {
444
449
  value: "stuck",
445
450
  size: "small"
446
451
  }, {
447
- default: x(() => [s(l, {
452
+ default: S(() => [s(l, {
448
453
  start: "",
449
454
  size: "small",
450
455
  color: "error"
451
456
  }, {
452
- default: x(() => c[8] || (c[8] = [o("mdi-sync-alert")])),
457
+ default: S(() => c[8] || (c[8] = [o("mdi-sync-alert")])),
453
458
  _: 1
454
- }), o(" Stuck (" + v(E.value.stuck) + ") ", 1)]),
459
+ }), o(" Stuck (" + y(E.value.stuck) + ") ", 1)]),
455
460
  _: 1
456
461
  }),
457
- s(w, {
462
+ s(T, {
458
463
  value: "failed",
459
464
  size: "small"
460
465
  }, {
461
- default: x(() => [o("Ever failed (" + v(E.value.failed) + ")", 1)]),
466
+ default: S(() => [o("Ever failed (" + y(E.value.failed) + ")", 1)]),
462
467
  _: 1
463
468
  }),
464
- s(w, {
469
+ s(T, {
465
470
  value: "frozen",
466
471
  size: "small"
467
472
  }, {
468
- default: x(() => [s(l, {
473
+ default: S(() => [s(l, {
469
474
  start: "",
470
475
  size: "small",
471
476
  color: "warning"
472
477
  }, {
473
- default: x(() => c[9] || (c[9] = [o("mdi-snowflake")])),
478
+ default: S(() => c[9] || (c[9] = [o("mdi-snowflake")])),
474
479
  _: 1
475
- }), o(" Frozen ELO (" + v(E.value.frozen) + ") ", 1)]),
480
+ }), o(" Frozen ELO (" + y(E.value.frozen) + ") ", 1)]),
476
481
  _: 1
477
482
  })
478
483
  ]),
479
484
  _: 1
480
- }, 8, ["modelValue"]), s(j, {
481
- modelValue: S.value,
482
- "onUpdate:modelValue": c[1] || (c[1] = (e) => S.value = e),
485
+ }, 8, ["modelValue"]), s(A, {
486
+ modelValue: v.value,
487
+ "onUpdate:modelValue": c[1] || (c[1] = (e) => v.value = e),
483
488
  density: "compact",
484
489
  variant: "outlined",
485
490
  "hide-details": "",
@@ -488,64 +493,64 @@ var G = {
488
493
  "prepend-inner-icon": "mdi-magnify",
489
494
  style: { "max-width": "320px" }
490
495
  }, null, 8, ["modelValue"])]),
491
- f.value.length === 0 ? (p(), n(M, {
496
+ f.value.length === 0 ? (m(), n(M, {
492
497
  key: 0,
493
498
  type: "info",
494
499
  variant: "tonal"
495
500
  }, {
496
- default: x(() => c[10] || (c[10] = [o("No card history for this learner.")])),
501
+ default: S(() => c[10] || (c[10] = [o("No card history for this learner.")])),
497
502
  _: 1
498
- })) : (p(), n(R, {
503
+ })) : (m(), n(R, {
499
504
  key: 1,
500
505
  modelValue: C.value,
501
506
  "onUpdate:modelValue": c[2] || (c[2] = (e) => C.value = e),
502
507
  multiple: "",
503
508
  variant: "accordion"
504
509
  }, {
505
- default: x(() => [(p(!0), i(e, null, h(O.value, (e) => (p(), n(L, {
510
+ default: S(() => [(m(!0), i(e, null, g(O.value, (e) => (m(), n(L, {
506
511
  key: e.cardId,
507
512
  value: e.cardId,
508
513
  "data-card": e.cardId,
509
- class: u(e.cardId === T.value ? "sk-card-flash" : "")
514
+ class: u(e.cardId === w.value ? "sk-card-flash" : "")
510
515
  }, {
511
- default: x(() => [s(F, null, {
512
- default: x(() => [a("div", Se, [
513
- e.stuck ? (p(), n(l, {
516
+ default: S(() => [s(F, null, {
517
+ default: S(() => [a("div", Ie, [
518
+ e.stuck ? (m(), n(l, {
514
519
  key: 0,
515
520
  color: "error",
516
521
  size: "small",
517
522
  title: "failed + overdue review"
518
523
  }, {
519
- default: x(() => c[11] || (c[11] = [o("mdi-sync-alert")])),
524
+ default: S(() => c[11] || (c[11] = [o("mdi-sync-alert")])),
520
525
  _: 1
521
526
  })) : r("", !0),
522
- e.frozenElo ? (p(), n(l, {
527
+ e.frozenElo ? (m(), n(l, {
523
528
  key: 1,
524
529
  color: "warning",
525
530
  size: "small",
526
531
  title: "repeatedly failed, ELO barely updated"
527
532
  }, {
528
- default: x(() => c[12] || (c[12] = [o(" mdi-snowflake ")])),
533
+ default: S(() => c[12] || (c[12] = [o(" mdi-snowflake ")])),
529
534
  _: 1
530
535
  })) : r("", !0),
531
- a("span", Ce, v(e.card?.questionType ?? "card"), 1),
532
- a("code", we, v(y(shortId)(e.cardId, 24)), 1),
533
- headline(e) ? (p(), i("span", Te, v(headline(e)), 1)) : r("", !0),
536
+ a("span", Le, y(e.card?.questionType ?? "card"), 1),
537
+ a("code", Re, y(b(shortId)(e.cardId, 24)), 1),
538
+ headline(e) ? (m(), i("span", ze, y(headline(e)), 1)) : r("", !0),
534
539
  s(N),
535
- e.fails > 0 ? (p(), n(P, {
540
+ e.fails > 0 ? (m(), n(P, {
536
541
  key: 3,
537
542
  size: "x-small",
538
543
  color: "error",
539
544
  variant: "tonal"
540
545
  }, {
541
- default: x(() => [o(v(e.fails) + " fail" + v(e.fails === 1 ? "" : "s"), 1)]),
546
+ default: S(() => [o(y(e.fails) + " fail" + y(e.fails === 1 ? "" : "s"), 1)]),
542
547
  _: 2
543
548
  }, 1024)) : r("", !0),
544
549
  s(P, {
545
550
  size: "x-small",
546
551
  variant: "tonal"
547
552
  }, {
548
- default: x(() => [o(v(e.attempts) + " view" + v(e.attempts === 1 ? "" : "s"), 1)]),
553
+ default: S(() => [o(y(e.attempts) + " view" + y(e.attempts === 1 ? "" : "s"), 1)]),
549
554
  _: 2
550
555
  }, 1024),
551
556
  s(P, {
@@ -553,16 +558,16 @@ var G = {
553
558
  variant: "tonal",
554
559
  color: "grey"
555
560
  }, {
556
- default: x(() => [o(v(y(A)(e.totalTimeMs / 1e3)), 1)]),
561
+ default: S(() => [o(y(b(j)(e.totalTimeMs / 1e3)), 1)]),
557
562
  _: 2
558
563
  }, 1024),
559
- e.pendingReview ? (p(), n(P, {
564
+ e.pendingReview ? (m(), n(P, {
560
565
  key: 4,
561
566
  size: "x-small",
562
567
  color: e.pendingReview.overdue ? "error" : "success",
563
568
  variant: "flat"
564
569
  }, {
565
- default: x(() => [o(" review " + v(e.pendingReview.overdue ? "overdue" : "scheduled"), 1)]),
570
+ default: S(() => [o(" review " + y(e.pendingReview.overdue ? "overdue" : "scheduled"), 1)]),
566
571
  _: 2
567
572
  }, 1032, ["color"])) : r("", !0),
568
573
  s(P, {
@@ -570,13 +575,13 @@ var G = {
570
575
  variant: "tonal",
571
576
  color: e.frozenElo ? "warning" : void 0
572
577
  }, {
573
- default: x(() => [o(" ELO " + v(e.cardElo === null ? "?" : Math.round(e.cardElo)) + " ", 1), e.cardEloCount === null ? r("", !0) : (p(), i("span", Ee, "/" + v(e.cardEloCount), 1))]),
578
+ default: S(() => [o(" ELO " + y(e.cardElo === null ? "?" : Math.round(e.cardElo)) + " ", 1), e.cardEloCount === null ? r("", !0) : (m(), i("span", Be, "/" + y(e.cardEloCount), 1))]),
574
579
  _: 2
575
580
  }, 1032, ["color"])
576
581
  ])]),
577
582
  _: 2
578
583
  }, 1024), s(I, null, {
579
- default: x(() => [s(q, {
584
+ default: S(() => [s(q, {
580
585
  dossier: e,
581
586
  interpreters: t.interpreters
582
587
  }, null, 8, ["dossier", "interpreters"])]),
@@ -593,39 +598,39 @@ var G = {
593
598
  ]);
594
599
  };
595
600
  }
596
- }), [["__scopeId", "data-v-bb6b302b"]]), De = { class: "sk-run-detail" }, Oe = {
601
+ }), [["__scopeId", "data-v-bb6b302b"]]), Ve = { class: "sk-run-detail" }, He = {
597
602
  key: 0,
598
603
  class: "mb-2"
599
- }, ke = { class: "text-right" }, Ae = { class: "text-right" }, je = { class: "text-right" }, Me = { class: "text-right" }, Ne = {
604
+ }, Ue = { class: "text-right" }, We = { class: "text-right" }, Ge = { class: "text-right" }, Ke = { class: "text-right" }, qe = {
600
605
  key: 1,
601
606
  class: "mb-2"
602
- }, Pe = { class: "text-right" }, Fe = { class: "text-right" }, Ie = { class: "text-right" }, Le = {
607
+ }, Je = { class: "text-right" }, Ye = { class: "text-right" }, Xe = { class: "text-right" }, Ze = {
603
608
  key: 2,
604
609
  class: "mb-2 sk-mini-line text-medium-emphasis"
605
- }, Re = {
610
+ }, Qe = {
606
611
  key: 3,
607
612
  class: "mb-2"
608
- }, ze = {
613
+ }, $e = {
609
614
  key: 4,
610
615
  class: "mb-2"
611
- }, Be = { class: "text-caption font-weight-medium" }, Ve = {
616
+ }, et = { class: "text-caption font-weight-medium" }, tt = {
612
617
  key: 0,
613
618
  class: "text-medium-emphasis font-weight-regular"
614
- }, He = {
619
+ }, nt = {
615
620
  key: 1,
616
621
  title: "runner-up"
617
- }, Ue = ["onClick"], We = { class: "text-right" }, Ge = { class: "text-caption font-weight-medium" }, Ke = ["onClick"], qe = { class: "text-medium-emphasis" }, Je = { class: "text-no-wrap" }, Ye = { class: "text-no-wrap" }, Xe = { class: "text-right text-no-wrap" }, Ze = { class: "text-caption" }, Qe = {
622
+ }, rt = ["onClick"], it = { class: "text-right" }, at = { class: "text-caption font-weight-medium" }, ot = ["onClick"], st = { class: "text-medium-emphasis" }, ct = { class: "text-no-wrap" }, lt = { class: "text-no-wrap" }, ut = { class: "text-right text-no-wrap" }, dt = { class: "text-caption" }, ft = {
618
623
  key: 5,
619
624
  class: "mb-2"
620
- }, $e = { class: "sk-hint-block" }, et = {
625
+ }, pt = { class: "sk-hint-block" }, mt = {
621
626
  key: 6,
622
627
  class: "text-caption text-medium-emphasis"
623
- }, tt = { key: 2 }, Y = /* @__PURE__ */ K(/* @__PURE__ */ c({
628
+ }, ht = { key: 2 }, Y = /* @__PURE__ */ K(/* @__PURE__ */ c({
624
629
  __name: "RunDetail",
625
630
  props: { run: {} },
626
631
  emits: ["open-card"],
627
632
  setup(c, { emit: l }) {
628
- let d = c, f = l, m = t(() => {
633
+ let d = c, f = l, p = t(() => {
629
634
  let e = d.run.unselectedNew, t = [];
630
635
  return e?.nextInLine && t.push({
631
636
  label: "next new card in line",
@@ -634,135 +639,135 @@ var G = {
634
639
  label: "top-generated new card (sunk)",
635
640
  card: e.topGenerated
636
641
  }), t;
637
- }), _ = t(() => z(d.run).map((e) => `${e.source} ${e.count}`).join(" · "));
642
+ }), h = t(() => U(d.run).map((e) => `${e.source} ${e.count}`).join(" · "));
638
643
  return (t, c) => {
639
- let l = g("v-table"), d = g("v-icon");
640
- return p(), i("div", De, [
641
- t.run.generators?.length ? (p(), i("div", Oe, [c[1] || (c[1] = a("div", { class: "text-caption font-weight-medium" }, "generators", -1)), s(l, {
644
+ let l = _("v-table"), d = _("v-icon");
645
+ return m(), i("div", Ve, [
646
+ t.run.generators?.length ? (m(), i("div", He, [c[1] || (c[1] = a("div", { class: "text-caption font-weight-medium" }, "generators", -1)), s(l, {
642
647
  density: "compact",
643
648
  class: "sk-mini-table"
644
649
  }, {
645
- default: x(() => [c[0] || (c[0] = a("thead", null, [a("tr", null, [
650
+ default: S(() => [c[0] || (c[0] = a("thead", null, [a("tr", null, [
646
651
  a("th"),
647
652
  a("th", { class: "text-right" }, "cards"),
648
653
  a("th", { class: "text-right" }, "new"),
649
654
  a("th", { class: "text-right" }, "review"),
650
655
  a("th", { class: "text-right" }, "top")
651
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(t.run.generators, (e) => (p(), i("tr", { key: e.name }, [
652
- a("td", null, v(e.name), 1),
653
- a("td", ke, v(e.cardCount), 1),
654
- a("td", Ae, v(e.newCount), 1),
655
- a("td", je, v(e.reviewCount), 1),
656
- a("td", Me, v(e.topScore.toFixed(2)), 1)
656
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(t.run.generators, (e) => (m(), i("tr", { key: e.name }, [
657
+ a("td", null, y(e.name), 1),
658
+ a("td", Ue, y(e.cardCount), 1),
659
+ a("td", We, y(e.newCount), 1),
660
+ a("td", Ge, y(e.reviewCount), 1),
661
+ a("td", Ke, y(e.topScore.toFixed(2)), 1)
657
662
  ]))), 128))])]),
658
663
  _: 1
659
664
  })])) : r("", !0),
660
- t.run.filters?.length ? (p(), i("div", Ne, [c[3] || (c[3] = a("div", { class: "text-caption font-weight-medium" }, "filters", -1)), s(l, {
665
+ t.run.filters?.length ? (m(), i("div", qe, [c[3] || (c[3] = a("div", { class: "text-caption font-weight-medium" }, "filters", -1)), s(l, {
661
666
  density: "compact",
662
667
  class: "sk-mini-table"
663
668
  }, {
664
- default: x(() => [c[2] || (c[2] = a("thead", null, [a("tr", null, [
669
+ default: S(() => [c[2] || (c[2] = a("thead", null, [a("tr", null, [
665
670
  a("th"),
666
671
  a("th", null, "kind"),
667
672
  a("th", { class: "text-right" }, "boosted"),
668
673
  a("th", { class: "text-right" }, "penalized"),
669
674
  a("th", { class: "text-right" }, "passed"),
670
675
  a("th", { class: "text-right" }, "removed")
671
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(t.run.filters, (e) => (p(), i("tr", { key: e.name }, [
672
- a("td", null, v(e.name), 1),
673
- a("td", null, v(e.kind ?? "—"), 1),
674
- a("td", Pe, v(e.boosted), 1),
675
- a("td", Fe, v(e.penalized), 1),
676
- a("td", Ie, v(e.passed), 1),
677
- a("td", { class: u(["text-right", e.removed > 0 ? "text-error" : ""]) }, v(e.removed), 3)
676
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(t.run.filters, (e) => (m(), i("tr", { key: e.name }, [
677
+ a("td", null, y(e.name), 1),
678
+ a("td", null, y(e.kind ?? "—"), 1),
679
+ a("td", Je, y(e.boosted), 1),
680
+ a("td", Ye, y(e.penalized), 1),
681
+ a("td", Xe, y(e.passed), 1),
682
+ a("td", { class: u(["text-right", e.removed > 0 ? "text-error" : ""]) }, y(e.removed), 3)
678
683
  ]))), 128))])]),
679
684
  _: 1
680
685
  })])) : r("", !0),
681
- t.run.versions ? (p(), i("div", Le, " strategies " + v(t.run.versions.strategies ?? "—") + " · content " + v(t.run.versions.content ?? "—"), 1)) : r("", !0),
682
- t.run.regulators?.length ? (p(), i("div", Re, [c[4] || (c[4] = a("div", { class: "text-caption font-weight-medium" }, "regulators", -1)), (p(!0), i(e, null, h(t.run.regulators, (e) => (p(), i("div", {
686
+ t.run.versions ? (m(), i("div", Ze, " strategies " + y(t.run.versions.strategies ?? "—") + " · content " + y(t.run.versions.content ?? "—"), 1)) : r("", !0),
687
+ t.run.regulators?.length ? (m(), i("div", Qe, [c[4] || (c[4] = a("div", { class: "text-caption font-weight-medium" }, "regulators", -1)), (m(!0), i(e, null, g(t.run.regulators, (e) => (m(), i("div", {
683
688
  key: e.name,
684
689
  class: "sk-mini-line"
685
- }, [a("span", { class: u(e.multiplier > 1 ? "text-warning" : "text-medium-emphasis") }, " ×" + v(e.multiplier.toFixed(2)), 3), o(" " + v(y(L)(e)), 1)]))), 128))])) : r("", !0),
686
- t.run.cards?.length ? (p(), i("div", ze, [a("div", Be, [c[5] || (c[5] = o(" selection ")), _.value ? (p(), i("span", Ve, " · by source: " + v(_.value), 1)) : r("", !0)]), s(l, {
690
+ }, [a("span", { class: u(e.multiplier > 1 ? "text-warning" : "text-medium-emphasis") }, " ×" + y(e.multiplier.toFixed(2)), 3), o(" " + y(b(z)(e)), 1)]))), 128))])) : r("", !0),
691
+ t.run.cards?.length ? (m(), i("div", $e, [a("div", et, [c[5] || (c[5] = o(" selection ")), h.value ? (m(), i("span", tt, " · by source: " + y(h.value), 1)) : r("", !0)]), s(l, {
687
692
  density: "compact",
688
693
  class: "sk-mini-table"
689
694
  }, {
690
- default: x(() => [c[7] || (c[7] = a("thead", null, [a("tr", null, [
695
+ default: S(() => [c[7] || (c[7] = a("thead", null, [a("tr", null, [
691
696
  a("th"),
692
697
  a("th", null, "card"),
693
698
  a("th", null, "origin"),
694
699
  a("th", null, "source"),
695
700
  a("th", { class: "text-right" }, "score")
696
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(t.run.cards, (e) => (p(), i("tr", {
701
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(t.run.cards, (e) => (m(), i("tr", {
697
702
  key: e.cardId,
698
703
  class: u(e.selected ? "" : "text-medium-emphasis")
699
704
  }, [
700
- a("td", null, [e.selected ? (p(), n(d, {
705
+ a("td", null, [e.selected ? (m(), n(d, {
701
706
  key: 0,
702
707
  size: "x-small",
703
708
  color: "success"
704
709
  }, {
705
- default: x(() => c[6] || (c[6] = [o("mdi-check")])),
710
+ default: S(() => c[6] || (c[6] = [o("mdi-check")])),
706
711
  _: 1
707
- })) : (p(), i("span", He, "·"))]),
712
+ })) : (m(), i("span", nt, "·"))]),
708
713
  a("td", null, [a("a", {
709
714
  class: "sk-card-link",
710
715
  onClick: (t) => f("open-card", e.cardId)
711
- }, v(e.cardId), 9, Ue)]),
712
- a("td", null, v(e.origin), 1),
713
- a("td", null, v(y(R)(e)), 1),
714
- a("td", We, v(y(j)(e.score)), 1)
716
+ }, y(e.cardId), 9, rt)]),
717
+ a("td", null, y(e.origin), 1),
718
+ a("td", null, y(b(B)(e)), 1),
719
+ a("td", it, y(b(M)(e.score)), 1)
715
720
  ], 2))), 128))])]),
716
721
  _: 1
717
722
  })])) : r("", !0),
718
- (p(!0), i(e, null, h(m.value, (t) => (p(), i("div", {
723
+ (m(!0), i(e, null, g(p.value, (t) => (m(), i("div", {
719
724
  key: t.label,
720
725
  class: "mb-2"
721
- }, [a("div", Ge, [
722
- o(v(t.label) + ": ", 1),
726
+ }, [a("div", at, [
727
+ o(y(t.label) + ": ", 1),
723
728
  a("a", {
724
729
  class: "sk-card-link",
725
730
  onClick: (e) => f("open-card", t.card.cardId)
726
- }, v(t.card.cardId), 9, Ke),
727
- a("span", qe, " (" + v(t.card.origin) + ", " + v(y(R)(t.card)) + ") final " + v(y(j)(t.card.score)), 1)
731
+ }, y(t.card.cardId), 9, ot),
732
+ a("span", st, " (" + y(t.card.origin) + ", " + y(b(B)(t.card)) + ") final " + y(b(M)(t.card.score)), 1)
728
733
  ]), s(l, {
729
734
  density: "compact",
730
735
  class: "sk-mini-table"
731
736
  }, {
732
- default: x(() => [a("tbody", null, [(p(!0), i(e, null, h(t.card.trail, (e, t) => (p(), i("tr", { key: t }, [
733
- a("td", Je, v(e.action), 1),
734
- a("td", Ye, v(e.strategyName), 1),
735
- a("td", Xe, v(y(j)(e.score)), 1),
736
- a("td", Ze, v(e.reason), 1)
737
+ default: S(() => [a("tbody", null, [(m(!0), i(e, null, g(t.card.trail, (e, t) => (m(), i("tr", { key: t }, [
738
+ a("td", ct, y(e.action), 1),
739
+ a("td", lt, y(e.strategyName), 1),
740
+ a("td", ut, y(b(M)(e.score)), 1),
741
+ a("td", dt, y(e.reason), 1)
737
742
  ]))), 128))])]),
738
743
  _: 2
739
744
  }, 1024)]))), 128)),
740
- t.run.hints ? (p(), i("div", Qe, [c[8] || (c[8] = a("div", { class: "text-caption font-weight-medium" }, "hints", -1)), a("pre", $e, v(JSON.stringify(t.run.hints, null, 2)), 1)])) : r("", !0),
741
- t.run.discardedTail ? (p(), i("div", et, [
742
- o(" discarded tail: " + v(t.run.discardedTail.count) + " cards ", 1),
743
- t.run.discardedTail.scoreRange ? (p(), i(e, { key: 0 }, [o(" · score [" + v(t.run.discardedTail.scoreRange[0].toFixed(2)) + ", " + v(t.run.discardedTail.scoreRange[1].toFixed(2)) + "] ", 1)], 64)) : r("", !0),
744
- t.run.discardedTail.eloRange ? (p(), i(e, { key: 1 }, [o(" · ELO [" + v(Math.round(t.run.discardedTail.eloRange[0])) + ", " + v(Math.round(t.run.discardedTail.eloRange[1])) + "] ", 1)], 64)) : r("", !0),
745
- t.run.discardedTail.note ? (p(), i("div", tt, v(t.run.discardedTail.note), 1)) : r("", !0)
745
+ t.run.hints ? (m(), i("div", ft, [c[8] || (c[8] = a("div", { class: "text-caption font-weight-medium" }, "hints", -1)), a("pre", pt, y(JSON.stringify(t.run.hints, null, 2)), 1)])) : r("", !0),
746
+ t.run.discardedTail ? (m(), i("div", mt, [
747
+ o(" discarded tail: " + y(t.run.discardedTail.count) + " cards ", 1),
748
+ t.run.discardedTail.scoreRange ? (m(), i(e, { key: 0 }, [o(" · score [" + y(t.run.discardedTail.scoreRange[0].toFixed(2)) + ", " + y(t.run.discardedTail.scoreRange[1].toFixed(2)) + "] ", 1)], 64)) : r("", !0),
749
+ t.run.discardedTail.eloRange ? (m(), i(e, { key: 1 }, [o(" · ELO [" + y(Math.round(t.run.discardedTail.eloRange[0])) + ", " + y(Math.round(t.run.discardedTail.eloRange[1])) + "] ", 1)], 64)) : r("", !0),
750
+ t.run.discardedTail.note ? (m(), i("div", ht, y(t.run.discardedTail.note), 1)) : r("", !0)
746
751
  ])) : r("", !0)
747
752
  ]);
748
753
  };
749
754
  }
750
- }), [["__scopeId", "data-v-90c88783"]]), nt = { class: "d-flex align-center flex-wrap mb-4 ga-2" }, rt = { class: "text-caption text-medium-emphasis" }, it = { class: "text-right" }, at = { class: "text-right" }, ot = {
755
+ }), [["__scopeId", "data-v-90c88783"]]), gt = { class: "d-flex align-center flex-wrap mb-4 ga-2" }, _t = { class: "text-caption text-medium-emphasis" }, vt = { class: "text-right" }, yt = { class: "text-right" }, bt = {
751
756
  key: 1,
752
757
  class: "text-caption text-disabled"
753
- }, st = { class: "sk-hint-block" }, ct = { class: "sk-hint-block" }, lt = { class: "text-caption text-medium-emphasis mb-4" }, ut = { class: "text-right" }, dt = { class: "text-right" }, ft = { class: "text-disabled" }, pt = { class: "text-right" }, mt = { class: "d-flex flex-wrap ga-5" }, ht = { class: "text-caption text-medium-emphasis" }, gt = { class: "text-h6 text-success" }, _t = { class: "text-caption text-medium-emphasis" }, vt = { class: "text-h6 text-error" }, yt = { class: "text-h6" }, bt = { class: "text-caption text-disabled" }, xt = { class: "d-flex align-center flex-wrap mb-2 ga-3" }, St = {
758
+ }, xt = { class: "sk-hint-block" }, St = { class: "sk-hint-block" }, Ct = { class: "text-caption text-medium-emphasis mb-4" }, wt = { class: "text-right" }, Tt = { class: "text-right" }, Et = { class: "text-disabled" }, Dt = { class: "text-right" }, Ot = { class: "d-flex flex-wrap ga-5" }, kt = { class: "text-caption text-medium-emphasis" }, At = { class: "text-h6 text-success" }, jt = { class: "text-caption text-medium-emphasis" }, Mt = { class: "text-h6 text-error" }, Nt = { class: "text-h6" }, Pt = { class: "text-caption text-disabled" }, Ft = { class: "d-flex align-center flex-wrap mb-2 ga-3" }, It = {
754
759
  key: 4,
755
760
  class: "sk-timeline"
756
- }, Ct = { class: "sk-tl-time text-caption text-disabled" }, wt = { class: "sk-tl-gutter" }, Tt = {
761
+ }, Lt = { class: "sk-tl-time text-caption text-disabled" }, Rt = { class: "sk-tl-gutter" }, zt = {
757
762
  key: 0,
758
763
  class: "sk-tl-body"
759
- }, Et = { class: "d-flex align-center flex-wrap ga-1" }, Dt = { class: "font-weight-medium" }, Ot = { class: "text-caption text-medium-emphasis ml-2" }, kt = {
764
+ }, Bt = { class: "d-flex align-center flex-wrap ga-1" }, Vt = { class: "font-weight-medium" }, Ht = { class: "text-caption text-medium-emphasis ml-2" }, Ut = {
760
765
  key: 1,
761
766
  class: "text-caption text-error ml-2"
762
- }, At = {
767
+ }, Wt = {
763
768
  key: 1,
764
769
  class: "sk-tl-body"
765
- }, jt = ["title", "onClick"], Mt = { class: "text-caption" }, Nt = { class: "text-caption text-medium-emphasis ml-2" }, Pt = {
770
+ }, Gt = ["title", "onClick"], Kt = { class: "text-caption" }, qt = { class: "text-caption text-medium-emphasis ml-2" }, Jt = {
766
771
  key: 0,
767
772
  class: "text-caption text-disabled ml-2"
768
773
  }, X = /* @__PURE__ */ K(/* @__PURE__ */ c({
@@ -774,29 +779,29 @@ var G = {
774
779
  },
775
780
  emits: ["open-card"],
776
781
  setup(c, { emit: l }) {
777
- let d = c, f = l, _ = t(() => V(d.dataset, d.sessionId, d.interpreters)), b = t(() => _.value.summary.doc), S = t(() => B(_.value?.timeline ?? [], d.interpreters)), w = t(() => E(_.value?.timeline ?? [])), T = t(() => _.value?.timeline.filter((e) => e.kind === "response").length ?? 0), D = m("all"), j = t(() => {
778
- let e = _.value?.timeline ?? [];
779
- return !D.value || D.value === "all" ? e : e.filter((e) => e.kind === D.value);
780
- }), M = m(/* @__PURE__ */ new Set());
782
+ let d = c, f = l, p = t(() => te(d.dataset, d.sessionId, d.interpreters)), v = t(() => p.value.summary.doc), x = t(() => ee(p.value?.timeline ?? [], d.interpreters)), C = t(() => D(p.value?.timeline ?? [])), T = t(() => p.value?.timeline.filter((e) => e.kind === "response").length ?? 0), E = h("all"), O = t(() => {
783
+ let e = p.value?.timeline ?? [];
784
+ return !E.value || E.value === "all" ? e : e.filter((e) => e.kind === E.value);
785
+ }), M = h(/* @__PURE__ */ new Set());
781
786
  function toggle(e) {
782
787
  let t = new Set(M.value);
783
788
  t.has(e) ? t.delete(e) : t.add(e), M.value = t;
784
789
  }
785
- let { copied: P, copy: F } = useCopy();
790
+ let { copied: N, copy: F } = useCopy();
786
791
  function asText() {
787
- return _.value ? ne(d.dataset.username, _.value, {
788
- servedTags: S.value,
789
- eloLedger: w.value
792
+ return p.value ? ne(d.dataset.username, p.value, {
793
+ servedTags: x.value,
794
+ eloLedger: C.value
790
795
  }, d.interpreters) : "";
791
796
  }
792
797
  let I = t(() => {
793
- let e = _.value?.summary;
798
+ let e = p.value?.summary;
794
799
  if (!e) return "";
795
- let t = A(e.doc.plannedSeconds);
796
- return e.durationSeconds === null ? `— of ${t}` : `${A(e.durationSeconds)} of ${t}`;
800
+ let t = j(e.doc.plannedSeconds);
801
+ return e.durationSeconds === null ? `— of ${t}` : `${j(e.durationSeconds)} of ${t}`;
797
802
  });
798
803
  function skillTags(e) {
799
- return e.filter((e) => N(d.interpreters, e)).slice(0, 3);
804
+ return e.filter((e) => P(d.interpreters, e)).slice(0, 3);
800
805
  }
801
806
  function fmtNum(e) {
802
807
  return e === null ? "—" : Number.isInteger(e) ? String(e) : e.toFixed(1);
@@ -814,22 +819,22 @@ var G = {
814
819
  return e.kind === "run" ? "sk-tl-run" : e.isCorrect === !1 ? "sk-tl-fail" : "";
815
820
  }
816
821
  return (t, c) => {
817
- let l = g("v-alert"), d = g("v-chip"), m = g("v-icon"), E = g("v-spacer"), A = g("v-btn"), L = g("v-table"), R = g("v-card"), z = g("v-col"), B = g("v-row"), V = g("v-btn-toggle");
818
- return p(), i("div", null, [_.value ? (p(), i(e, { key: 1 }, [
819
- a("div", nt, [
822
+ let l = _("v-alert"), d = _("v-chip"), h = _("v-icon"), D = _("v-spacer"), j = _("v-btn"), L = _("v-table"), R = _("v-card"), z = _("v-col"), B = _("v-row"), U = _("v-btn-toggle");
823
+ return m(), i("div", null, [p.value ? (m(), i(e, { key: 1 }, [
824
+ a("div", gt, [
820
825
  s(d, {
821
826
  size: "small",
822
827
  variant: "flat",
823
- color: y(statusColor)(b.value.status)
828
+ color: b(statusColor)(v.value.status)
824
829
  }, {
825
- default: x(() => [o(v(b.value.status), 1)]),
830
+ default: S(() => [o(y(v.value.status), 1)]),
826
831
  _: 1
827
832
  }, 8, ["color"]),
828
833
  s(d, {
829
834
  size: "small",
830
835
  variant: "tonal"
831
836
  }, {
832
- default: x(() => [o(v(y(fmtTime)(b.value.startTime)), 1)]),
837
+ default: S(() => [o(y(b(fmtTime)(v.value.startTime)), 1)]),
833
838
  _: 1
834
839
  }),
835
840
  s(d, {
@@ -837,78 +842,78 @@ var G = {
837
842
  variant: "tonal",
838
843
  color: "grey"
839
844
  }, {
840
- default: x(() => [o(v(I.value), 1)]),
845
+ default: S(() => [o(y(I.value), 1)]),
841
846
  _: 1
842
847
  }),
843
- (p(!0), i(e, null, h(_.value.summary.flags, (e) => (p(), n(d, {
848
+ (m(!0), i(e, null, g(p.value.summary.flags, (e) => (m(), n(d, {
844
849
  key: e,
845
850
  size: "small",
846
851
  variant: "tonal",
847
- color: y(W)[e].color,
848
- title: y(C)[e].help
852
+ color: b(G)[e].color,
853
+ title: b(w)[e].help
849
854
  }, {
850
- default: x(() => [s(m, {
855
+ default: S(() => [s(h, {
851
856
  start: "",
852
857
  size: "small"
853
858
  }, {
854
- default: x(() => [o(v(y(W)[e].icon), 1)]),
859
+ default: S(() => [o(y(b(G)[e].icon), 1)]),
855
860
  _: 2
856
- }, 1024), o(" " + v(y(C)[e].label), 1)]),
861
+ }, 1024), o(" " + y(b(w)[e].label), 1)]),
857
862
  _: 2
858
863
  }, 1032, ["color", "title"]))), 128)),
859
- s(E),
860
- a("code", rt, v(t.sessionId), 1),
861
- s(A, {
864
+ s(D),
865
+ a("code", _t, y(t.sessionId), 1),
866
+ s(j, {
862
867
  variant: "text",
863
868
  size: "small",
864
- "prepend-icon": y(P) === "session" ? "mdi-check" : "mdi-clipboard-text-outline",
865
- color: y(P) === "session" ? "success" : void 0,
866
- onClick: c[0] || (c[0] = (e) => y(F)(asText(), "session"))
869
+ "prepend-icon": b(N) === "session" ? "mdi-check" : "mdi-clipboard-text-outline",
870
+ color: b(N) === "session" ? "success" : void 0,
871
+ onClick: c[0] || (c[0] = (e) => b(F)(asText(), "session"))
867
872
  }, {
868
- default: x(() => [o(v(y(P) === "session" ? "Copied" : "Copy as text"), 1)]),
873
+ default: S(() => [o(y(b(N) === "session" ? "Copied" : "Copy as text"), 1)]),
869
874
  _: 1
870
875
  }, 8, ["prepend-icon", "color"])
871
876
  ]),
872
- _.value.responsesMissing ? (p(), n(l, {
877
+ p.value.responsesMissing ? (m(), n(l, {
873
878
  key: 0,
874
879
  type: "warning",
875
880
  variant: "tonal",
876
881
  density: "compact",
877
882
  class: "mb-4"
878
883
  }, {
879
- default: x(() => [o(" The session records " + v(b.value.tally?.responses) + " responses but only " + v(T.value) + " card records carry its id. The timeline is incomplete. ", 1)]),
884
+ default: S(() => [o(" The session records " + y(v.value.tally?.responses) + " responses but only " + y(T.value) + " card records carry its id. The timeline is incomplete. ", 1)]),
880
885
  _: 1
881
886
  })) : r("", !0),
882
887
  s(B, { class: "mb-2" }, {
883
- default: x(() => [s(z, {
888
+ default: S(() => [s(z, {
884
889
  cols: "12",
885
890
  md: "6"
886
891
  }, {
887
- default: x(() => [s(R, {
892
+ default: S(() => [s(R, {
888
893
  variant: "outlined",
889
894
  class: "pa-3 h-100"
890
895
  }, {
891
- default: x(() => [
896
+ default: S(() => [
892
897
  c[4] || (c[4] = a("div", { class: "text-subtitle-2 mb-1" }, "Learner state", -1)),
893
898
  c[5] || (c[5] = a("div", { class: "text-caption text-medium-emphasis mb-3" }, " What the navigator was choosing against, and what moved. ", -1)),
894
- _.value.summary.state.length ? (p(), n(L, {
899
+ p.value.summary.state.length ? (m(), n(L, {
895
900
  key: 0,
896
901
  density: "compact",
897
902
  class: "sk-mini-table"
898
903
  }, {
899
- default: x(() => [c[3] || (c[3] = a("thead", null, [a("tr", null, [
904
+ default: S(() => [c[3] || (c[3] = a("thead", null, [a("tr", null, [
900
905
  a("th"),
901
906
  a("th", { class: "text-right" }, "Start"),
902
907
  a("th", { class: "text-right" }, "End"),
903
908
  a("th", { class: "text-right" }, "Δ")
904
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(_.value.summary.state, (e) => (p(), i("tr", { key: e.label }, [
905
- a("td", null, v(e.label), 1),
906
- a("td", it, v(fmtNum(e.from)), 1),
907
- a("td", at, v(fmtNum(e.to)), 1),
908
- a("td", { class: u(["text-right", y(deltaClass)(e.delta)]) }, v(y(k)(e.delta)), 3)
909
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(p.value.summary.state, (e) => (m(), i("tr", { key: e.label }, [
910
+ a("td", null, y(e.label), 1),
911
+ a("td", vt, y(fmtNum(e.from)), 1),
912
+ a("td", yt, y(fmtNum(e.to)), 1),
913
+ a("td", { class: u(["text-right", b(deltaClass)(e.delta)]) }, y(b(A)(e.delta)), 3)
909
914
  ]))), 128))])]),
910
915
  _: 1
911
- })) : (p(), i("div", ot, "No state snapshot recorded."))
916
+ })) : (m(), i("div", bt, "No state snapshot recorded."))
912
917
  ]),
913
918
  _: 1
914
919
  })]),
@@ -917,17 +922,17 @@ var G = {
917
922
  cols: "12",
918
923
  md: "6"
919
924
  }, {
920
- default: x(() => [s(R, {
925
+ default: S(() => [s(R, {
921
926
  variant: "outlined",
922
927
  class: "pa-3 h-100"
923
928
  }, {
924
- default: x(() => [
929
+ default: S(() => [
925
930
  c[6] || (c[6] = a("div", { class: "text-subtitle-2 mb-1" }, "Session hints", -1)),
926
931
  c[7] || (c[7] = a("div", { class: "text-caption text-medium-emphasis mb-3" }, " What outcome observers told the navigator. They act only through these. ", -1)),
927
932
  c[8] || (c[8] = a("span", { class: "text-caption font-weight-medium" }, "at open", -1)),
928
- a("pre", st, v(fmtHints(b.value.config?.initHints)), 1),
933
+ a("pre", xt, y(fmtHints(v.value.config?.initHints)), 1),
929
934
  c[9] || (c[9] = a("span", { class: "text-caption font-weight-medium" }, "at close", -1)),
930
- a("pre", ct, v(fmtHints(b.value.finalHints)), 1)
935
+ a("pre", St, y(fmtHints(v.value.finalHints)), 1)
931
936
  ]),
932
937
  _: 1
933
938
  })]),
@@ -935,216 +940,216 @@ var G = {
935
940
  })]),
936
941
  _: 1
937
942
  }),
938
- a("div", lt, [
939
- o(" batch limit " + v(b.value.config?.defaultBatchLimit ?? "?") + " · " + v(b.value.config?.sourceCount ?? "?") + " source(s) · opening queues supply " + v(b.value.initialQueues?.supplyQ ?? "?") + " / failed " + v(b.value.initialQueues?.failedQ ?? "?") + " ", 1),
940
- b.value.tally ? (p(), i(e, { key: 0 }, [o(" · ended with " + v(b.value.tally.failedQRemaining) + " still in the failed queue", 1)], 64)) : r("", !0),
941
- b.value.versions ? (p(), i(e, { key: 1 }, [o(" · framework " + v(b.value.versions.framework), 1), b.value.versions.app ? (p(), i(e, { key: 0 }, [o(" · app " + v(b.value.versions.app), 1)], 64)) : r("", !0)], 64)) : r("", !0)
943
+ a("div", Ct, [
944
+ o(" batch limit " + y(v.value.config?.defaultBatchLimit ?? "?") + " · " + y(v.value.config?.sourceCount ?? "?") + " source(s) · opening queues supply " + y(v.value.initialQueues?.supplyQ ?? "?") + " / failed " + y(v.value.initialQueues?.failedQ ?? "?") + " ", 1),
945
+ v.value.tally ? (m(), i(e, { key: 0 }, [o(" · ended with " + y(v.value.tally.failedQRemaining) + " still in the failed queue", 1)], 64)) : r("", !0),
946
+ v.value.versions ? (m(), i(e, { key: 1 }, [o(" · framework " + y(v.value.versions.framework), 1), v.value.versions.app ? (m(), i(e, { key: 0 }, [o(" · app " + y(v.value.versions.app), 1)], 64)) : r("", !0)], 64)) : r("", !0)
942
947
  ]),
943
- S.value.length ? (p(), n(R, {
948
+ x.value.length ? (m(), n(R, {
944
949
  key: 1,
945
950
  variant: "outlined",
946
951
  class: "pa-3 mb-4"
947
952
  }, {
948
- default: x(() => [
953
+ default: S(() => [
949
954
  c[11] || (c[11] = a("div", { class: "text-subtitle-2 mb-1" }, "Served tags", -1)),
950
955
  c[12] || (c[12] = a("div", { class: "text-caption text-medium-emphasis mb-2" }, " What this sitting put in front of the learner, by content tag. A response with several tags counts toward each. ", -1)),
951
956
  s(L, {
952
957
  density: "compact",
953
958
  class: "sk-mini-table"
954
959
  }, {
955
- default: x(() => [c[10] || (c[10] = a("thead", null, [a("tr", null, [
960
+ default: S(() => [c[10] || (c[10] = a("thead", null, [a("tr", null, [
956
961
  a("th", null, "Tag"),
957
962
  a("th", { class: "text-right" }, "Resp."),
958
963
  a("th", { class: "text-right" }, "Cards"),
959
964
  a("th", { class: "text-right" }, "Accuracy"),
960
965
  a("th", { class: "text-right" }, "Time")
961
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(S.value, (n) => (p(), i("tr", { key: n.tag }, [
962
- a("td", null, [a("code", { class: u(y(N)(t.interpreters, n.tag) ? "text-primary" : "") }, v(n.tag), 3)]),
963
- a("td", ut, v(n.responses), 1),
964
- a("td", dt, v(n.cards), 1),
965
- a("td", { class: u(["text-right", y(accuracyClass)(n.accuracy)]) }, [n.accuracy === null ? (p(), i(e, { key: 0 }, [o("—")], 64)) : (p(), i(e, { key: 1 }, [o(v(Math.round(n.accuracy * 100)) + "% ", 1), a("span", ft, "(" + v(n.correct) + "/" + v(n.correct + n.incorrect) + ")", 1)], 64))], 2),
966
- a("td", pt, v((n.totalTimeMs / 1e3).toFixed(1)) + "s", 1)
966
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(x.value, (n) => (m(), i("tr", { key: n.tag }, [
967
+ a("td", null, [a("code", { class: u(b(P)(t.interpreters, n.tag) ? "text-primary" : "") }, y(n.tag), 3)]),
968
+ a("td", wt, y(n.responses), 1),
969
+ a("td", Tt, y(n.cards), 1),
970
+ a("td", { class: u(["text-right", b(accuracyClass)(n.accuracy)]) }, [n.accuracy === null ? (m(), i(e, { key: 0 }, [o("—")], 64)) : (m(), i(e, { key: 1 }, [o(y(Math.round(n.accuracy * 100)) + "% ", 1), a("span", Et, "(" + y(n.correct) + "/" + y(n.correct + n.incorrect) + ")", 1)], 64))], 2),
971
+ a("td", Dt, y((n.totalTimeMs / 1e3).toFixed(1)) + "s", 1)
967
972
  ]))), 128))])]),
968
973
  _: 1
969
974
  })
970
975
  ]),
971
976
  _: 1
972
977
  })) : r("", !0),
973
- w.value ? (p(), n(R, {
978
+ C.value ? (m(), n(R, {
974
979
  key: 2,
975
980
  variant: "outlined",
976
981
  class: "pa-3 mb-4"
977
982
  }, {
978
- default: x(() => [
983
+ default: S(() => [
979
984
  c[15] || (c[15] = a("div", { class: "text-subtitle-2 mb-1" }, "ELO ledger", -1)),
980
985
  c[16] || (c[16] = a("div", { class: "text-caption text-medium-emphasis mb-3" }, " The per-response learner global-ELO exchanges that net to the session's ELO move. Wins above the learner's level pay little; losses below it cost a lot, so a high hit rate can still net negative. ", -1)),
981
- a("div", mt, [
982
- a("div", null, [c[13] || (c[13] = a("div", { class: "text-caption text-medium-emphasis" }, "net", -1)), a("div", { class: u(["text-h6", y(deltaClass)(w.value.net)]) }, v(y(k)(w.value.net)), 3)]),
983
- a("div", null, [a("div", ht, "gained · " + v(w.value.wins) + " win(s)", 1), a("div", gt, v(y(k)(w.value.gained)), 1)]),
984
- a("div", null, [a("div", _t, "lost · " + v(w.value.losses) + " loss(es)", 1), a("div", vt, v(y(k)(w.value.lost)), 1)]),
986
+ a("div", Ot, [
987
+ a("div", null, [c[13] || (c[13] = a("div", { class: "text-caption text-medium-emphasis" }, "net", -1)), a("div", { class: u(["text-h6", b(deltaClass)(C.value.net)]) }, y(b(A)(C.value.net)), 3)]),
988
+ a("div", null, [a("div", kt, "gained · " + y(C.value.wins) + " win(s)", 1), a("div", At, y(b(A)(C.value.gained)), 1)]),
989
+ a("div", null, [a("div", jt, "lost · " + y(C.value.losses) + " loss(es)", 1), a("div", Mt, y(b(A)(C.value.lost)), 1)]),
985
990
  a("div", null, [
986
991
  c[14] || (c[14] = a("div", { class: "text-caption text-medium-emphasis" }, "exchanges", -1)),
987
- a("div", yt, v(w.value.count), 1),
988
- a("div", bt, "of " + v(T.value) + " response(s)", 1)
992
+ a("div", Nt, y(C.value.count), 1),
993
+ a("div", Pt, "of " + y(T.value) + " response(s)", 1)
989
994
  ])
990
995
  ])
991
996
  ]),
992
997
  _: 1
993
998
  })) : r("", !0),
994
- a("div", xt, [c[17] || (c[17] = a("h2", { class: "text-h6" }, "Timeline", -1)), s(V, {
995
- modelValue: D.value,
996
- "onUpdate:modelValue": c[1] || (c[1] = (e) => D.value = e),
999
+ a("div", Ft, [c[17] || (c[17] = a("h2", { class: "text-h6" }, "Timeline", -1)), s(U, {
1000
+ modelValue: E.value,
1001
+ "onUpdate:modelValue": c[1] || (c[1] = (e) => E.value = e),
997
1002
  density: "compact",
998
1003
  color: "primary",
999
1004
  variant: "outlined"
1000
1005
  }, {
1001
- default: x(() => [
1002
- s(A, {
1006
+ default: S(() => [
1007
+ s(j, {
1003
1008
  value: "all",
1004
1009
  size: "small"
1005
1010
  }, {
1006
- default: x(() => [o("All (" + v(_.value.timeline.length) + ")", 1)]),
1011
+ default: S(() => [o("All (" + y(p.value.timeline.length) + ")", 1)]),
1007
1012
  _: 1
1008
1013
  }),
1009
- s(A, {
1014
+ s(j, {
1010
1015
  value: "response",
1011
1016
  size: "small"
1012
1017
  }, {
1013
- default: x(() => [o("Responses (" + v(T.value) + ")", 1)]),
1018
+ default: S(() => [o("Responses (" + y(T.value) + ")", 1)]),
1014
1019
  _: 1
1015
1020
  }),
1016
- s(A, {
1021
+ s(j, {
1017
1022
  value: "run",
1018
1023
  size: "small"
1019
1024
  }, {
1020
- default: x(() => [o("Runs (" + v(_.value.timeline.length - T.value) + ")", 1)]),
1025
+ default: S(() => [o("Runs (" + y(p.value.timeline.length - T.value) + ")", 1)]),
1021
1026
  _: 1
1022
1027
  })
1023
1028
  ]),
1024
1029
  _: 1
1025
1030
  }, 8, ["modelValue"])]),
1026
- _.value.timeline.length === 0 ? (p(), n(l, {
1031
+ p.value.timeline.length === 0 ? (m(), n(l, {
1027
1032
  key: 3,
1028
1033
  type: "info",
1029
1034
  variant: "tonal"
1030
1035
  }, {
1031
- default: x(() => c[18] || (c[18] = [o("Nothing recorded for this session.")])),
1036
+ default: S(() => c[18] || (c[18] = [o("Nothing recorded for this session.")])),
1032
1037
  _: 1
1033
- })) : (p(), i("div", St, [(p(!0), i(e, null, h(j.value, (l, g) => (p(), i("div", {
1034
- key: g,
1038
+ })) : (m(), i("div", It, [(m(!0), i(e, null, g(O.value, (l, p) => (m(), i("div", {
1039
+ key: p,
1035
1040
  class: u(["sk-tl-row", rowClass(l)])
1036
1041
  }, [
1037
- a("div", Ct, v(y(fmtClock)(l.at)), 1),
1038
- a("div", wt, [s(m, {
1042
+ a("div", Lt, y(b(fmtClock)(l.at)), 1),
1043
+ a("div", Rt, [s(h, {
1039
1044
  size: "small",
1040
1045
  color: entryColor(l)
1041
1046
  }, {
1042
- default: x(() => [o(v(entryIcon(l)), 1)]),
1047
+ default: S(() => [o(y(entryIcon(l)), 1)]),
1043
1048
  _: 2
1044
1049
  }, 1032, ["color"])]),
1045
- l.kind === "run" ? (p(), i("div", Tt, [a("div", Et, [
1046
- a("span", Dt, v(l.run.label), 1),
1047
- l.run.mode ? (p(), n(d, {
1050
+ l.kind === "run" ? (m(), i("div", zt, [a("div", Bt, [
1051
+ a("span", Vt, y(l.run.label), 1),
1052
+ l.run.mode ? (m(), n(d, {
1048
1053
  key: 0,
1049
1054
  size: "x-small",
1050
1055
  variant: "tonal"
1051
1056
  }, {
1052
- default: x(() => [o(v(l.run.mode), 1)]),
1057
+ default: S(() => [o(y(l.run.mode), 1)]),
1053
1058
  _: 2
1054
1059
  }, 1024)) : r("", !0),
1055
- a("span", Ot, " generated " + v(l.run.generatedCount) + " → selected " + v(l.run.finalCount) + " (" + v(l.run.newSelected) + " new, " + v(l.run.reviewsSelected) + " review) ", 1),
1056
- l.run.generatedCount > 0 && l.run.finalCount === 0 ? (p(), i("span", kt, " nothing survived ")) : r("", !0),
1057
- typeof l.run.userElo == "number" ? (p(), n(d, {
1060
+ a("span", Ht, " generated " + y(l.run.generatedCount) + " → selected " + y(l.run.finalCount) + " (" + y(l.run.newSelected) + " new, " + y(l.run.reviewsSelected) + " review) ", 1),
1061
+ l.run.generatedCount > 0 && l.run.finalCount === 0 ? (m(), i("span", Ut, " nothing survived ")) : r("", !0),
1062
+ typeof l.run.userElo == "number" ? (m(), n(d, {
1058
1063
  key: 2,
1059
1064
  size: "x-small",
1060
1065
  variant: "tonal",
1061
1066
  color: "grey",
1062
1067
  class: "ml-2"
1063
1068
  }, {
1064
- default: x(() => [o(" ELO " + v(Math.round(l.run.userElo)), 1)]),
1069
+ default: S(() => [o(" ELO " + y(Math.round(l.run.userElo)), 1)]),
1065
1070
  _: 2
1066
1071
  }, 1024)) : r("", !0),
1067
- s(E),
1068
- s(A, {
1072
+ s(D),
1073
+ s(j, {
1069
1074
  icon: M.value.has(l.run.runId) ? "mdi-chevron-up" : "mdi-chevron-down",
1070
1075
  size: "x-small",
1071
1076
  variant: "text",
1072
1077
  onClick: (e) => toggle(l.run.runId)
1073
1078
  }, null, 8, ["icon", "onClick"]),
1074
- s(A, {
1075
- icon: y(P) === l.run.runId ? "mdi-check" : "mdi-content-copy",
1079
+ s(j, {
1080
+ icon: b(N) === l.run.runId ? "mdi-check" : "mdi-content-copy",
1076
1081
  size: "x-small",
1077
1082
  variant: "text",
1078
- color: y(P) === l.run.runId ? "success" : void 0,
1083
+ color: b(N) === l.run.runId ? "success" : void 0,
1079
1084
  title: "Copy run as text",
1080
- onClick: (e) => y(F)(y(ee)(l.run), l.run.runId)
1085
+ onClick: (e) => b(F)(b(V)(l.run), l.run.runId)
1081
1086
  }, null, 8, [
1082
1087
  "icon",
1083
1088
  "color",
1084
1089
  "onClick"
1085
1090
  ])
1086
- ]), M.value.has(l.run.runId) ? (p(), n(Y, {
1091
+ ]), M.value.has(l.run.runId) ? (m(), n(Y, {
1087
1092
  key: 0,
1088
1093
  run: l.run,
1089
1094
  class: "mt-1",
1090
1095
  onOpenCard: c[2] || (c[2] = (e) => f("open-card", e))
1091
- }, null, 8, ["run"])) : r("", !0)])) : (p(), i("div", At, [
1096
+ }, null, 8, ["run"])) : r("", !0)])) : (m(), i("div", Wt, [
1092
1097
  a("a", {
1093
1098
  class: "sk-card-link",
1094
1099
  title: `Open ${l.cardId} in card history`,
1095
1100
  onClick: (e) => f("open-card", l.cardId)
1096
- }, [o(v(l.questionType ?? "card") + " ", 1), a("code", Mt, v(y(shortId)(l.cardId)), 1)], 8, jt),
1097
- (p(!0), i(e, null, h(skillTags(l.tags), (e) => (p(), n(d, {
1101
+ }, [o(y(l.questionType ?? "card") + " ", 1), a("code", Kt, y(b(shortId)(l.cardId)), 1)], 8, Gt),
1102
+ (m(!0), i(e, null, g(skillTags(l.tags), (e) => (m(), n(d, {
1098
1103
  key: e,
1099
1104
  size: "x-small",
1100
1105
  variant: "outlined",
1101
1106
  color: "primary",
1102
1107
  class: "ml-1"
1103
1108
  }, {
1104
- default: x(() => [o(v(y(H)(t.interpreters, e)), 1)]),
1109
+ default: S(() => [o(y(b(W)(t.interpreters, e)), 1)]),
1105
1110
  _: 2
1106
1111
  }, 1024))), 128)),
1107
- a("span", Nt, [o(v((l.timeSpentMs / 1e3).toFixed(1)) + "s ", 1), l.priorAttempts ? (p(), i(e, { key: 0 }, [o(" · attempt " + v(l.priorAttempts + 1), 1)], 64)) : r("", !0)]),
1108
- l.userAnswer == null ? r("", !0) : (p(), i("span", Pt, "“" + v(y(O)(l.userAnswer)) + "”", 1)),
1109
- l.elo ? (p(), i(e, { key: 1 }, [s(d, {
1112
+ a("span", qt, [o(y((l.timeSpentMs / 1e3).toFixed(1)) + "s ", 1), l.priorAttempts ? (m(), i(e, { key: 0 }, [o(" · attempt " + y(l.priorAttempts + 1), 1)], 64)) : r("", !0)]),
1113
+ l.userAnswer == null ? r("", !0) : (m(), i("span", Jt, "“" + y(b(k)(l.userAnswer)) + "”", 1)),
1114
+ l.elo ? (m(), i(e, { key: 1 }, [s(d, {
1110
1115
  size: "x-small",
1111
1116
  variant: "tonal",
1112
- color: y(deltaColor)(l.elo.global.delta),
1117
+ color: b(deltaColor)(l.elo.global.delta),
1113
1118
  class: "ml-2",
1114
1119
  title: `learner global ELO ${l.elo.global.before} → ${l.elo.global.after} · userScore ${l.elo.userScore.toFixed(2)}`
1115
1120
  }, {
1116
- default: x(() => [o(" ELO " + v(y(k)(l.elo.global.delta)), 1)]),
1121
+ default: S(() => [o(" ELO " + y(b(A)(l.elo.global.delta)), 1)]),
1117
1122
  _: 2
1118
- }, 1032, ["color", "title"]), (p(!0), i(e, null, h(y(te)(l.elo), (e) => (p(), n(d, {
1123
+ }, 1032, ["color", "title"]), (m(!0), i(e, null, g(b(H)(l.elo), (e) => (m(), n(d, {
1119
1124
  key: e.tag,
1120
1125
  size: "x-small",
1121
1126
  variant: "text",
1122
- color: y(deltaColor)(e.delta),
1127
+ color: b(deltaColor)(e.delta),
1123
1128
  class: "sk-elo-tag",
1124
1129
  title: `${e.tag}: ${e.before} → ${e.after} (score ${e.score?.toFixed(2)})`
1125
1130
  }, {
1126
- default: x(() => [o(v(y(H)(t.interpreters, e.tag)) + " " + v(y(k)(e.delta)), 1)]),
1131
+ default: S(() => [o(y(b(W)(t.interpreters, e.tag)) + " " + y(b(A)(e.delta)), 1)]),
1127
1132
  _: 2
1128
1133
  }, 1032, ["color", "title"]))), 128))], 64)) : r("", !0)
1129
1134
  ]))
1130
1135
  ], 2))), 128))]))
1131
- ], 64)) : (p(), n(l, {
1136
+ ], 64)) : (m(), n(l, {
1132
1137
  key: 0,
1133
1138
  type: "info",
1134
1139
  variant: "tonal"
1135
1140
  }, {
1136
- default: x(() => [o("No session with id " + v(t.sessionId) + ".", 1)]),
1141
+ default: S(() => [o("No session with id " + y(t.sessionId) + ".", 1)]),
1137
1142
  _: 1
1138
1143
  }))]);
1139
1144
  };
1140
1145
  }
1141
- }), [["__scopeId", "data-v-3cc6eb88"]]), Ft = { class: "text-h6" }, It = { class: "text-caption" }, Lt = { class: "d-flex align-center flex-wrap mb-3 ga-3" }, Rt = ["onClick"], zt = { class: "text-no-wrap" }, Bt = { class: "text-right" }, Vt = { class: "text-right" }, Ht = {
1146
+ }), [["__scopeId", "data-v-3cc6eb88"]]), Yt = { class: "text-h6" }, Xt = { class: "text-caption" }, Zt = { class: "d-flex align-center flex-wrap mb-3 ga-3" }, Qt = ["onClick"], $t = { class: "text-no-wrap" }, en = { class: "text-right" }, tn = { class: "text-right" }, nn = {
1142
1147
  key: 1,
1143
1148
  class: "text-disabled"
1144
- }, Ut = { class: "text-right" }, Wt = { class: "text-no-wrap text-caption" }, Gt = { class: "text-no-wrap text-caption" }, Kt = { key: 0 }, qt = {
1149
+ }, rn = { class: "text-right" }, an = { class: "text-no-wrap text-caption" }, on = { class: "text-no-wrap text-caption" }, sn = { key: 0 }, cn = {
1145
1150
  key: 0,
1146
1151
  class: "text-disabled"
1147
- }, Jt = { class: "text-right" }, Z = /* @__PURE__ */ K(/* @__PURE__ */ c({
1152
+ }, ln = { class: "text-right" }, Z = /* @__PURE__ */ K(/* @__PURE__ */ c({
1148
1153
  __name: "LearnerSessionList",
1149
1154
  props: {
1150
1155
  dataset: {},
@@ -1152,15 +1157,15 @@ var G = {
1152
1157
  },
1153
1158
  emits: ["open"],
1154
1159
  setup(c, { emit: l }) {
1155
- let d = c, f = l, _ = t(() => re(d.dataset, d.interpreters)), b = m("all"), S = t(() => {
1160
+ let d = c, f = l, p = t(() => re(d.dataset, d.interpreters)), v = h("all"), x = t(() => {
1156
1161
  let e = /* @__PURE__ */ new Map();
1157
- for (let t of _.value) for (let n of t.flags) e.set(n, (e.get(n) ?? 0) + 1);
1162
+ for (let t of p.value) for (let n of t.flags) e.set(n, (e.get(n) ?? 0) + 1);
1158
1163
  return [...e.entries()].map(([e, t]) => ({
1159
1164
  flag: e,
1160
1165
  count: t
1161
1166
  })).sort((e, t) => t.count - e.count);
1162
- }), w = t(() => !b.value || b.value === "all" ? _.value : _.value.filter((e) => e.flags.includes(b.value))), T = t(() => {
1163
- let e = _.value, t = e.filter((e) => e.doc.status === "closed").length, n = e.reduce((e, t) => e + (t.doc.tally?.responses ?? 0), 0), r = e.reduce((e, t) => e + (t.doc.tally?.correct ?? 0), 0), i = e.reduce((e, t) => e + (t.durationSeconds ?? 0), 0);
1167
+ }), C = t(() => !v.value || v.value === "all" ? p.value : p.value.filter((e) => e.flags.includes(v.value))), T = t(() => {
1168
+ let e = p.value, t = e.filter((e) => e.doc.status === "closed").length, n = e.reduce((e, t) => e + (t.doc.tally?.responses ?? 0), 0), r = e.reduce((e, t) => e + (t.doc.tally?.correct ?? 0), 0), i = e.reduce((e, t) => e + (t.durationSeconds ?? 0), 0);
1164
1169
  return [
1165
1170
  {
1166
1171
  label: "sessions",
@@ -1189,7 +1194,7 @@ var G = {
1189
1194
  },
1190
1195
  {
1191
1196
  label: "time studied",
1192
- value: A(i),
1197
+ value: j(i),
1193
1198
  color: "grey"
1194
1199
  }
1195
1200
  ];
@@ -1210,83 +1215,83 @@ var G = {
1210
1215
  return t;
1211
1216
  }
1212
1217
  function clockText(e) {
1213
- let t = A(e.doc.plannedSeconds);
1214
- return e.durationSeconds === null ? `— of ${t}` : `${A(e.durationSeconds)} of ${t}`;
1218
+ let t = j(e.doc.plannedSeconds);
1219
+ return e.durationSeconds === null ? `— of ${t}` : `${j(e.durationSeconds)} of ${t}`;
1215
1220
  }
1216
1221
  return (t, c) => {
1217
- let l = g("v-card"), d = g("v-col"), m = g("v-row"), E = g("v-btn"), D = g("v-icon"), O = g("v-btn-toggle"), A = g("v-alert"), j = g("v-chip"), M = g("v-table");
1218
- return p(), i("div", null, [
1222
+ let l = _("v-card"), d = _("v-col"), h = _("v-row"), E = _("v-btn"), D = _("v-icon"), O = _("v-btn-toggle"), k = _("v-alert"), j = _("v-chip"), M = _("v-table");
1223
+ return m(), i("div", null, [
1219
1224
  c[4] || (c[4] = a("p", { class: "text-caption text-medium-emphasis mb-4" }, [
1220
1225
  o(" One row per sitting. Flags name a specific way the session failed to do its job; open one to read its interleaved timeline of responses and pipeline runs. "),
1221
1226
  a("strong", null, "Δ"),
1222
1227
  o(" is movement across the session: ELO, then any progress metrics the course declares. ")
1223
1228
  ], -1)),
1224
- s(m, {
1229
+ s(h, {
1225
1230
  dense: "",
1226
1231
  class: "mb-2"
1227
1232
  }, {
1228
- default: x(() => [(p(!0), i(e, null, h(T.value, (e) => (p(), n(d, {
1233
+ default: S(() => [(m(!0), i(e, null, g(T.value, (e) => (m(), n(d, {
1229
1234
  key: e.label,
1230
1235
  cols: "6",
1231
1236
  sm: "4",
1232
1237
  md: "2"
1233
1238
  }, {
1234
- default: x(() => [s(l, {
1239
+ default: S(() => [s(l, {
1235
1240
  variant: "tonal",
1236
1241
  color: e.color,
1237
1242
  class: "pa-2 text-center"
1238
1243
  }, {
1239
- default: x(() => [a("div", Ft, v(e.value), 1), a("div", It, v(e.label), 1)]),
1244
+ default: S(() => [a("div", Yt, y(e.value), 1), a("div", Xt, y(e.label), 1)]),
1240
1245
  _: 2
1241
1246
  }, 1032, ["color"])]),
1242
1247
  _: 2
1243
1248
  }, 1024))), 128))]),
1244
1249
  _: 1
1245
1250
  }),
1246
- a("div", Lt, [s(O, {
1247
- modelValue: b.value,
1248
- "onUpdate:modelValue": c[0] || (c[0] = (e) => b.value = e),
1251
+ a("div", Zt, [s(O, {
1252
+ modelValue: v.value,
1253
+ "onUpdate:modelValue": c[0] || (c[0] = (e) => v.value = e),
1249
1254
  density: "compact",
1250
1255
  color: "primary",
1251
1256
  variant: "outlined"
1252
1257
  }, {
1253
- default: x(() => [s(E, {
1258
+ default: S(() => [s(E, {
1254
1259
  value: "all",
1255
1260
  size: "small"
1256
1261
  }, {
1257
- default: x(() => [o("All (" + v(_.value.length) + ")", 1)]),
1262
+ default: S(() => [o("All (" + y(p.value.length) + ")", 1)]),
1258
1263
  _: 1
1259
- }), (p(!0), i(e, null, h(S.value, (e) => (p(), n(E, {
1264
+ }), (m(!0), i(e, null, g(x.value, (e) => (m(), n(E, {
1260
1265
  key: e.flag,
1261
1266
  value: e.flag,
1262
1267
  size: "small",
1263
- title: y(C)[e.flag].help
1268
+ title: b(w)[e.flag].help
1264
1269
  }, {
1265
- default: x(() => [s(D, {
1270
+ default: S(() => [s(D, {
1266
1271
  start: "",
1267
1272
  size: "small",
1268
- color: y(W)[e.flag].color
1273
+ color: b(G)[e.flag].color
1269
1274
  }, {
1270
- default: x(() => [o(v(y(W)[e.flag].icon), 1)]),
1275
+ default: S(() => [o(y(b(G)[e.flag].icon), 1)]),
1271
1276
  _: 2
1272
- }, 1032, ["color"]), o(" " + v(y(C)[e.flag].label) + " (" + v(e.count) + ") ", 1)]),
1277
+ }, 1032, ["color"]), o(" " + y(b(w)[e.flag].label) + " (" + y(e.count) + ") ", 1)]),
1273
1278
  _: 2
1274
1279
  }, 1032, ["value", "title"]))), 128))]),
1275
1280
  _: 1
1276
1281
  }, 8, ["modelValue"])]),
1277
- _.value.length === 0 ? (p(), n(A, {
1282
+ p.value.length === 0 ? (m(), n(k, {
1278
1283
  key: 0,
1279
1284
  type: "info",
1280
1285
  variant: "tonal"
1281
1286
  }, {
1282
- default: x(() => c[1] || (c[1] = [o(" No study sessions recorded. Session records began with a framework release; there is no backfill, so earlier activity shows only in card history. ")])),
1287
+ default: S(() => c[1] || (c[1] = [o(" No study sessions recorded. Session records began with a framework release; there is no backfill, so earlier activity shows only in card history. ")])),
1283
1288
  _: 1
1284
- })) : (p(), n(M, {
1289
+ })) : (m(), n(M, {
1285
1290
  key: 1,
1286
1291
  density: "compact",
1287
1292
  class: "sk-admin-table"
1288
1293
  }, {
1289
- default: x(() => [c[3] || (c[3] = a("thead", null, [a("tr", null, [
1294
+ default: S(() => [c[3] || (c[3] = a("thead", null, [a("tr", null, [
1290
1295
  a("th", null, "Started"),
1291
1296
  a("th", null, "Status"),
1292
1297
  a("th", { class: "text-right" }, "Cards"),
@@ -1296,109 +1301,697 @@ var G = {
1296
1301
  a("th", null, "Δ"),
1297
1302
  a("th", null, "Flags"),
1298
1303
  a("th")
1299
- ])], -1)), a("tbody", null, [(p(!0), i(e, null, h(w.value, (t) => (p(), i("tr", {
1304
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(C.value, (t) => (m(), i("tr", {
1300
1305
  key: t.doc.sessionId,
1301
1306
  class: "sk-admin-row",
1302
1307
  onClick: (e) => f("open", t.doc.sessionId)
1303
1308
  }, [
1304
- a("td", zt, v(y(fmtTime)(t.doc.startTime)), 1),
1309
+ a("td", $t, y(b(fmtTime)(t.doc.startTime)), 1),
1305
1310
  a("td", null, [s(j, {
1306
1311
  size: "x-small",
1307
1312
  variant: "flat",
1308
- color: y(statusColor)(t.doc.status)
1313
+ color: b(statusColor)(t.doc.status)
1309
1314
  }, {
1310
- default: x(() => [o(v(t.doc.status), 1)]),
1315
+ default: S(() => [o(y(t.doc.status), 1)]),
1311
1316
  _: 2
1312
1317
  }, 1032, ["color"])]),
1313
- a("td", Bt, v(t.doc.tally?.cardsPresented ?? "—"), 1),
1314
- a("td", Vt, [t.accuracy === null ? (p(), i("span", Ht, "—")) : (p(), i("span", {
1318
+ a("td", en, y(t.doc.tally?.cardsPresented ?? "—"), 1),
1319
+ a("td", tn, [t.accuracy === null ? (m(), i("span", nn, "—")) : (m(), i("span", {
1315
1320
  key: 0,
1316
- class: u(y(accuracyClass)(t.accuracy))
1317
- }, v(Math.round(t.accuracy * 100)) + "% ", 3))]),
1318
- a("td", Ut, v(t.doc.runs?.length ?? 0), 1),
1319
- a("td", Wt, v(clockText(t)), 1),
1320
- a("td", Gt, [(p(!0), i(e, null, h(deltas(t), (t, n) => (p(), i(e, { key: t.label }, [n > 0 ? (p(), i("span", Kt, " · ")) : r("", !0), a("span", { class: u(y(deltaClass)(t.delta)) }, v(y(k)(t.delta)) + "\xA0" + v(t.label), 3)], 64))), 128)), deltas(t).length === 0 ? (p(), i("span", qt, "—")) : r("", !0)]),
1321
- a("td", null, [(p(!0), i(e, null, h(t.flags, (e) => (p(), n(D, {
1321
+ class: u(b(accuracyClass)(t.accuracy))
1322
+ }, y(Math.round(t.accuracy * 100)) + "% ", 3))]),
1323
+ a("td", rn, y(t.doc.runs?.length ?? 0), 1),
1324
+ a("td", an, y(clockText(t)), 1),
1325
+ a("td", on, [(m(!0), i(e, null, g(deltas(t), (t, n) => (m(), i(e, { key: t.label }, [n > 0 ? (m(), i("span", sn, " · ")) : r("", !0), a("span", { class: u(b(deltaClass)(t.delta)) }, y(b(A)(t.delta)) + "\xA0" + y(t.label), 3)], 64))), 128)), deltas(t).length === 0 ? (m(), i("span", cn, "—")) : r("", !0)]),
1326
+ a("td", null, [(m(!0), i(e, null, g(t.flags, (e) => (m(), n(D, {
1322
1327
  key: e,
1323
1328
  size: "small",
1324
1329
  class: "mr-1",
1325
- color: y(W)[e].color,
1326
- title: `${y(C)[e].label}: ${y(C)[e].help}`
1330
+ color: b(G)[e].color,
1331
+ title: `${b(w)[e].label}: ${b(w)[e].help}`
1327
1332
  }, {
1328
- default: x(() => [o(v(y(W)[e].icon), 1)]),
1333
+ default: S(() => [o(y(b(G)[e].icon), 1)]),
1329
1334
  _: 2
1330
1335
  }, 1032, ["color", "title"]))), 128))]),
1331
- a("td", Jt, [s(D, {
1336
+ a("td", ln, [s(D, {
1332
1337
  size: "small",
1333
1338
  class: "text-disabled"
1334
1339
  }, {
1335
- default: x(() => c[2] || (c[2] = [o("mdi-chevron-right")])),
1340
+ default: S(() => c[2] || (c[2] = [o("mdi-chevron-right")])),
1336
1341
  _: 1
1337
1342
  })])
1338
- ], 8, Rt))), 128))])]),
1343
+ ], 8, Qt))), 128))])]),
1339
1344
  _: 1
1340
1345
  }))
1341
1346
  ]);
1342
1347
  };
1343
1348
  }
1344
- }), [["__scopeId", "data-v-5c46cc58"]]), Yt = { class: "sk-pipeline" }, Xt = { class: "d-flex flex-wrap align-center ga-2 mb-3" }, Zt = { class: "text-caption" }, Qt = {
1349
+ }), [["__scopeId", "data-v-5c46cc58"]]), Q = /* @__PURE__ */ c({
1350
+ __name: "EChart",
1351
+ props: {
1352
+ option: {},
1353
+ height: {}
1354
+ },
1355
+ emits: ["click"],
1356
+ setup(e, { emit: t }) {
1357
+ se([
1358
+ ce,
1359
+ le,
1360
+ ue,
1361
+ de,
1362
+ fe,
1363
+ pe,
1364
+ me,
1365
+ he
1366
+ ]);
1367
+ let n = e, r = t, a = h(null), o = v(null), s = null;
1368
+ return p(() => {
1369
+ a.value && (o.value = oe(a.value), o.value.setOption(n.option, { notMerge: !0 }), o.value.on("click", (e) => r("click", e)), s = new ResizeObserver(() => o.value?.resize()), s.observe(a.value));
1370
+ }), x(() => n.option, (e) => o.value?.setOption(e, { notMerge: !0 })), f(() => {
1371
+ s?.disconnect(), o.value?.dispose();
1372
+ }), (e, t) => (m(), i("div", {
1373
+ ref_key: "el",
1374
+ ref: a,
1375
+ style: d({
1376
+ height: `${e.height}px`,
1377
+ width: "100%"
1378
+ })
1379
+ }, null, 4));
1380
+ }
1381
+ }), un = { class: "text-h6" }, dn = { class: "text-caption" }, fn = { class: "d-flex align-center flex-wrap mb-1 ga-3" }, pn = { class: "d-flex align-center flex-wrap mb-4 ga-3" }, mn = { class: "text-caption text-medium-emphasis" }, hn = {
1382
+ key: 1,
1383
+ class: "text-caption text-disabled pa-4"
1384
+ }, gn = { class: "sk-tag-elo-sticky" }, _n = { class: "text-caption text-medium-emphasis mb-1" }, vn = ["onClick"], yn = { class: "text-caption" }, bn = { class: "text-caption text-medium-emphasis" }, xn = { class: "text-right" }, Sn = ["title"], Cn = { class: "text-right" }, wn = {
1385
+ key: 0,
1386
+ class: "sk-ticks"
1387
+ }, Tn = ["title"], En = { class: "text-caption ml-1" }, Dn = {
1388
+ key: 1,
1389
+ class: "text-caption text-disabled"
1390
+ }, On = { class: "text-caption" }, kn = { class: "text-caption" }, An = { class: "text-right" }, $ = 8, jn = 20, Mn = /* @__PURE__ */ K(/* @__PURE__ */ c({
1391
+ __name: "LearnerTagElo",
1392
+ props: {
1393
+ dataset: {},
1394
+ interpreters: {}
1395
+ },
1396
+ setup(c) {
1397
+ let l = c, f = t(() => ie(l.dataset)), p = t(() => {
1398
+ let e = f.value?.rows ?? [];
1399
+ return [...(f.value?.groups ?? []).map((e) => ({
1400
+ key: `group:${e.id}`,
1401
+ batch: e,
1402
+ course: !1
1403
+ })), ...(l.interpreters?.tagBatches ?? []).map((e) => ({
1404
+ key: `course:${e.id}`,
1405
+ batch: e,
1406
+ course: !0
1407
+ }))].map((t) => ({
1408
+ ...t,
1409
+ matches: e.filter((e) => F(e.tag, t.batch, e.role)).length
1410
+ }));
1411
+ }), isBookkeeping = (e) => e.roles?.some((e) => e === "intro" || e === "expose") ?? !1, v = h([]), C = h("score"), w = h(0), T = h(""), byScore = (e, t) => e.score === null || t.score === null ? Number(e.score === null) - Number(t.score === null) : t.score - e.score, byLastSeen = (e, t) => (t.lastSeen ?? "").localeCompare(e.lastSeen ?? ""), E = {
1412
+ score: byScore,
1413
+ count: (e, t) => t.count - e.count,
1414
+ lastSeen: byLastSeen,
1415
+ tag: (e, t) => e.tag.localeCompare(t.tag)
1416
+ }, D = t(() => {
1417
+ let e = p.value.filter((e) => v.value.includes(e.key)).map((e) => e.batch), t = T.value?.trim().toLowerCase(), n = Number(w.value) || 0;
1418
+ return (f.value?.rows ?? []).filter((r) => e.some((e) => F(r.tag, e, r.role)) && r.count >= n && (!t || r.tag.toLowerCase().includes(t))).sort((e, t) => E[C.value](e, t) || e.tag.localeCompare(t.tag));
1419
+ }), O = t(() => D.value.filter((e) => e.score !== null)), k = h(/* @__PURE__ */ new Map());
1420
+ function toggle(e) {
1421
+ let t = new Map(k.value);
1422
+ if (t.has(e)) t.delete(e);
1423
+ else {
1424
+ if (t.size >= $) return;
1425
+ let n = new Set(t.values()), r = 0;
1426
+ for (; n.has(r);) r++;
1427
+ t.set(e, r);
1428
+ }
1429
+ k.value = t;
1430
+ }
1431
+ x(() => l.dataset, () => {
1432
+ k.value = /* @__PURE__ */ new Map(), v.value = p.value.filter((e) => !e.course && !isBookkeeping(e.batch)).map((e) => e.key);
1433
+ }, { immediate: !0 });
1434
+ let A = t(() => {
1435
+ let e = /* @__PURE__ */ new Map(), t = /* @__PURE__ */ new Map();
1436
+ for (let n of D.value) {
1437
+ let r = W(l.interpreters, n.tag);
1438
+ e.set(n.tag, r), t.set(r, (t.get(r) ?? 0) + 1);
1439
+ }
1440
+ return new Map([...e].map(([e, n]) => [e, (t.get(n) ?? 0) > 1 ? e : n]));
1441
+ }), labelOf = (e) => A.value.get(e) ?? W(l.interpreters, e), j = ae(), M = t(() => j.current.value.dark), N = {
1442
+ light: [
1443
+ "#2a78d6",
1444
+ "#eb6834",
1445
+ "#1baf7a",
1446
+ "#eda100",
1447
+ "#e87ba4",
1448
+ "#008300",
1449
+ "#6250d6",
1450
+ "#e34948"
1451
+ ],
1452
+ dark: [
1453
+ "#3987e5",
1454
+ "#d95926",
1455
+ "#199e70",
1456
+ "#c98500",
1457
+ "#d55181",
1458
+ "#008300",
1459
+ "#9085e9",
1460
+ "#e66767"
1461
+ ]
1462
+ }, P = {
1463
+ light: {
1464
+ primary: "#0b0b0b",
1465
+ secondary: "#52514e",
1466
+ muted: "#898781",
1467
+ grid: "#e1e0d9",
1468
+ axis: "#c3c2b7"
1469
+ },
1470
+ dark: {
1471
+ primary: "#f0efec",
1472
+ secondary: "#c3c2b7",
1473
+ muted: "#898781",
1474
+ grid: "#2c2c2a",
1475
+ axis: "#383835"
1476
+ }
1477
+ }, I = t(() => P[M.value ? "dark" : "light"]), slotColor = (e) => N[M.value ? "dark" : "light"][e], L = t(() => M.value ? "rgba(195,194,183,0.18)" : "rgba(82,81,78,0.16)"), R = t(() => j.current.value.colors.surface), z = t(() => Math.max(160, O.value.length * jn + 72)), dotSize = (e) => Math.min(20, 8 + 2.2 * Math.log1p(e));
1478
+ function escapeHtml(e) {
1479
+ return e.replace(/[&<>"']/g, (e) => `&#${e.charCodeAt(0)};`);
1480
+ }
1481
+ function rowTooltip(e) {
1482
+ let t = e.recent.length ? `recent ${e.recentOk}/${e.recent.length} correct` : "no recent buffer";
1483
+ return [
1484
+ `<b>${escapeHtml(e.tag)}</b>`,
1485
+ `ELO ${e.score} (${signed(e.vsGlobal)} vs global) · ${e.count} responses`,
1486
+ `${t} · last seen ${fmtDate(e.lastSeen)}`
1487
+ ].join("<br/>");
1488
+ }
1489
+ let B = t(() => {
1490
+ let e = O.value, t = I.value, n = f.value?.global.score ?? 0, r = [n, ...e.map((e) => e.score)];
1491
+ return {
1492
+ animation: !1,
1493
+ grid: {
1494
+ left: 8,
1495
+ right: 16,
1496
+ top: 24,
1497
+ bottom: 8,
1498
+ containLabel: !0
1499
+ },
1500
+ tooltip: {
1501
+ trigger: "axis",
1502
+ axisPointer: {
1503
+ type: "shadow",
1504
+ axis: "y"
1505
+ },
1506
+ formatter: (t) => {
1507
+ let n = t[0]?.dataIndex;
1508
+ return n === void 0 ? "" : rowTooltip(e[n]);
1509
+ }
1510
+ },
1511
+ xAxis: {
1512
+ type: "value",
1513
+ position: "top",
1514
+ min: Math.floor((Math.min(...r) - 20) / 50) * 50,
1515
+ max: Math.ceil((Math.max(...r) + 20) / 50) * 50,
1516
+ axisLabel: { color: t.muted },
1517
+ axisLine: { show: !1 },
1518
+ splitLine: { lineStyle: { color: t.grid } }
1519
+ },
1520
+ yAxis: {
1521
+ type: "category",
1522
+ inverse: !0,
1523
+ triggerEvent: !0,
1524
+ data: e.map((e) => labelOf(e.tag)),
1525
+ axisLabel: {
1526
+ color: t.secondary,
1527
+ fontSize: 11,
1528
+ interval: 0
1529
+ },
1530
+ axisTick: { show: !1 },
1531
+ axisLine: { lineStyle: { color: t.axis } }
1532
+ },
1533
+ series: [{
1534
+ type: "scatter",
1535
+ data: e.map((e, n) => {
1536
+ let r = k.value.get(e.tag);
1537
+ return {
1538
+ name: e.tag,
1539
+ value: [e.score, n],
1540
+ symbolSize: dotSize(e.count),
1541
+ itemStyle: {
1542
+ color: r === void 0 ? t.muted : slotColor(r),
1543
+ borderColor: R.value,
1544
+ borderWidth: 2
1545
+ }
1546
+ };
1547
+ }),
1548
+ markLine: {
1549
+ silent: !0,
1550
+ symbol: "none",
1551
+ lineStyle: {
1552
+ color: t.primary,
1553
+ type: "solid",
1554
+ width: 1
1555
+ },
1556
+ label: {
1557
+ formatter: `global ${n}`,
1558
+ color: t.secondary,
1559
+ position: "end"
1560
+ },
1561
+ data: [{ xAxis: n }]
1562
+ }
1563
+ }]
1564
+ };
1565
+ });
1566
+ function onDotClick(e) {
1567
+ if (e.componentType === "series" && typeof e.name == "string") toggle(e.name);
1568
+ else if (e.componentType === "yAxis") {
1569
+ let t = e.value, n = O.value.find((e) => labelOf(e.tag) === t);
1570
+ n && toggle(n.tag);
1571
+ }
1572
+ }
1573
+ let toData = (e) => e.map((e) => [e.at, e.score]);
1574
+ function valueAt(e, t) {
1575
+ let n = null;
1576
+ for (let r of e) {
1577
+ if (Date.parse(r.at) > t) break;
1578
+ n = r.score;
1579
+ }
1580
+ return n;
1581
+ }
1582
+ let V = t(() => {
1583
+ let e = f.value, t = I.value;
1584
+ if (!e) return {};
1585
+ let n = [...k.value].filter(([t]) => e.series.tags[t]), r = O.value.filter((t) => !k.value.has(t.tag) && e.series.tags[t.tag]), i = n.length <= 4, a = [{
1586
+ name: "global",
1587
+ color: t.primary,
1588
+ points: e.series.global
1589
+ }, ...n.map(([t, n]) => ({
1590
+ name: labelOf(t),
1591
+ color: slotColor(n),
1592
+ points: e.series.tags[t]
1593
+ }))];
1594
+ return {
1595
+ animation: !1,
1596
+ grid: {
1597
+ left: 8,
1598
+ right: i ? 96 : 16,
1599
+ top: 36,
1600
+ bottom: 48,
1601
+ containLabel: !0
1602
+ },
1603
+ legend: {
1604
+ top: 0,
1605
+ data: a.map((e) => e.name),
1606
+ textStyle: { color: t.secondary },
1607
+ selectedMode: !1
1608
+ },
1609
+ tooltip: {
1610
+ trigger: "axis",
1611
+ formatter: (e) => {
1612
+ let t = Number(e[0]?.axisValue);
1613
+ if (!Number.isFinite(t)) return "";
1614
+ let n = a.map((e) => ({
1615
+ s: e,
1616
+ value: valueAt(e.points, t)
1617
+ })).filter((e) => e.value !== null).map(({ s: e, value: t }) => `<span style="display:inline-block;width:8px;height:8px;border-radius:4px;margin-right:6px;background:${e.color}"></span>${escapeHtml(e.name)} ${t}`);
1618
+ return [fmtTime(new Date(t).toISOString()), ...n].join("<br/>");
1619
+ }
1620
+ },
1621
+ xAxis: {
1622
+ type: "time",
1623
+ axisLabel: { color: t.muted },
1624
+ axisLine: { lineStyle: { color: t.axis } },
1625
+ splitLine: { show: !1 }
1626
+ },
1627
+ yAxis: {
1628
+ type: "value",
1629
+ scale: !0,
1630
+ axisLabel: { color: t.muted },
1631
+ splitLine: { lineStyle: { color: t.grid } }
1632
+ },
1633
+ dataZoom: [{ type: "inside" }, {
1634
+ type: "slider",
1635
+ height: 16,
1636
+ bottom: 8
1637
+ }],
1638
+ series: [...r.map((n) => ({
1639
+ type: "line",
1640
+ name: n.tag,
1641
+ data: toData(e.series.tags[n.tag]),
1642
+ step: "end",
1643
+ showSymbol: !1,
1644
+ triggerLineEvent: !0,
1645
+ lineStyle: {
1646
+ width: 1,
1647
+ color: L.value
1648
+ },
1649
+ itemStyle: { color: L.value },
1650
+ emphasis: { lineStyle: {
1651
+ width: 2,
1652
+ color: t.muted
1653
+ } },
1654
+ z: 1
1655
+ })), ...a.map((e, n) => ({
1656
+ type: "line",
1657
+ name: e.name,
1658
+ data: toData(e.points),
1659
+ step: "end",
1660
+ showSymbol: !1,
1661
+ triggerLineEvent: !0,
1662
+ lineStyle: {
1663
+ width: 2,
1664
+ color: e.color
1665
+ },
1666
+ itemStyle: { color: e.color },
1667
+ endLabel: {
1668
+ show: n === 0 || i,
1669
+ formatter: e.name,
1670
+ color: t.secondary
1671
+ },
1672
+ z: n === 0 ? 3 : 4
1673
+ }))]
1674
+ };
1675
+ });
1676
+ function onLineClick(e) {
1677
+ if (e.componentType !== "series" || typeof e.seriesName != "string") return;
1678
+ let t = f.value?.series.tags[e.seriesName] === void 0 ? [...k.value.keys()].find((t) => labelOf(t) === e.seriesName) : e.seriesName;
1679
+ t && toggle(t);
1680
+ }
1681
+ function signed(e) {
1682
+ return e === null ? "—" : e > 0 ? `+${e}` : String(e);
1683
+ }
1684
+ function fmtDate(e) {
1685
+ if (!e) return "—";
1686
+ let t = new Date(e);
1687
+ return Number.isNaN(t.getTime()) ? e : t.toLocaleDateString();
1688
+ }
1689
+ function staleTitle(e) {
1690
+ return e.staleScore === void 0 ? "counted, not rated" : "counted, not rated: the bracketed score predates count-only roles and is ignored";
1691
+ }
1692
+ let H = t(() => {
1693
+ let e = f.value, t = (e?.rows ?? []).filter((e) => e.score !== null), n = O.value.map((e) => e.vsGlobal).sort((e, t) => e - t), r = n.length ? n[Math.floor(n.length / 2)] : null;
1694
+ return [
1695
+ {
1696
+ label: `global ELO (${e?.global.count ?? 0} responses)`,
1697
+ value: e?.global.score ?? "—"
1698
+ },
1699
+ {
1700
+ label: "rated tags in view",
1701
+ value: `${O.value.length} / ${t.length}`
1702
+ },
1703
+ {
1704
+ label: "median vs global, in view",
1705
+ value: signed(r)
1706
+ },
1707
+ {
1708
+ label: "trajectories from",
1709
+ value: fmtDate(e?.seriesFrom ?? null)
1710
+ }
1711
+ ];
1712
+ });
1713
+ return (t, c) => {
1714
+ let l = _("v-alert"), h = _("v-card"), x = _("v-col"), E = _("v-row"), A = _("v-chip"), j = _("v-chip-group"), M = _("v-btn"), N = _("v-btn-toggle"), P = _("v-text-field"), F = _("v-spacer"), I = _("v-table");
1715
+ return m(), i("div", null, [f.value ? (m(), i(e, { key: 1 }, [
1716
+ c[17] || (c[17] = a("p", { class: "text-caption text-medium-emphasis mb-4" }, [
1717
+ o(" The learner's ELO on each tag (from their course registration) beside their global ELO. A tag's rating starts at the learner's global ELO when first graded and moves only on responses that grade it: read it with its response count. Bookkeeping tags ("),
1718
+ a("code", null, "intro"),
1719
+ o(", "),
1720
+ a("code", null, "expose"),
1721
+ o(") are counted, never rated, and are hidden by default. ")
1722
+ ], -1)),
1723
+ s(E, {
1724
+ dense: "",
1725
+ class: "mb-2"
1726
+ }, {
1727
+ default: S(() => [(m(!0), i(e, null, g(H.value, (e) => (m(), n(x, {
1728
+ key: e.label,
1729
+ cols: "6",
1730
+ sm: "3"
1731
+ }, {
1732
+ default: S(() => [s(h, {
1733
+ variant: "tonal",
1734
+ color: "primary",
1735
+ class: "pa-2 text-center"
1736
+ }, {
1737
+ default: S(() => [a("div", un, y(e.value), 1), a("div", dn, y(e.label), 1)]),
1738
+ _: 2
1739
+ }, 1024)]),
1740
+ _: 2
1741
+ }, 1024))), 128))]),
1742
+ _: 1
1743
+ }),
1744
+ a("div", fn, [s(j, {
1745
+ modelValue: v.value,
1746
+ "onUpdate:modelValue": c[0] || (c[0] = (e) => v.value = e),
1747
+ multiple: "",
1748
+ column: "",
1749
+ "selected-class": "text-primary"
1750
+ }, {
1751
+ default: S(() => [(m(!0), i(e, null, g(p.value, (e) => (m(), n(A, {
1752
+ key: e.key,
1753
+ value: e.key,
1754
+ size: "small",
1755
+ filter: "",
1756
+ variant: e.course ? "outlined" : "tonal",
1757
+ title: e.course ? "course batch" : "namespace × role"
1758
+ }, {
1759
+ default: S(() => [o(y(e.batch.label) + " (" + y(e.matches) + ") ", 1)]),
1760
+ _: 2
1761
+ }, 1032, [
1762
+ "value",
1763
+ "variant",
1764
+ "title"
1765
+ ]))), 128))]),
1766
+ _: 1
1767
+ }, 8, ["modelValue"])]),
1768
+ a("div", pn, [
1769
+ s(N, {
1770
+ modelValue: C.value,
1771
+ "onUpdate:modelValue": c[1] || (c[1] = (e) => C.value = e),
1772
+ mandatory: "",
1773
+ density: "compact",
1774
+ color: "primary",
1775
+ variant: "outlined"
1776
+ }, {
1777
+ default: S(() => [
1778
+ s(M, {
1779
+ value: "score",
1780
+ size: "small"
1781
+ }, {
1782
+ default: S(() => c[6] || (c[6] = [o("ELO")])),
1783
+ _: 1
1784
+ }),
1785
+ s(M, {
1786
+ value: "count",
1787
+ size: "small"
1788
+ }, {
1789
+ default: S(() => c[7] || (c[7] = [o("Responses")])),
1790
+ _: 1
1791
+ }),
1792
+ s(M, {
1793
+ value: "lastSeen",
1794
+ size: "small"
1795
+ }, {
1796
+ default: S(() => c[8] || (c[8] = [o("Last seen")])),
1797
+ _: 1
1798
+ }),
1799
+ s(M, {
1800
+ value: "tag",
1801
+ size: "small"
1802
+ }, {
1803
+ default: S(() => c[9] || (c[9] = [o("Name")])),
1804
+ _: 1
1805
+ })
1806
+ ]),
1807
+ _: 1
1808
+ }, 8, ["modelValue"]),
1809
+ s(P, {
1810
+ modelValue: w.value,
1811
+ "onUpdate:modelValue": c[2] || (c[2] = (e) => w.value = e),
1812
+ modelModifiers: { number: !0 },
1813
+ type: "number",
1814
+ min: "0",
1815
+ density: "compact",
1816
+ variant: "outlined",
1817
+ "hide-details": "",
1818
+ label: "min responses",
1819
+ style: { "max-width": "140px" }
1820
+ }, null, 8, ["modelValue"]),
1821
+ s(P, {
1822
+ modelValue: T.value,
1823
+ "onUpdate:modelValue": c[3] || (c[3] = (e) => T.value = e),
1824
+ density: "compact",
1825
+ variant: "outlined",
1826
+ "hide-details": "",
1827
+ clearable: "",
1828
+ placeholder: "filter by tag",
1829
+ "prepend-inner-icon": "mdi-magnify",
1830
+ style: { "max-width": "280px" }
1831
+ }, null, 8, ["modelValue"]),
1832
+ s(F),
1833
+ a("span", mn, [o(y(k.value.size) + "/" + y($) + " plotted ", 1), k.value.size ? (m(), n(M, {
1834
+ key: 0,
1835
+ variant: "text",
1836
+ size: "x-small",
1837
+ onClick: c[4] || (c[4] = (e) => k.value = /* @__PURE__ */ new Map())
1838
+ }, {
1839
+ default: S(() => c[10] || (c[10] = [o("clear")])),
1840
+ _: 1
1841
+ })) : r("", !0)])
1842
+ ]),
1843
+ D.value.length === 0 ? (m(), n(l, {
1844
+ key: 0,
1845
+ type: "info",
1846
+ variant: "tonal"
1847
+ }, {
1848
+ default: S(() => c[11] || (c[11] = [o("No tags match these filters.")])),
1849
+ _: 1
1850
+ })) : (m(), n(E, { key: 1 }, {
1851
+ default: S(() => [s(x, {
1852
+ cols: "12",
1853
+ md: "5"
1854
+ }, {
1855
+ default: S(() => [
1856
+ c[12] || (c[12] = a("div", { class: "text-subtitle-2" }, "ELO by tag", -1)),
1857
+ c[13] || (c[13] = a("div", { class: "text-caption text-medium-emphasis mb-1" }, " Dot size: responses (log scale). Click a dot or a name to plot its trajectory. ", -1)),
1858
+ O.value.length ? (m(), n(Q, {
1859
+ key: 0,
1860
+ option: B.value,
1861
+ height: z.value,
1862
+ onClick: onDotClick
1863
+ }, null, 8, ["option", "height"])) : (m(), i("div", hn, "No rated tags in this selection."))
1864
+ ]),
1865
+ _: 1
1866
+ }), s(x, {
1867
+ cols: "12",
1868
+ md: "7"
1869
+ }, {
1870
+ default: S(() => [a("div", gn, [
1871
+ c[14] || (c[14] = a("div", { class: "text-subtitle-2" }, "Trajectories", -1)),
1872
+ a("div", _n, [f.value.seriesFrom ? (m(), i(e, { key: 0 }, [o(" From " + y(b(fmtTime)(f.value.seriesFrom)) + ", when sessions began recording ELO events. Faint lines are the other tags in view; click one to plot it. A jump between recorded events is a session that didn't save its events. ", 1)], 64)) : (m(), i(e, { key: 1 }, [o("No session in this dataset recorded ELO events.")], 64))]),
1873
+ f.value.seriesFrom ? (m(), n(Q, {
1874
+ key: 0,
1875
+ option: V.value,
1876
+ height: 380,
1877
+ onClick: onLineClick
1878
+ }, null, 8, ["option"])) : r("", !0)
1879
+ ])]),
1880
+ _: 1
1881
+ })]),
1882
+ _: 1
1883
+ })),
1884
+ D.value.length ? (m(), n(I, {
1885
+ key: 2,
1886
+ density: "compact",
1887
+ class: "mt-4 sk-tag-elo-table"
1888
+ }, {
1889
+ default: S(() => [c[16] || (c[16] = a("thead", null, [a("tr", null, [
1890
+ a("th", null, "Tag"),
1891
+ a("th", null, "Batch"),
1892
+ a("th", { class: "text-right" }, "ELO"),
1893
+ a("th", { class: "text-right" }, "vs global"),
1894
+ a("th", { class: "text-right" }, "Responses"),
1895
+ a("th", null, "Recent first attempts"),
1896
+ a("th", null, "First seen"),
1897
+ a("th", null, "Last seen"),
1898
+ a("th", { class: "text-right" }, "ELO events")
1899
+ ])], -1)), a("tbody", null, [(m(!0), i(e, null, g(D.value, (t) => (m(), i("tr", {
1900
+ key: t.tag,
1901
+ class: u({ "sk-pickable": t.score !== null }),
1902
+ onClick: (e) => t.score !== null && toggle(t.tag)
1903
+ }, [
1904
+ a("td", null, [a("span", {
1905
+ class: "sk-swatch",
1906
+ style: d({ background: k.value.has(t.tag) ? slotColor(k.value.get(t.tag)) : "transparent" })
1907
+ }, null, 4), a("code", yn, y(t.tag), 1)]),
1908
+ a("td", bn, y(t.group), 1),
1909
+ a("td", xn, [t.score === null ? (m(), i("span", {
1910
+ key: 1,
1911
+ class: "text-disabled",
1912
+ title: staleTitle(t)
1913
+ }, [c[15] || (c[15] = o(" —")), t.staleScore === void 0 ? r("", !0) : (m(), i(e, { key: 0 }, [o(" (" + y(t.staleScore) + ")", 1)], 64))], 8, Sn)) : (m(), i(e, { key: 0 }, [o(y(t.score), 1)], 64))]),
1914
+ a("td", { class: u(["text-right", b(deltaClass)(t.vsGlobal)]) }, y(signed(t.vsGlobal)), 3),
1915
+ a("td", Cn, y(t.count), 1),
1916
+ a("td", null, [t.recent.length ? (m(), i("span", wn, [(m(!0), i(e, null, g(t.recent, (e, t) => (m(), i("span", {
1917
+ key: t,
1918
+ class: u(["sk-tick", e.ok ? "bg-success" : "bg-error"]),
1919
+ title: `${b(fmtTime)(e.at)} · ${e.ok ? "correct" : "missed"} · ${e.card}`
1920
+ }, null, 10, Tn))), 128)), a("span", En, y(t.recentOk) + "/" + y(t.recent.length), 1)])) : (m(), i("span", Dn, "—"))]),
1921
+ a("td", On, y(fmtDate(t.firstSeen)), 1),
1922
+ a("td", kn, y(fmtDate(t.lastSeen)), 1),
1923
+ a("td", An, y(t.events || ""), 1)
1924
+ ], 10, vn))), 128))])]),
1925
+ _: 1
1926
+ })) : r("", !0)
1927
+ ], 64)) : (m(), n(l, {
1928
+ key: 0,
1929
+ type: "info",
1930
+ variant: "tonal"
1931
+ }, {
1932
+ default: S(() => c[5] || (c[5] = [o(" This learner's registration carries no ELO for this course. ")])),
1933
+ _: 1
1934
+ }))]);
1935
+ };
1936
+ }
1937
+ }), [["__scopeId", "data-v-ec9e083c"]]), Nn = { class: "sk-pipeline" }, Pn = { class: "d-flex flex-wrap align-center ga-2 mb-3" }, Fn = { class: "text-caption" }, In = {
1345
1938
  key: 0,
1346
1939
  class: "text-caption text-medium-emphasis"
1347
- }, $t = { class: "sk-stage" }, en = { class: "d-flex align-center mb-1" }, tn = { class: "sk-stage-num" }, nn = { class: "font-weight-medium" }, rn = { class: "text-caption text-medium-emphasis mb-2" }, an = { class: "d-flex flex-wrap align-center ga-2" }, on = { class: "font-weight-medium" }, sn = { class: "text-caption" }, cn = {
1940
+ }, Ln = { class: "sk-stage" }, Rn = { class: "d-flex align-center mb-1" }, zn = { class: "sk-stage-num" }, Bn = { class: "font-weight-medium" }, Vn = { class: "text-caption text-medium-emphasis mb-2" }, Hn = { class: "d-flex flex-wrap align-center ga-2" }, Un = { class: "font-weight-medium" }, Wn = { class: "text-caption" }, Gn = {
1348
1941
  key: 0,
1349
1942
  class: "text-caption mt-1"
1350
- }, ln = {
1943
+ }, Kn = {
1351
1944
  key: 1,
1352
1945
  class: "text-caption mt-1"
1353
- }, un = {
1946
+ }, qn = {
1354
1947
  key: 1,
1355
1948
  class: "text-medium-emphasis"
1356
- }, dn = {
1949
+ }, Jn = {
1357
1950
  key: 2,
1358
1951
  class: "mt-1"
1359
- }, fn = ["onClick"], pn = {
1952
+ }, Yn = ["onClick"], Xn = {
1360
1953
  key: 0,
1361
1954
  class: "sk-config"
1362
- }, mn = {
1955
+ }, Zn = {
1363
1956
  key: 0,
1364
1957
  class: "text-caption text-medium-emphasis"
1365
- }, hn = { class: "d-flex flex-wrap align-center ga-2" }, gn = { class: "font-weight-medium" }, _n = { class: "text-caption" }, vn = {
1958
+ }, Qn = { class: "d-flex flex-wrap align-center ga-2" }, $n = { class: "font-weight-medium" }, er = { class: "text-caption" }, tr = {
1366
1959
  key: 0,
1367
1960
  class: "text-caption mt-1"
1368
- }, yn = {
1961
+ }, nr = {
1369
1962
  key: 1,
1370
1963
  class: "text-caption mt-1 text-medium-emphasis"
1371
- }, bn = {
1964
+ }, rr = {
1372
1965
  key: 2,
1373
1966
  class: "mt-1"
1374
- }, xn = { class: "sk-impact-bar" }, Sn = ["title"], Cn = { class: "text-caption" }, wn = {
1967
+ }, ir = { class: "sk-impact-bar" }, ar = ["title"], or = { class: "text-caption" }, sr = {
1375
1968
  key: 1,
1376
1969
  class: "text-caption text-medium-emphasis"
1377
- }, Tn = {
1970
+ }, cr = {
1378
1971
  key: 3,
1379
1972
  class: "mt-1"
1380
- }, En = ["onClick"], Dn = {
1973
+ }, lr = ["onClick"], ur = {
1381
1974
  key: 0,
1382
1975
  class: "sk-config"
1383
- }, Q = { class: "sk-nav" }, On = { class: "d-flex flex-wrap align-center ga-2" }, kn = { class: "text-caption mt-1" }, An = {
1976
+ }, dr = { class: "sk-nav" }, fr = { class: "d-flex flex-wrap align-center ga-2" }, pr = { class: "text-caption mt-1" }, mr = {
1384
1977
  key: 0,
1385
1978
  class: "text-caption mt-1"
1386
- }, jn = { class: "sk-nav" }, Mn = { class: "d-flex flex-wrap align-center ga-2" }, Nn = { class: "text-caption mt-1" }, Pn = {
1979
+ }, hr = { class: "sk-nav" }, gr = { class: "d-flex flex-wrap align-center ga-2" }, _r = { class: "text-caption mt-1" }, vr = {
1387
1980
  key: 0,
1388
1981
  class: "text-caption mt-1"
1389
- }, Fn = {
1982
+ }, yr = {
1390
1983
  key: 0,
1391
1984
  class: "text-caption text-medium-emphasis"
1392
- }, In = {
1985
+ }, br = {
1393
1986
  key: 3,
1394
1987
  class: "text-caption"
1395
- }, Ln = {
1988
+ }, xr = {
1396
1989
  key: 0,
1397
1990
  class: "sk-stage-arrow"
1398
- }, Rn = {
1991
+ }, Sr = {
1399
1992
  key: 0,
1400
1993
  class: "text-caption text-medium-emphasis mt-3"
1401
- }, $ = /* @__PURE__ */ K(/* @__PURE__ */ c({
1994
+ }, Cr = /* @__PURE__ */ K(/* @__PURE__ */ c({
1402
1995
  __name: "PipelineOverview",
1403
1996
  props: {
1404
1997
  strategies: {},
@@ -1422,9 +2015,9 @@ var G = {
1422
2015
  }
1423
2016
  }, regStat = (e) => l.stats?.regulators.find((t) => t.name === e);
1424
2017
  function regStatText(e) {
1425
- return `In these runs: active (×>1) in ${e.runsActive}/${e.runs}, mean ×${e.meanMultiplier.toFixed(2)}, max ×${e.maxMultiplier.toFixed(2)}. Last: ${L(e.last)}.`;
2018
+ return `In these runs: active (×>1) in ${e.runsActive}/${e.runs}, mean ×${e.meanMultiplier.toFixed(2)}, max ×${e.maxMultiplier.toFixed(2)}. Last: ${z(e.last)}.`;
1426
2019
  }
1427
- let _ = {
2020
+ let p = {
1428
2021
  gate: "Gate: its penalties mean not ready yet; regulators will not lift what it penalized.",
1429
2022
  signal: "Signal: its penalties express preference."
1430
2023
  };
@@ -1433,21 +2026,21 @@ var G = {
1433
2026
  return t ? {
1434
2027
  kind: t,
1435
2028
  label: t,
1436
- help: _[t]
2029
+ help: p[t]
1437
2030
  } : {
1438
2031
  kind: "gate",
1439
2032
  label: "gate (undeclared)",
1440
- help: `${_.gate} Its class declares no kind, so it counts as a gate.`
2033
+ help: `${p.gate} Its class declares no kind, so it counts as a gate.`
1441
2034
  };
1442
2035
  }
1443
- let b = t(() => ie(l.strategies, l.courseId)), S = t(() => new Map((l.stats?.generators ?? []).map((e) => [e.name, e]))), C = t(() => new Map((l.stats?.filters ?? []).map((e) => [e.name, e]))), genStat = (e) => S.value.get(e), filterStat = (e) => C.value.get(e), w = t(() => {
1444
- let e = [...b.value.notes], t = l.stats;
2036
+ let v = t(() => _e(l.strategies, l.courseId)), x = t(() => new Map((l.stats?.generators ?? []).map((e) => [e.name, e]))), C = t(() => new Map((l.stats?.filters ?? []).map((e) => [e.name, e]))), genStat = (e) => x.value.get(e), filterStat = (e) => C.value.get(e), w = t(() => {
2037
+ let e = [...v.value.notes], t = l.stats;
1445
2038
  if (!t) return e;
1446
- for (let t of b.value.filters) {
2039
+ for (let t of v.value.filters) {
1447
2040
  let n = filterStat(t.name);
1448
2041
  n && n.boosted + n.penalized + n.removed === 0 && e.push(`${t.name} changed no candidate's score in ${n.runs} runs.`);
1449
2042
  }
1450
- if (t.runsWithSelection > 0) for (let t of b.value.generators) {
2043
+ if (t.runsWithSelection > 0) for (let t of v.value.generators) {
1451
2044
  let n = genStat(t.name);
1452
2045
  n && n.runs > 0 && n.selected === 0 && e.push(`${t.name} proposed candidates in ${n.runs} runs, and none was selected.`);
1453
2046
  }
@@ -1490,7 +2083,7 @@ var G = {
1490
2083
  function fmtPct(e) {
1491
2084
  return e === 0 ? "0%" : e < .01 ? "<1%" : `${Math.round(e * 100)}%`;
1492
2085
  }
1493
- let T = m(/* @__PURE__ */ new Set());
2086
+ let T = h(/* @__PURE__ */ new Set());
1494
2087
  function toggleConfig(e) {
1495
2088
  let t = new Set(T.value);
1496
2089
  t.has(e) ? t.delete(e) : t.add(e), T.value = t;
@@ -1505,216 +2098,220 @@ var G = {
1505
2098
  }
1506
2099
  }
1507
2100
  return (t, c) => {
1508
- let l = g("v-chip"), m = g("v-alert"), _ = g("v-icon");
1509
- return p(), i("div", Yt, [
1510
- a("div", Xt, [
2101
+ let l = _("v-chip"), p = _("v-alert"), h = _("v-icon");
2102
+ return m(), i("div", Nn, [
2103
+ a("div", Pn, [
1511
2104
  s(l, {
1512
2105
  size: "small",
1513
2106
  variant: "tonal",
1514
- color: b.value.kind === "default" ? "warning" : "primary"
2107
+ color: v.value.kind === "default" ? "warning" : "primary"
1515
2108
  }, {
1516
- default: x(() => [o(v(b.value.kind === "default" ? "default pipeline: the course has no strategy docs" : "assembled from strategy docs"), 1)]),
2109
+ default: S(() => [o(y(v.value.kind === "default" ? "default pipeline: the course has no strategy docs" : "assembled from strategy docs"), 1)]),
1517
2110
  _: 1
1518
2111
  }, 8, ["color"]),
1519
- a("span", Zt, v(b.value.generators.length) + " generator(s) · " + v(b.value.filters.length) + " filter(s) ", 1),
1520
- t.stats ? (p(), i("span", Qt, " · run stats" + v(t.statsLabel ? ` for ${t.statsLabel}` : "") + ": " + v(t.stats.runs) + " runs over " + v(t.stats.sessions) + " sessions, " + v(y(fmtTime)(t.stats.firstRunAt)) + " – " + v(y(fmtTime)(t.stats.lastRunAt)), 1)) : r("", !0)
2112
+ a("span", Fn, y(v.value.generators.length) + " generator(s) · " + y(v.value.filters.length) + " filter(s) ", 1),
2113
+ t.stats ? (m(), i("span", In, " · run stats" + y(t.statsLabel ? ` for ${t.statsLabel}` : "") + ": " + y(t.stats.runs) + " runs over " + y(t.stats.sessions) + " sessions, " + y(b(fmtTime)(t.stats.firstRunAt)) + " – " + y(b(fmtTime)(t.stats.lastRunAt)), 1)) : r("", !0)
1521
2114
  ]),
1522
- (p(!0), i(e, null, h(b.value.skipped, (e) => (p(), n(m, {
2115
+ (m(!0), i(e, null, g(v.value.skipped, (e) => (m(), n(p, {
1523
2116
  key: e.strategy._id,
1524
2117
  type: "warning",
1525
2118
  variant: "tonal",
1526
2119
  density: "compact",
1527
2120
  class: "mb-2"
1528
2121
  }, {
1529
- default: x(() => [
1530
- a("strong", null, v(e.strategy.name), 1),
2122
+ default: S(() => [
2123
+ a("strong", null, y(e.strategy.name), 1),
1531
2124
  c[0] || (c[0] = o(" (")),
1532
- a("code", null, v(e.strategy.implementingClass), 1),
1533
- o(") is " + v(e.reason) + " in this app, so it would not run here. A course's own navigators only plan correctly in the app that registers them. ", 1)
2125
+ a("code", null, y(e.strategy.implementingClass), 1),
2126
+ o(") is " + y(e.reason) + " in this app, so it would not run here. A course's own navigators only plan correctly in the app that registers them. ", 1)
1534
2127
  ]),
1535
2128
  _: 2
1536
2129
  }, 1024))), 128)),
1537
- (p(!0), i(e, null, h(b.value.warnings, (e) => (p(), n(m, {
2130
+ (m(!0), i(e, null, g(v.value.warnings, (e) => (m(), n(p, {
1538
2131
  key: e,
1539
2132
  type: "warning",
1540
2133
  variant: "tonal",
1541
2134
  density: "compact",
1542
2135
  class: "mb-2"
1543
2136
  }, {
1544
- default: x(() => [o(v(e), 1)]),
2137
+ default: S(() => [o(y(e), 1)]),
1545
2138
  _: 2
1546
2139
  }, 1024))), 128)),
1547
- (p(!0), i(e, null, h(w.value, (e) => (p(), n(m, {
2140
+ (m(!0), i(e, null, g(w.value, (e) => (m(), n(p, {
1548
2141
  key: e,
1549
2142
  type: "info",
1550
2143
  variant: "tonal",
1551
2144
  density: "compact",
1552
2145
  class: "mb-2"
1553
2146
  }, {
1554
- default: x(() => [o(v(e), 1)]),
2147
+ default: S(() => [o(y(e), 1)]),
1555
2148
  _: 2
1556
2149
  }, 1024))), 128)),
1557
- (p(!0), i(e, null, h(y(U), (m, g) => (p(), i("div", { key: m.key }, [a("div", $t, [
1558
- a("div", en, [a("span", tn, v(g + 1), 1), a("span", nn, v(m.title), 1)]),
1559
- a("div", rn, v(m.summary), 1),
1560
- m.key === "generate" ? (p(!0), i(e, { key: 0 }, h(b.value.generators, (n) => (p(), i("div", {
2150
+ (m(!0), i(e, null, g(b(ge), (p, _) => (m(), i("div", { key: p.key }, [a("div", Ln, [
2151
+ a("div", Rn, [a("span", zn, y(_ + 1), 1), a("span", Bn, y(p.title), 1)]),
2152
+ a("div", Vn, y(p.summary), 1),
2153
+ p.key === "generate" ? (m(!0), i(e, { key: 0 }, g(v.value.generators, (n) => (m(), i("div", {
1561
2154
  key: n.name,
1562
2155
  class: "sk-nav"
1563
2156
  }, [
1564
- a("div", an, [
1565
- a("span", on, v(n.name), 1),
1566
- a("code", sn, v(n.implementingClass), 1),
2157
+ a("div", Hn, [
2158
+ a("span", Un, y(n.name), 1),
2159
+ a("code", Wn, y(n.implementingClass), 1),
1567
2160
  s(l, {
1568
2161
  size: "x-small",
1569
2162
  variant: "outlined",
1570
2163
  color: f[n.origin].color
1571
2164
  }, {
1572
- default: x(() => [o(v(f[n.origin].label), 1)]),
2165
+ default: S(() => [o(y(f[n.origin].label), 1)]),
1573
2166
  _: 2
1574
2167
  }, 1032, ["color"])
1575
2168
  ]),
1576
- n.strategy?.description ? (p(), i("div", cn, v(n.strategy.description), 1)) : r("", !0),
1577
- t.stats ? (p(), i("div", ln, [genStat(n.name) ? (p(), i(e, { key: 0 }, [o(v(fmtNum(genStat(n.name).meanCards)) + " candidates/run (" + v(fmtNum(genStat(n.name).meanNew)) + " new, " + v(fmtNum(genStat(n.name).meanReview)) + " review) · top score " + v(genStat(n.name).topScoreLast.toFixed(2)) + " last, " + v(genStat(n.name).topScoreMax.toFixed(2)) + " max ", 1), t.stats.runsWithSelection > 0 ? (p(), i(e, { key: 0 }, [
2169
+ n.strategy?.description ? (m(), i("div", Gn, y(n.strategy.description), 1)) : r("", !0),
2170
+ t.stats ? (m(), i("div", Kn, [genStat(n.name) ? (m(), i(e, { key: 0 }, [o(y(fmtNum(genStat(n.name).meanCards)) + " candidates/run (" + y(fmtNum(genStat(n.name).meanNew)) + " new, " + y(fmtNum(genStat(n.name).meanReview)) + " review) · top score " + y(genStat(n.name).topScoreLast.toFixed(2)) + " last, " + y(genStat(n.name).topScoreMax.toFixed(2)) + " max ", 1), t.stats.runsWithSelection > 0 ? (m(), i(e, { key: 0 }, [
1578
2171
  c[1] || (c[1] = o(" · ")),
1579
- a("strong", null, v(genStat(n.name).selected), 1),
2172
+ a("strong", null, y(genStat(n.name).selected), 1),
1580
2173
  c[2] || (c[2] = o(" selected ")),
1581
- genStat(n.name).firstAttempts > 0 ? (p(), i(e, { key: 0 }, [o(" · first attempts " + v(genStat(n.name).firstAttemptsCorrect) + "/" + v(genStat(n.name).firstAttempts) + " correct ", 1), a("span", { class: u(y(accuracyClass)(accuracyOf(genStat(n.name)))) }, " (" + v(Math.round(100 * accuracyOf(genStat(n.name)))) + "%) ", 3)], 64)) : r("", !0)
1582
- ], 64)) : r("", !0)], 64)) : (p(), i("span", un, "absent from these runs"))])) : r("", !0),
1583
- prettyConfig(n.strategy?.serializedData) ? (p(), i("div", dn, [a("a", {
2174
+ genStat(n.name).firstAttempts > 0 ? (m(), i(e, { key: 0 }, [o(" · first attempts " + y(genStat(n.name).firstAttemptsCorrect) + "/" + y(genStat(n.name).firstAttempts) + " correct ", 1), a("span", { class: u(b(accuracyClass)(accuracyOf(genStat(n.name)))) }, " (" + y(Math.round(100 * accuracyOf(genStat(n.name)))) + "%) ", 3)], 64)) : r("", !0)
2175
+ ], 64)) : r("", !0)], 64)) : (m(), i("span", qn, "absent from these runs"))])) : r("", !0),
2176
+ prettyConfig(n.strategy?.serializedData) ? (m(), i("div", Jn, [a("a", {
1584
2177
  class: "sk-config-link text-caption",
1585
2178
  onClick: (e) => toggleConfig(`g:${n.name}`)
1586
- }, v(T.value.has(`g:${n.name}`) ? "Hide" : "Show") + " config ", 9, fn), T.value.has(`g:${n.name}`) ? (p(), i("pre", pn, v(prettyConfig(n.strategy?.serializedData)), 1)) : r("", !0)])) : r("", !0)
1587
- ]))), 128)) : m.key === "filter" ? (p(), i(e, { key: 1 }, [b.value.filters.length === 0 ? (p(), i("div", mn, "No filters.")) : r("", !0), (p(!0), i(e, null, h(b.value.filters, (m) => (p(), i("div", {
1588
- key: m.name,
2179
+ }, y(T.value.has(`g:${n.name}`) ? "Hide" : "Show") + " config ", 9, Yn), T.value.has(`g:${n.name}`) ? (m(), i("pre", Xn, y(prettyConfig(n.strategy?.serializedData)), 1)) : r("", !0)])) : r("", !0)
2180
+ ]))), 128)) : p.key === "filter" ? (m(), i(e, { key: 1 }, [v.value.filters.length === 0 ? (m(), i("div", Zn, "No filters.")) : r("", !0), (m(!0), i(e, null, g(v.value.filters, (p) => (m(), i("div", {
2181
+ key: p.name,
1589
2182
  class: "sk-nav"
1590
2183
  }, [
1591
- a("div", hn, [
1592
- a("span", gn, v(m.name), 1),
1593
- a("code", _n, v(m.implementingClass), 1),
2184
+ a("div", Qn, [
2185
+ a("span", $n, y(p.name), 1),
2186
+ a("code", er, y(p.implementingClass), 1),
1594
2187
  s(l, {
1595
2188
  size: "x-small",
1596
2189
  variant: "outlined",
1597
- color: f[m.origin].color
2190
+ color: f[p.origin].color
1598
2191
  }, {
1599
- default: x(() => [o(v(f[m.origin].label), 1)]),
2192
+ default: S(() => [o(y(f[p.origin].label), 1)]),
1600
2193
  _: 2
1601
2194
  }, 1032, ["color"]),
1602
- m.strategy?.learnable ? (p(), n(l, {
2195
+ p.strategy?.learnable ? (m(), n(l, {
1603
2196
  key: 0,
1604
2197
  size: "x-small",
1605
2198
  variant: "outlined"
1606
2199
  }, {
1607
- default: x(() => c[3] || (c[3] = [o("learnable weight")])),
2200
+ default: S(() => c[3] || (c[3] = [o("learnable weight")])),
1608
2201
  _: 1
1609
2202
  })) : r("", !0),
1610
2203
  s(l, {
1611
2204
  size: "x-small",
1612
2205
  variant: "tonal",
1613
- color: filterKind(m).kind === "gate" ? "deep-orange" : "blue-grey",
1614
- title: filterKind(m).help
2206
+ color: filterKind(p).kind === "gate" ? "deep-orange" : "blue-grey",
2207
+ title: filterKind(p).help
1615
2208
  }, {
1616
- default: x(() => [o(v(filterKind(m).label), 1)]),
2209
+ default: S(() => [o(y(filterKind(p).label), 1)]),
1617
2210
  _: 2
1618
2211
  }, 1032, ["color", "title"])
1619
2212
  ]),
1620
- m.strategy?.description ? (p(), i("div", vn, v(m.strategy.description), 1)) : m.strategy ? r("", !0) : (p(), i("div", yn, " Built in code; no strategy document. ")),
1621
- t.stats ? (p(), i("div", bn, [filterStat(m.name) ? (p(), i(e, { key: 0 }, [a("div", xn, [(p(!0), i(e, null, h(impactParts(filterStat(m.name)), (e) => (p(), i("div", {
2213
+ p.strategy?.description ? (m(), i("div", tr, y(p.strategy.description), 1)) : p.strategy ? r("", !0) : (m(), i("div", nr, " Built in code; no strategy document. ")),
2214
+ t.stats ? (m(), i("div", rr, [filterStat(p.name) ? (m(), i(e, { key: 0 }, [a("div", ir, [(m(!0), i(e, null, g(impactParts(filterStat(p.name)), (e) => (m(), i("div", {
1622
2215
  key: e.key,
1623
2216
  class: u(`bg-${e.color}`),
1624
2217
  style: d({ width: `${e.share * 100}%` }),
1625
2218
  title: `${e.key}: ${e.count}`
1626
- }, null, 14, Sn))), 128))]), a("div", Cn, [o(" over " + v(filterStat(m.name).runs) + " runs: ", 1), (p(!0), i(e, null, h(impactParts(filterStat(m.name)), (e) => (p(), i("span", {
2219
+ }, null, 14, ar))), 128))]), a("div", or, [o(" over " + y(filterStat(p.name).runs) + " runs: ", 1), (m(!0), i(e, null, g(impactParts(filterStat(p.name)), (e) => (m(), i("span", {
1627
2220
  key: e.key,
1628
2221
  class: "mr-2"
1629
- }, [a("span", { class: u(`text-${e.color}`) }, "●", 2), o(" " + v(e.key) + " " + v(fmtPct(e.share)), 1)]))), 128))])], 64)) : (p(), i("span", wn, "absent from these runs"))])) : r("", !0),
1630
- prettyConfig(m.strategy?.serializedData) ? (p(), i("div", Tn, [a("a", {
2222
+ }, [a("span", { class: u(`text-${e.color}`) }, "●", 2), o(" " + y(e.key) + " " + y(fmtPct(e.share)), 1)]))), 128))])], 64)) : (m(), i("span", sr, "absent from these runs"))])) : r("", !0),
2223
+ prettyConfig(p.strategy?.serializedData) ? (m(), i("div", cr, [a("a", {
1631
2224
  class: "sk-config-link text-caption",
1632
- onClick: (e) => toggleConfig(`f:${m.name}`)
1633
- }, v(T.value.has(`f:${m.name}`) ? "Hide" : "Show") + " config ", 9, En), T.value.has(`f:${m.name}`) ? (p(), i("pre", Dn, v(prettyConfig(m.strategy?.serializedData)), 1)) : r("", !0)])) : r("", !0)
1634
- ]))), 128))], 64)) : m.key === "regulate" ? (p(), i(e, { key: 2 }, [
1635
- a("div", Q, [
1636
- a("div", On, [c[5] || (c[5] = a("span", { class: "font-weight-medium" }, "Review mass", -1)), s(l, {
2225
+ onClick: (e) => toggleConfig(`f:${p.name}`)
2226
+ }, y(T.value.has(`f:${p.name}`) ? "Hide" : "Show") + " config ", 9, lr), T.value.has(`f:${p.name}`) ? (m(), i("pre", ur, y(prettyConfig(p.strategy?.serializedData)), 1)) : r("", !0)])) : r("", !0)
2227
+ ]))), 128))], 64)) : p.key === "regulate" ? (m(), i(e, { key: 2 }, [
2228
+ a("div", dr, [
2229
+ a("div", fr, [c[5] || (c[5] = a("span", { class: "font-weight-medium" }, "Review mass", -1)), s(l, {
1637
2230
  size: "x-small",
1638
2231
  variant: "outlined"
1639
2232
  }, {
1640
- default: x(() => c[4] || (c[4] = [o("on review cards")])),
2233
+ default: S(() => c[4] || (c[4] = [o("on review cards")])),
1641
2234
  _: 1
1642
2235
  })]),
1643
- a("div", kn, " Each due review weighs its SRS urgency (0–1) times the filters' net effect on it. Above " + v(b.value.regulators.reviewMass.healthyMass) + " card-equivalents, every review is multiplied by ×" + v(b.value.regulators.reviewMass.rate) + " per " + v(b.value.regulators.reviewMass.healthyMass) + " in excess (uncapped). Reviews without an urgency weigh their score against " + v(b.value.regulators.reviewMass.referenceScore) + ". ", 1),
1644
- regStat("review-mass") ? (p(), i("div", An, v(regStatText(regStat("review-mass"))), 1)) : r("", !0)
2236
+ a("div", pr, " Each due review weighs its SRS urgency (0–1) times the filters' net effect on it. Above " + y(v.value.regulators.reviewMass.healthyMass) + " card-equivalents, every review is multiplied by ×" + y(v.value.regulators.reviewMass.rate) + " per " + y(v.value.regulators.reviewMass.healthyMass) + " in excess (uncapped). Reviews without an urgency weigh their score against " + y(v.value.regulators.reviewMass.referenceScore) + ". ", 1),
2237
+ regStat("review-mass") ? (m(), i("div", mr, y(regStatText(regStat("review-mass"))), 1)) : r("", !0)
1645
2238
  ]),
1646
- a("div", jn, [
1647
- a("div", Mn, [c[7] || (c[7] = a("span", { class: "font-weight-medium" }, "Intake", -1)), s(l, {
2239
+ a("div", hr, [
2240
+ a("div", gr, [c[7] || (c[7] = a("span", { class: "font-weight-medium" }, "Intake", -1)), s(l, {
1648
2241
  size: "x-small",
1649
2242
  variant: "outlined"
1650
2243
  }, {
1651
- default: x(() => c[6] || (c[6] = [o("on new cards no gate penalized")])),
2244
+ default: S(() => c[6] || (c[6] = [o("on new cards no gate penalized")])),
1652
2245
  _: 1
1653
2246
  })]),
1654
- a("div", Nn, " ×" + v(b.value.regulators.intake.rate) + " per " + v(b.value.regulators.intake.scaleHours) + " hours since a new card was last presented (uncapped). The clock stops while no eligible new card exists. ", 1),
1655
- regStat("intake") ? (p(), i("div", Pn, v(regStatText(regStat("intake"))), 1)) : r("", !0)
2247
+ a("div", _r, " ×" + y(v.value.regulators.intake.rate) + " per " + y(v.value.regulators.intake.scaleHours) + " hours since a new card was last presented (uncapped). The clock stops while no eligible new card exists. ", 1),
2248
+ regStat("intake") ? (m(), i("div", vr, y(regStatText(regStat("intake"))), 1)) : r("", !0)
1656
2249
  ]),
1657
- t.stats && t.stats.regulators.length === 0 ? (p(), i("div", Fn, " None of these runs recorded regulator readings (recorded from 0.2.29). ")) : r("", !0)
1658
- ], 64)) : m.key === "select" && t.stats && t.stats.runsWithSelection > 0 ? (p(), i("div", In, [
1659
- o(v(t.stats.selectedUnattributed) + " selected card(s) had no generator: forced in by a hint's ", 1),
2250
+ t.stats && t.stats.regulators.length === 0 ? (m(), i("div", yr, " None of these runs recorded regulator readings (recorded from 0.2.29). ")) : r("", !0)
2251
+ ], 64)) : p.key === "select" && t.stats && t.stats.runsWithSelection > 0 ? (m(), i("div", br, [
2252
+ o(y(t.stats.selectedUnattributed) + " selected card(s) had no generator: forced in by a hint's ", 1),
1660
2253
  c[8] || (c[8] = a("code", null, "requireCards", -1)),
1661
2254
  c[9] || (c[9] = o(". "))
1662
2255
  ])) : r("", !0)
1663
- ]), g < y(U).length - 1 ? (p(), i("div", Ln, [s(_, { size: "small" }, {
1664
- default: x(() => c[10] || (c[10] = [o("mdi-arrow-down")])),
2256
+ ]), _ < b(ge).length - 1 ? (m(), i("div", xr, [s(h, { size: "small" }, {
2257
+ default: S(() => c[10] || (c[10] = [o("mdi-arrow-down")])),
1665
2258
  _: 1
1666
2259
  })])) : r("", !0)]))), 128)),
1667
- t.stats && t.stats.runsWithSelection === 0 ? (p(), i("div", Rn, " None of these runs recorded which cards they selected (recorded from 0.2.28), so selection and first-attempt counts are not shown. ")) : r("", !0)
2260
+ t.stats && t.stats.runsWithSelection === 0 ? (m(), i("div", Sr, " None of these runs recorded which cards they selected (recorded from 0.2.28), so selection and first-attempt counts are not shown. ")) : r("", !0)
1668
2261
  ]);
1669
2262
  };
1670
2263
  }
1671
- }), [["__scopeId", "data-v-24b6038f"]]), zn = /* @__PURE__ */ c({
2264
+ }), [["__scopeId", "data-v-24b6038f"]]), wr = /* @__PURE__ */ c({
1672
2265
  __name: "LearnerDiagnostics",
1673
2266
  props: {
1674
2267
  dataset: {},
1675
2268
  interpreters: {}
1676
2269
  },
1677
2270
  setup(a) {
1678
- let c = a, l = m("sessions"), u = m(null), d = m(void 0), f = t(() => F(c.dataset));
2271
+ let c = a, l = h("sessions"), u = h(null), d = h(void 0), f = t(() => L(c.dataset));
1679
2272
  function openCard(e) {
1680
2273
  d.value = void 0, l.value = "cards", setTimeout(() => d.value = e);
1681
2274
  }
1682
- return b(() => c.dataset, () => {
2275
+ return x(() => c.dataset, () => {
1683
2276
  l.value = "sessions", u.value = null, d.value = void 0;
1684
2277
  }), (t, a) => {
1685
- let c = g("v-tab"), m = g("v-tabs"), h = g("v-btn");
1686
- return p(), i("div", null, [s(m, {
2278
+ let c = _("v-tab"), p = _("v-tabs"), h = _("v-btn");
2279
+ return m(), i("div", null, [s(p, {
1687
2280
  modelValue: l.value,
1688
2281
  "onUpdate:modelValue": a[0] || (a[0] = (e) => l.value = e),
1689
2282
  density: "compact",
1690
2283
  class: "mb-4"
1691
2284
  }, {
1692
- default: x(() => [
2285
+ default: S(() => [
1693
2286
  s(c, { value: "sessions" }, {
1694
- default: x(() => [o("Sessions (" + v(t.dataset.sessions.length) + ")", 1)]),
2287
+ default: S(() => [o("Sessions (" + y(t.dataset.sessions.length) + ")", 1)]),
1695
2288
  _: 1
1696
2289
  }),
1697
2290
  s(c, { value: "cards" }, {
1698
- default: x(() => [o("Cards (" + v(t.dataset.cardHistories.length) + ")", 1)]),
2291
+ default: S(() => [o("Cards (" + y(t.dataset.cardHistories.length) + ")", 1)]),
1699
2292
  _: 1
1700
2293
  }),
1701
- t.dataset.strategies ? (p(), n(c, {
2294
+ t.dataset.strategies ? (m(), n(c, {
1702
2295
  key: 0,
1703
2296
  value: "pipeline"
1704
2297
  }, {
1705
- default: x(() => a[3] || (a[3] = [o("Pipeline")])),
2298
+ default: S(() => a[3] || (a[3] = [o("Pipeline")])),
1706
2299
  _: 1
1707
- })) : r("", !0)
2300
+ })) : r("", !0),
2301
+ s(c, { value: "elo" }, {
2302
+ default: S(() => a[4] || (a[4] = [o("ELO")])),
2303
+ _: 1
2304
+ })
1708
2305
  ]),
1709
2306
  _: 1
1710
- }, 8, ["modelValue"]), l.value === "sessions" ? (p(), i(e, { key: 0 }, [u.value ? (p(), i(e, { key: 0 }, [s(h, {
2307
+ }, 8, ["modelValue"]), l.value === "sessions" ? (m(), i(e, { key: 0 }, [u.value ? (m(), i(e, { key: 0 }, [s(h, {
1711
2308
  variant: "text",
1712
2309
  size: "small",
1713
2310
  "prepend-icon": "mdi-arrow-left",
1714
2311
  class: "mb-2",
1715
2312
  onClick: a[1] || (a[1] = (e) => u.value = null)
1716
2313
  }, {
1717
- default: x(() => a[4] || (a[4] = [o(" All sessions ")])),
2314
+ default: S(() => a[5] || (a[5] = [o(" All sessions ")])),
1718
2315
  _: 1
1719
2316
  }), s(X, {
1720
2317
  dataset: t.dataset,
@@ -1725,12 +2322,12 @@ var G = {
1725
2322
  "dataset",
1726
2323
  "session-id",
1727
2324
  "interpreters"
1728
- ])], 64)) : (p(), n(Z, {
2325
+ ])], 64)) : (m(), n(Z, {
1729
2326
  key: 1,
1730
2327
  dataset: t.dataset,
1731
2328
  interpreters: t.interpreters,
1732
2329
  onOpen: a[2] || (a[2] = (e) => u.value = e)
1733
- }, null, 8, ["dataset", "interpreters"]))], 64)) : l.value === "cards" ? (p(), n(J, {
2330
+ }, null, 8, ["dataset", "interpreters"]))], 64)) : l.value === "cards" ? (m(), n(J, {
1734
2331
  key: 1,
1735
2332
  dataset: t.dataset,
1736
2333
  interpreters: t.interpreters,
@@ -1739,7 +2336,7 @@ var G = {
1739
2336
  "dataset",
1740
2337
  "interpreters",
1741
2338
  "focus"
1742
- ])) : l.value === "pipeline" && t.dataset.strategies ? (p(), n($, {
2339
+ ])) : l.value === "pipeline" && t.dataset.strategies ? (m(), n(Cr, {
1743
2340
  key: 2,
1744
2341
  strategies: t.dataset.strategies,
1745
2342
  "course-id": t.dataset.courseId,
@@ -1750,11 +2347,15 @@ var G = {
1750
2347
  "course-id",
1751
2348
  "stats",
1752
2349
  "stats-label"
1753
- ])) : r("", !0)]);
2350
+ ])) : l.value === "elo" ? (m(), n(Mn, {
2351
+ key: 3,
2352
+ dataset: t.dataset,
2353
+ interpreters: t.interpreters
2354
+ }, null, 8, ["dataset", "interpreters"])) : r("", !0)]);
1754
2355
  };
1755
2356
  }
1756
2357
  });
1757
2358
  //#endregion
1758
- export { q as CardDossierDetail, J as LearnerCardHistory, ce as LearnerDatasetSource, zn as LearnerDiagnostics, X as LearnerSessionDetail, Z as LearnerSessionList, $ as PipelineOverview, Y as RunDetail, downloadLearnerDump, useLearnerDataset };
2359
+ export { q as CardDossierDetail, J as LearnerCardHistory, xe as LearnerDatasetSource, wr as LearnerDiagnostics, X as LearnerSessionDetail, Z as LearnerSessionList, Mn as LearnerTagElo, Cr as PipelineOverview, Y as RunDetail, downloadLearnerDump, useLearnerDataset };
1759
2360
 
1760
2361
  //# sourceMappingURL=common-ui-admin.es.js.map