@local-civics/mgmt-ui 0.1.53 → 0.1.55

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.
package/dist/index.d.ts CHANGED
@@ -4,18 +4,28 @@ import * as React from 'react';
4
4
  /**
5
5
  * Item
6
6
  */
7
- interface Item$g {
7
+ interface Item$i {
8
+ lessonName: string;
9
+ isStarted?: boolean;
10
+ isComplete?: boolean;
11
+ }
12
+
13
+ /**
14
+ * Item
15
+ */
16
+ interface Item$h {
8
17
  userId: string;
9
18
  avatar: string;
10
19
  name: string;
11
20
  email: string;
12
21
  isComplete?: boolean;
22
+ lessons: Item$i[];
13
23
  }
14
24
 
15
25
  /**
16
26
  * Item
17
27
  */
18
- interface Item$f {
28
+ interface Item$g {
19
29
  lessonId: string;
20
30
  lessonName: string;
21
31
  percentageCompletion: number;
@@ -24,7 +34,7 @@ interface Item$f {
24
34
  /**
25
35
  * BadgeUserItem
26
36
  */
27
- type BadgeUserItem = Item$g;
37
+ type BadgeUserItem = Item$h;
28
38
  /**
29
39
  * BadgeClass
30
40
  */
@@ -41,14 +51,14 @@ type BadgeProps = {
41
51
  displayName: string;
42
52
  description: string;
43
53
  classes: BadgeClass[];
44
- lessons: Item$f[];
54
+ lessons: Item$g[];
45
55
  classId: string;
46
56
  students: BadgeUserItem[];
47
57
  onBackClick: () => void;
48
58
  onClassChange: (classId: string) => void;
49
59
  onPreviewClick: () => void;
50
60
  onUserClick: (user: BadgeUserItem) => void;
51
- onLessonClick: (lesson: Item$f) => void;
61
+ onLessonClick: (lesson: Item$g) => void;
52
62
  };
53
63
  /**
54
64
  * Badge
@@ -60,7 +70,7 @@ declare const Badge: (props: BadgeProps) => JSX.Element;
60
70
  /**
61
71
  * Item
62
72
  */
63
- interface Item$e {
73
+ interface Item$f {
64
74
  badgeId: string;
65
75
  name: string;
66
76
  description: string;
@@ -69,7 +79,7 @@ interface Item$e {
69
79
  /**
70
80
  * BadgeItem
71
81
  */
72
- type BadgeItem = Item$e;
82
+ type BadgeItem = Item$f;
73
83
  /**
74
84
  * BadgesProps
75
85
  */
@@ -89,7 +99,7 @@ declare const Badges: (props: BadgesProps) => JSX.Element;
89
99
  /**
90
100
  * Item
91
101
  */
92
- interface Item$d {
102
+ interface Item$e {
93
103
  studentId: string;
94
104
  studentName: string;
95
105
  className: string;
@@ -98,7 +108,7 @@ interface Item$d {
98
108
  /**
99
109
  * Item
100
110
  */
101
- interface Item$c {
111
+ interface Item$d {
102
112
  lessonName: string;
103
113
  studentName: string;
104
114
  reflection: string;
@@ -108,7 +118,7 @@ interface Item$c {
108
118
  /**
109
119
  * Item
110
120
  */
111
- interface Item$b {
121
+ interface Item$c {
112
122
  studentName: string;
113
123
  impactStatement: string;
114
124
  }
@@ -116,7 +126,7 @@ interface Item$b {
116
126
  /**
117
127
  * Item
118
128
  */
119
- interface Item$a {
129
+ interface Item$b {
120
130
  badgeId: string;
121
131
  name: string;
122
132
  description: string;
@@ -126,7 +136,7 @@ interface Item$a {
126
136
  /**
127
137
  * Item
128
138
  */
129
- interface Item$9 {
139
+ interface Item$a {
130
140
  lessonId: string;
131
141
  name: string;
132
142
  description: string;
@@ -145,20 +155,20 @@ type DashboardClass = {
145
155
  */
146
156
  type DashboardProps = {
147
157
  loading: boolean;
148
- students: Item$d[];
149
- impacts: Item$b[];
150
- reflections: Item$c[];
158
+ students: Item$e[];
159
+ impacts: Item$c[];
160
+ reflections: Item$d[];
151
161
  classes: DashboardClass[];
152
- badges: Item$a[];
153
- lessons: Item$9[];
162
+ badges: Item$b[];
163
+ lessons: Item$a[];
154
164
  classId: string;
155
165
  percentageOfAccountsCreated: number;
156
166
  percentageOfBadgesEarned: number;
157
167
  percentageOfLessonsCompleted: number;
158
168
  onClassChange: (classId: string) => void;
159
- onViewStudentProfile: (student: Item$d) => void;
160
- onBadgeClick: (badge: Item$a) => void;
161
- onLessonClick: (lesson: Item$9) => void;
169
+ onViewStudentProfile: (student: Item$e) => void;
170
+ onBadgeClick: (badge: Item$b) => void;
171
+ onLessonClick: (lesson: Item$a) => void;
162
172
  };
163
173
  /**
164
174
  * Dashboard
@@ -170,7 +180,7 @@ declare const Dashboard: (props: DashboardProps) => JSX.Element;
170
180
  /**
171
181
  * Item
172
182
  */
173
- type Item$8 = {
183
+ type Item$9 = {
174
184
  classId: string;
175
185
  studentId: string;
176
186
  avatar: string;
@@ -187,7 +197,7 @@ type Item$8 = {
187
197
  /**
188
198
  * StudentItem
189
199
  */
190
- type StudentItem = Item$8;
200
+ type StudentItem = Item$9;
191
201
  /**
192
202
  * ClassProps
193
203
  */
@@ -203,6 +213,7 @@ type ClassProps = {
203
213
  onCreateStudents: (students: StudentItem[]) => void;
204
214
  onDeleteStudent: (student: StudentItem) => void;
205
215
  onStudentClick: (student: StudentItem) => void;
216
+ onCopyLinkClick: () => void;
206
217
  };
207
218
  /**
208
219
  * Class
@@ -214,7 +225,7 @@ declare const Class: (props: ClassProps) => JSX.Element;
214
225
  /**
215
226
  * Item
216
227
  */
217
- type Item$7 = {
228
+ type Item$8 = {
218
229
  classId: string;
219
230
  name: string;
220
231
  description: string;
@@ -223,7 +234,7 @@ type Item$7 = {
223
234
  /**
224
235
  * ClassItem
225
236
  */
226
- type ClassItem = Item$7;
237
+ type ClassItem = Item$8;
227
238
  /**
228
239
  * ClassesProps
229
240
  */
@@ -244,7 +255,7 @@ declare const Classes: (props: ClassesProps) => JSX.Element;
244
255
  /**
245
256
  * Item
246
257
  */
247
- interface Item$6 {
258
+ interface Item$7 {
248
259
  badgeId: string;
249
260
  badgeName: string;
250
261
  isComplete?: boolean;
@@ -253,7 +264,7 @@ interface Item$6 {
253
264
  /**
254
265
  * Item
255
266
  */
256
- interface Item$5 {
267
+ interface Item$6 {
257
268
  lessonId: string;
258
269
  lessonName: string;
259
270
  questionName: string;
@@ -263,7 +274,7 @@ interface Item$5 {
263
274
  /**
264
275
  * Item
265
276
  */
266
- interface Item$4 {
277
+ interface Item$5 {
267
278
  lessonId: string;
268
279
  lessonName: string;
269
280
  reflection: string;
@@ -279,13 +290,13 @@ type StudentProps = {
279
290
  impactStatement: string;
280
291
  numberOfProblemsSolved: number;
281
292
  percentageOfLessonsCompleted: number;
282
- badges: Item$6[];
283
- answers: Item$5[];
284
- reflections: Item$4[];
293
+ badges: Item$7[];
294
+ answers: Item$6[];
295
+ reflections: Item$5[];
285
296
  onBackClick: () => void;
286
- onBadgeClick: (item: Item$6) => void;
287
- onAnswerClick: (item: Item$5) => void;
288
- onReflectionClick: (item: Item$4) => void;
297
+ onBadgeClick: (item: Item$7) => void;
298
+ onAnswerClick: (item: Item$6) => void;
299
+ onReflectionClick: (item: Item$5) => void;
289
300
  };
290
301
  declare const Student: (props: StudentProps) => JSX.Element;
291
302
 
@@ -318,12 +329,20 @@ declare const Home: (props: HomeProps) => JSX.Element;
318
329
  /**
319
330
  * Item
320
331
  */
321
- interface Item$3 {
332
+ interface Item$4 {
322
333
  studentName: string;
323
334
  reflection: string;
324
335
  rating: number;
325
336
  }
326
337
 
338
+ /**
339
+ * Item
340
+ */
341
+ interface Item$3 {
342
+ questionName: string;
343
+ answer: string[];
344
+ }
345
+
327
346
  /**
328
347
  * Item
329
348
  */
@@ -332,6 +351,7 @@ interface Item$2 {
332
351
  avatar: string;
333
352
  name: string;
334
353
  email: string;
354
+ answers: Item$3[];
335
355
  isStarted?: boolean;
336
356
  isComplete?: boolean;
337
357
  }
@@ -368,7 +388,7 @@ type LessonProps = {
368
388
  classId: string;
369
389
  classes: LessonClass[];
370
390
  students: LessonUserItem[];
371
- reflections: Item$3[];
391
+ reflections: Item$4[];
372
392
  questions: Item$1[];
373
393
  onBackClick: () => void;
374
394
  onClassChange: (classId: string) => void;
package/dist/index.js CHANGED
@@ -4,6 +4,7 @@ var notifications = require('@mantine/notifications');
4
4
  var icons = require('@tabler/icons');
5
5
  var React = require('react');
6
6
  var core = require('@mantine/core');
7
+ var mantineDatatable = require('mantine-datatable');
7
8
  var dropzone = require('@mantine/dropzone');
8
9
  var form = require('@mantine/form');
9
10
  var papa = require('papaparse');
@@ -30,7 +31,7 @@ function _interopNamespaceDefault(e) {
30
31
  var React__namespace = /*#__PURE__*/_interopNamespaceDefault(React);
31
32
  var papa__namespace = /*#__PURE__*/_interopNamespaceDefault(papa);
32
33
 
33
- const useStyles$c = core.createStyles((theme) => ({
34
+ const useStyles$d = core.createStyles((theme) => ({
34
35
  root: {
35
36
  display: "flex",
36
37
  backgroundImage: `linear-gradient(-60deg, ${theme.colors[theme.primaryColor][4]} 0%, ${theme.colors[theme.primaryColor][7]} 100%)`,
@@ -77,7 +78,7 @@ const useStyles$c = core.createStyles((theme) => ({
77
78
  }
78
79
  }));
79
80
  const StatsGroup = ({ data }) => {
80
- const { classes } = useStyles$c();
81
+ const { classes } = useStyles$d();
81
82
  const stats = data.map((stat) => {
82
83
  const value = (() => {
83
84
  if (stat.unit === "%") {
@@ -96,7 +97,7 @@ const Tabs = (props) => {
96
97
  return /* @__PURE__ */ React__namespace.createElement(core.Tabs, { value: props.value, onTabChange: props.onChange }, /* @__PURE__ */ React__namespace.createElement(core.Tabs.List, null, tabs));
97
98
  };
98
99
 
99
- const useStyles$b = core.createStyles((theme) => ({
100
+ const useStyles$c = core.createStyles((theme) => ({
100
101
  wrapper: {
101
102
  display: "flex",
102
103
  alignItems: "center",
@@ -147,12 +148,20 @@ const useStyles$b = core.createStyles((theme) => ({
147
148
  }
148
149
  }));
149
150
  const PlaceholderBanner = (props) => {
150
- const { classes } = useStyles$b();
151
+ const { classes } = useStyles$c();
151
152
  const title = props.title || "Nothing to display";
152
153
  const description = props.description || "We don't have anything to show you here just yet. Add data, check back later, or adjust your search.";
153
154
  return /* @__PURE__ */ React__namespace.createElement("div", { className: classes.wrapper }, /* @__PURE__ */ React__namespace.createElement("div", { className: classes.body }, /* @__PURE__ */ React__namespace.createElement(core.Title, { className: classes.title }, props.loading ? "Loading..." : title), /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "sm", color: "dimmed" }, props.loading ? "Hold on, we're loading your data." : description)), /* @__PURE__ */ React__namespace.createElement(core.Image, { src: `https://cdn.localcivics.io/illustrations/${props.icon}.svg`, className: classes.image }));
154
155
  };
155
156
 
157
+ function Stack$2(props) {
158
+ if (props.items.length === 0) {
159
+ return null;
160
+ }
161
+ const rows = props.items.map((row) => /* @__PURE__ */ React__namespace.createElement(React__namespace.Fragment, null, /* @__PURE__ */ React__namespace.createElement(core.Grid.Col, { span: 6 }, /* @__PURE__ */ React__namespace.createElement(core.Title, { color: "dark.4", size: "lg" }, row.lessonName)), /* @__PURE__ */ React__namespace.createElement(core.Grid.Col, { span: 6 }, !!row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { variant: "filled" }, "Complete"), !row.isComplete && !row.isStarted && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "red", variant: "filled" }, "Not started"), !row.isComplete && !!row.isStarted && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "violet", variant: "filled" }, "In progress"))));
162
+ return /* @__PURE__ */ React__namespace.createElement(core.Grid, { grow: true, gutter: "lg", sx: { padding: 20, minWidth: 700 } }, rows);
163
+ }
164
+
156
165
  function Table$f(props) {
157
166
  if (props.items.length === 0) {
158
167
  return /* @__PURE__ */ React__namespace.createElement(
@@ -165,8 +174,30 @@ function Table$f(props) {
165
174
  }
166
175
  );
167
176
  }
168
- const rows = props.items.map((row) => /* @__PURE__ */ React__namespace.createElement("tr", { key: row.name }, /* @__PURE__ */ React__namespace.createElement("td", null, /* @__PURE__ */ React__namespace.createElement(core.UnstyledButton, { onClick: () => props.onClick && props.onClick(row) }, /* @__PURE__ */ React__namespace.createElement(core.Group, { spacing: "sm" }, /* @__PURE__ */ React__namespace.createElement(core.Avatar, { size: 40, src: row.avatar, radius: 40 }), /* @__PURE__ */ React__namespace.createElement("div", null, /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "sm", weight: 500 }, row.name), /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "xs", color: "dimmed" }, row.email))))), /* @__PURE__ */ React__namespace.createElement("td", null, !!row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { variant: "filled" }, "Complete"), !row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "red", variant: "filled" }, "Incomplete"))));
169
- return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(core.Table, { verticalSpacing: "sm", sx: { minWidth: 700 }, highlightOnHover: true, striped: true }, /* @__PURE__ */ React__namespace.createElement("thead", null, /* @__PURE__ */ React__namespace.createElement("tr", null, /* @__PURE__ */ React__namespace.createElement("th", null, "Student Name"), /* @__PURE__ */ React__namespace.createElement("th", null, "Badge Status"))), /* @__PURE__ */ React__namespace.createElement("tbody", null, rows)));
177
+ return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(
178
+ mantineDatatable.DataTable,
179
+ {
180
+ verticalSpacing: "sm",
181
+ sx: { minWidth: 700 },
182
+ withBorder: false,
183
+ borderRadius: "sm",
184
+ withColumnBorders: true,
185
+ striped: true,
186
+ highlightOnHover: true,
187
+ records: props.items,
188
+ columns: [{
189
+ accessor: "name",
190
+ title: "Student Name",
191
+ render: (row) => /* @__PURE__ */ React__namespace.createElement(core.UnstyledButton, null, /* @__PURE__ */ React__namespace.createElement(core.Group, { spacing: "sm" }, /* @__PURE__ */ React__namespace.createElement(core.Avatar, { size: 40, src: row.avatar, radius: 40 }), /* @__PURE__ */ React__namespace.createElement("div", null, /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "sm", weight: 500 }, row.name), /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "xs", color: "dimmed" }, row.email))))
192
+ }, {
193
+ accessor: "status",
194
+ render: (row) => /* @__PURE__ */ React__namespace.createElement(React__namespace.Fragment, null, !!row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { variant: "filled" }, "Complete"), !row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "red", variant: "filled" }, "Incomplete"))
195
+ }],
196
+ rowExpansion: {
197
+ content: ({ record }) => /* @__PURE__ */ React__namespace.createElement(Stack$2, { items: record.lessons })
198
+ }
199
+ }
200
+ ));
170
201
  }
171
202
 
172
203
  function Table$e(props) {
@@ -188,7 +219,7 @@ function Table$e(props) {
188
219
  return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(core.Table, { verticalSpacing: "sm", sx: { minWidth: 700 }, highlightOnHover: true, striped: true }, /* @__PURE__ */ React__namespace.createElement("thead", null, /* @__PURE__ */ React__namespace.createElement("tr", null, /* @__PURE__ */ React__namespace.createElement("th", null, "Lesson Name"), /* @__PURE__ */ React__namespace.createElement("th", null, "Lesson Completion"))), /* @__PURE__ */ React__namespace.createElement("tbody", null, rows)));
189
220
  }
190
221
 
191
- const useStyles$a = core.createStyles((theme) => ({
222
+ const useStyles$b = core.createStyles((theme) => ({
192
223
  title: {
193
224
  fontSize: 34,
194
225
  fontWeight: 900,
@@ -201,7 +232,7 @@ const useStyles$a = core.createStyles((theme) => ({
201
232
  }
202
233
  }));
203
234
  const Badge = (props) => {
204
- const { classes } = useStyles$a();
235
+ const { classes } = useStyles$b();
205
236
  const [tab, setTab] = React.useState("lessons");
206
237
  const numberOfStudents = props.students.length;
207
238
  const percentageOfBadgesEarned = numberOfStudents > 0 ? props.students.filter((u) => u.isComplete).length / numberOfStudents : 0;
@@ -299,7 +330,7 @@ function Table$d(props) {
299
330
  return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(core.Table, { horizontalSpacing: 0, verticalSpacing: 0, sx: { minWidth: 700 } }, /* @__PURE__ */ React__namespace.createElement("tbody", null, rows)));
300
331
  }
301
332
 
302
- const useStyles$9 = core.createStyles((theme) => ({
333
+ const useStyles$a = core.createStyles((theme) => ({
303
334
  title: {
304
335
  fontSize: 34,
305
336
  fontWeight: 900,
@@ -312,7 +343,7 @@ const useStyles$9 = core.createStyles((theme) => ({
312
343
  }
313
344
  }));
314
345
  const Badges = (props) => {
315
- const { classes } = useStyles$9();
346
+ const { classes } = useStyles$a();
316
347
  return /* @__PURE__ */ React__namespace.createElement(core.Container, { size: "lg", py: "xl" }, /* @__PURE__ */ React__namespace.createElement(core.Stack, { spacing: "md" }, /* @__PURE__ */ React__namespace.createElement(core.Grid, null, /* @__PURE__ */ React__namespace.createElement(core.Grid.Col, { sm: "auto" }, /* @__PURE__ */ React__namespace.createElement(core.Badge, { variant: "filled", size: "lg" }, "Badges"), /* @__PURE__ */ React__namespace.createElement(core.Title, { order: 2, className: classes.title, mt: "md" }, "Badges and micro-credentials"), /* @__PURE__ */ React__namespace.createElement(core.Text, { color: "dimmed", className: classes.description, mt: "sm" }, "Project-sized skills acquisition and standards alignment."))), /* @__PURE__ */ React__namespace.createElement(
317
348
  core.Autocomplete,
318
349
  {
@@ -520,6 +551,50 @@ const Dashboard = (props) => {
520
551
  )))))));
521
552
  };
522
553
 
554
+ const useStyles$9 = core.createStyles((theme) => ({
555
+ button: {
556
+ borderTopRightRadius: 0,
557
+ borderBottomRightRadius: 0,
558
+ marginLeft: 0,
559
+ marginRight: 0
560
+ },
561
+ menuControl: {
562
+ borderTopLeftRadius: 0,
563
+ borderBottomLeftRadius: 0,
564
+ border: 0,
565
+ borderLeft: `1px solid ${theme.colorScheme === "dark" ? theme.colors.dark[7] : theme.white}`
566
+ }
567
+ }));
568
+ const SplitButton = (props) => {
569
+ const { classes, theme } = useStyles$9();
570
+ const menuIconColor = theme.colors[theme.primaryColor][theme.colorScheme === "dark" ? 5 : 6];
571
+ return /* @__PURE__ */ React__namespace.createElement(core.Group, { noWrap: true, spacing: 0 }, /* @__PURE__ */ React__namespace.createElement(
572
+ core.Button,
573
+ {
574
+ className: classes.button,
575
+ leftIcon: /* @__PURE__ */ React__namespace.createElement(icons.IconPlaylistAdd, { size: 14 }),
576
+ onClick: props.onAddStudentsClick
577
+ },
578
+ "Add students"
579
+ ), /* @__PURE__ */ React__namespace.createElement(core.Menu, { transition: "pop", position: "bottom-end" }, /* @__PURE__ */ React__namespace.createElement(core.Menu.Target, null, /* @__PURE__ */ React__namespace.createElement(
580
+ core.ActionIcon,
581
+ {
582
+ variant: "filled",
583
+ color: theme.primaryColor,
584
+ size: 36,
585
+ className: classes.menuControl
586
+ },
587
+ /* @__PURE__ */ React__namespace.createElement(icons.IconChevronDown, { size: 16, stroke: 1.5 })
588
+ )), /* @__PURE__ */ React__namespace.createElement(core.Menu.Dropdown, null, /* @__PURE__ */ React__namespace.createElement(
589
+ core.Menu.Item,
590
+ {
591
+ icon: /* @__PURE__ */ React__namespace.createElement(icons.IconClipboardCopy, { size: 16, stroke: 1.5, color: menuIconColor }),
592
+ onClick: props.onCopyClassLinkClick
593
+ },
594
+ "Copy class link"
595
+ ))));
596
+ };
597
+
523
598
  function Table$7(props) {
524
599
  if (props.items.length === 0) {
525
600
  return /* @__PURE__ */ React__namespace.createElement(
@@ -657,12 +732,11 @@ const Class = (props) => {
657
732
  },
658
733
  "Classes"
659
734
  ), /* @__PURE__ */ React__namespace.createElement(core.Title, { order: 2, className: classes.title, mt: "md" }, props.displayName || "Class"), /* @__PURE__ */ React__namespace.createElement(core.Text, { color: "dimmed", className: classes.description, mt: "sm" }, props.description || "No description")), /* @__PURE__ */ React__namespace.createElement(core.Grid.Col, { sm: "content" }, !props.loading && /* @__PURE__ */ React__namespace.createElement(
660
- core.Button,
735
+ SplitButton,
661
736
  {
662
- onClick: () => setOpened(true),
663
- leftIcon: /* @__PURE__ */ React__namespace.createElement(icons.IconPlaylistAdd, { size: 14 })
664
- },
665
- "Add students"
737
+ onAddStudentsClick: () => setOpened(true),
738
+ onCopyClassLinkClick: props.onCopyLinkClick
739
+ }
666
740
  ))), /* @__PURE__ */ React__namespace.createElement("div", { style: { position: "relative" } }, /* @__PURE__ */ React__namespace.createElement(core.LoadingOverlay, { visible: props.loading, overlayBlur: 2 }), /* @__PURE__ */ React__namespace.createElement(core.Stack, { spacing: "sm" }, /* @__PURE__ */ React__namespace.createElement(StatsGroup, { data: [
667
741
  {
668
742
  title: "# OF STUDENTS",
@@ -1206,6 +1280,14 @@ function Table$2(props) {
1206
1280
  return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(core.Table, { verticalSpacing: "sm", sx: { minWidth: 700 }, highlightOnHover: true, striped: true }, /* @__PURE__ */ React__namespace.createElement("thead", null, /* @__PURE__ */ React__namespace.createElement("tr", null, /* @__PURE__ */ React__namespace.createElement("th", null, "Student Name"), /* @__PURE__ */ React__namespace.createElement("th", null, "Reflection"), /* @__PURE__ */ React__namespace.createElement("th", null, "Rating"))), /* @__PURE__ */ React__namespace.createElement("tbody", null, rows)));
1207
1281
  }
1208
1282
 
1283
+ function Stack$1(props) {
1284
+ if (props.items.length === 0) {
1285
+ return null;
1286
+ }
1287
+ const rows = props.items.map((row) => /* @__PURE__ */ React__namespace.createElement(core.Stack, { spacing: 0, key: row.questionName }, /* @__PURE__ */ React__namespace.createElement(core.Title, { color: "dark.4", size: "lg" }, row.questionName), /* @__PURE__ */ React__namespace.createElement(core.Text, null, row.answer.join(",") || "No answer.")));
1288
+ return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(core.Stack, { spacing: 24, sx: { padding: 20, minWidth: 700 } }, rows));
1289
+ }
1290
+
1209
1291
  function Table$1(props) {
1210
1292
  if (props.items.length === 0) {
1211
1293
  return /* @__PURE__ */ React__namespace.createElement(
@@ -1218,8 +1300,30 @@ function Table$1(props) {
1218
1300
  }
1219
1301
  );
1220
1302
  }
1221
- const rows = props.items.map((row) => /* @__PURE__ */ React__namespace.createElement("tr", { key: row.name }, /* @__PURE__ */ React__namespace.createElement("td", null, /* @__PURE__ */ React__namespace.createElement(core.UnstyledButton, { onClick: () => props.onClick && props.onClick(row) }, /* @__PURE__ */ React__namespace.createElement(core.Group, { spacing: "sm" }, /* @__PURE__ */ React__namespace.createElement(core.Avatar, { size: 40, src: row.avatar, radius: 40 }), /* @__PURE__ */ React__namespace.createElement("div", null, /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "sm", weight: 500 }, row.name), /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "xs", color: "dimmed" }, row.email))))), /* @__PURE__ */ React__namespace.createElement("td", null, !!row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { variant: "filled" }, "Complete"), !row.isComplete && !row.isStarted && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "red", variant: "filled" }, "Not started"), !row.isComplete && !!row.isStarted && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "violet", variant: "filled" }, "In progress"))));
1222
- return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(core.Table, { verticalSpacing: "sm", sx: { minWidth: 700 }, highlightOnHover: true, striped: true }, /* @__PURE__ */ React__namespace.createElement("thead", null, /* @__PURE__ */ React__namespace.createElement("tr", null, /* @__PURE__ */ React__namespace.createElement("th", null, "Lesson Name"), /* @__PURE__ */ React__namespace.createElement("th", null, "Status"))), /* @__PURE__ */ React__namespace.createElement("tbody", null, rows)));
1303
+ return /* @__PURE__ */ React__namespace.createElement(core.ScrollArea.Autosize, { maxHeight: 500 }, /* @__PURE__ */ React__namespace.createElement(
1304
+ mantineDatatable.DataTable,
1305
+ {
1306
+ verticalSpacing: "sm",
1307
+ sx: { minWidth: 700 },
1308
+ withBorder: false,
1309
+ borderRadius: "sm",
1310
+ withColumnBorders: true,
1311
+ striped: true,
1312
+ highlightOnHover: true,
1313
+ records: props.items,
1314
+ columns: [{
1315
+ accessor: "name",
1316
+ title: "Student Name",
1317
+ render: (row) => /* @__PURE__ */ React__namespace.createElement(core.UnstyledButton, null, /* @__PURE__ */ React__namespace.createElement(core.Group, { spacing: "sm" }, /* @__PURE__ */ React__namespace.createElement(core.Avatar, { size: 40, src: row.avatar, radius: 40 }), /* @__PURE__ */ React__namespace.createElement("div", null, /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "sm", weight: 500 }, row.name), /* @__PURE__ */ React__namespace.createElement(core.Text, { size: "xs", color: "dimmed" }, row.email))))
1318
+ }, {
1319
+ accessor: "status",
1320
+ render: (row) => /* @__PURE__ */ React__namespace.createElement(React__namespace.Fragment, null, !!row.isComplete && /* @__PURE__ */ React__namespace.createElement(core.Badge, { variant: "filled" }, "Complete"), !row.isComplete && !row.isStarted && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "red", variant: "filled" }, "Not started"), !row.isComplete && !!row.isStarted && /* @__PURE__ */ React__namespace.createElement(core.Badge, { color: "violet", variant: "filled" }, "In progress"))
1321
+ }],
1322
+ rowExpansion: {
1323
+ content: ({ record }) => /* @__PURE__ */ React__namespace.createElement(Stack$1, { items: record.answers })
1324
+ }
1325
+ }
1326
+ ));
1223
1327
  }
1224
1328
 
1225
1329
  function Stack(props) {
@@ -1349,8 +1453,8 @@ const Lesson = (props) => {
1349
1453
  value: tab,
1350
1454
  data: [
1351
1455
  { label: "By question", value: "question" },
1352
- { label: "By reflection", value: "reflections" },
1353
- { label: "By student", value: "students" }
1456
+ { label: "By student", value: "students" },
1457
+ { label: "By reflection", value: "reflections" }
1354
1458
  ],
1355
1459
  onChange: setTab
1356
1460
  }