rita-workspace 0.5.14 → 0.5.16

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.mts CHANGED
@@ -116,6 +116,8 @@ interface Translations {
116
116
  moveToFolder: string;
117
117
  moveToRoot: string;
118
118
  newFolderName: string;
119
+ backupReminder: string;
120
+ days: string;
119
121
  shortcutNewDrawing: string;
120
122
  }
121
123
  declare function getTranslations(langCode?: string): Translations;
package/dist/index.d.ts CHANGED
@@ -116,6 +116,8 @@ interface Translations {
116
116
  moveToFolder: string;
117
117
  moveToRoot: string;
118
118
  newFolderName: string;
119
+ backupReminder: string;
120
+ days: string;
119
121
  shortcutNewDrawing: string;
120
122
  }
121
123
  declare function getTranslations(langCode?: string): Translations;
package/dist/index.js CHANGED
@@ -318,6 +318,9 @@ var sv = {
318
318
  moveToFolder: "Flytta till mapp",
319
319
  moveToRoot: "Ingen mapp",
320
320
  newFolderName: "Ny mapp",
321
+ // Backup reminder
322
+ backupReminder: "Senaste backup:",
323
+ days: "dagar sedan",
321
324
  // Shortcuts
322
325
  shortcutNewDrawing: "Ctrl+Alt+N"
323
326
  };
@@ -365,6 +368,9 @@ var en = {
365
368
  moveToFolder: "Move to folder",
366
369
  moveToRoot: "No folder",
367
370
  newFolderName: "New folder",
371
+ // Backup reminder
372
+ backupReminder: "Last backup:",
373
+ days: "days ago",
368
374
  // Shortcuts
369
375
  shortcutNewDrawing: "Ctrl+Alt+N"
370
376
  };
@@ -1430,14 +1436,18 @@ var DrawingsDialog = ({
1430
1436
  foldersRef.current = folders;
1431
1437
  (0, import_react5.useEffect)(() => {
1432
1438
  if (open) {
1433
- setIsRefreshing(true);
1434
- refreshDrawings().finally(() => setIsRefreshing(false));
1435
- if (!prevOpenRef.current) {
1439
+ const isFirstOpen = !prevOpenRef.current;
1440
+ if (isFirstOpen) {
1436
1441
  setPosition(null);
1437
1442
  setSearchQuery("");
1438
1443
  setSelectedId(null);
1439
- setExpandedFolders(new Set(foldersRef.current.map((f) => f.id)));
1440
1444
  }
1445
+ setIsRefreshing(true);
1446
+ refreshDrawings().then(() => {
1447
+ if (isFirstOpen) {
1448
+ setExpandedFolders(new Set(foldersRef.current.map((f) => f.id)));
1449
+ }
1450
+ }).finally(() => setIsRefreshing(false));
1441
1451
  }
1442
1452
  prevOpenRef.current = open;
1443
1453
  }, [open, refreshDrawings]);
@@ -1549,6 +1559,11 @@ var DrawingsDialog = ({
1549
1559
  minute: "2-digit"
1550
1560
  });
1551
1561
  };
1562
+ const daysSinceBackup = (0, import_react5.useMemo)(() => {
1563
+ const lastBackup = localStorage.getItem("rita-workspace-last-backup");
1564
+ if (!lastBackup) return drawings.length > 0 ? 999 : null;
1565
+ return Math.floor((Date.now() - parseInt(lastBackup, 10)) / (1e3 * 60 * 60 * 24));
1566
+ }, [drawings.length, open]);
1552
1567
  const { rootDrawings, drawingsByFolder, filteredFolders } = (0, import_react5.useMemo)(() => {
1553
1568
  const query = searchQuery.toLowerCase().trim();
1554
1569
  const filtered = query ? drawings.filter((d) => d.name.toLowerCase().includes(query)) : drawings;
@@ -1598,6 +1613,16 @@ var DrawingsDialog = ({
1598
1613
  const renderDrawingRow = (drawing) => /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
1599
1614
  "div",
1600
1615
  {
1616
+ draggable: !editingId && !confirmDeleteId,
1617
+ onDragStart: (e) => {
1618
+ setDraggingDrawingId(drawing.id);
1619
+ e.dataTransfer.effectAllowed = "move";
1620
+ e.dataTransfer.setData("text/plain", drawing.id);
1621
+ },
1622
+ onDragEnd: () => {
1623
+ setDraggingDrawingId(null);
1624
+ setDropTargetFolderId(null);
1625
+ },
1601
1626
  onMouseEnter: () => setHoveredId(drawing.id),
1602
1627
  onMouseLeave: () => setHoveredId(null),
1603
1628
  onClick: (e) => {
@@ -1612,40 +1637,13 @@ var DrawingsDialog = ({
1612
1637
  gap: "12px",
1613
1638
  borderRadius: "8px",
1614
1639
  marginBottom: "4px",
1615
- cursor: "pointer",
1640
+ cursor: draggingDrawingId ? "grabbing" : "pointer",
1616
1641
  backgroundColor: activeDrawing?.id === drawing.id ? "var(--color-primary-light, rgba(108, 99, 255, 0.1))" : selectedId === drawing.id ? "var(--color-primary-light, rgba(108, 99, 255, 0.06))" : "transparent",
1617
1642
  border: selectedId === drawing.id && activeDrawing?.id !== drawing.id ? "1px solid var(--color-primary, #6c63ff)" : "1px solid transparent",
1618
1643
  transition: "background-color 0.15s, border-color 0.15s",
1619
1644
  opacity: draggingDrawingId === drawing.id ? 0.4 : switchingId && switchingId !== drawing.id ? 0.5 : 1
1620
1645
  },
1621
1646
  children: [
1622
- /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
1623
- "span",
1624
- {
1625
- draggable: !editingId && !confirmDeleteId,
1626
- onDragStart: (e) => {
1627
- setDraggingDrawingId(drawing.id);
1628
- e.dataTransfer.effectAllowed = "move";
1629
- e.dataTransfer.setData("text/plain", drawing.id);
1630
- },
1631
- onDragEnd: () => {
1632
- setDraggingDrawingId(null);
1633
- setDropTargetFolderId(null);
1634
- },
1635
- onClick: (e) => e.stopPropagation(),
1636
- style: {
1637
- cursor: "grab",
1638
- fontSize: "14px",
1639
- color: "var(--text-secondary-color, #aaa)",
1640
- flexShrink: 0,
1641
- userSelect: "none",
1642
- padding: "4px 2px",
1643
- visibility: hoveredId === drawing.id || selectedId === drawing.id || draggingDrawingId === drawing.id ? "visible" : "hidden"
1644
- },
1645
- title: t.moveToFolder,
1646
- children: "\u283F"
1647
- }
1648
- ),
1649
1647
  renderThumbnail && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { style: {
1650
1648
  width: "64px",
1651
1649
  height: "48px",
@@ -2135,8 +2133,7 @@ var DrawingsDialog = ({
2135
2133
  icon: "\u{1F4C4}",
2136
2134
  label: t.createNewDrawing,
2137
2135
  description: t.createNewDrawingDesc,
2138
- onClick: () => handleCreate(),
2139
- primary: true
2136
+ onClick: () => handleCreate()
2140
2137
  }
2141
2138
  ),
2142
2139
  /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
@@ -2204,6 +2201,7 @@ var DrawingsDialog = ({
2204
2201
  )
2205
2202
  ] }),
2206
2203
  /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { style: sectionHeaderStyle, children: t.sectionWorkspace }),
2204
+ daysSinceBackup !== null && daysSinceBackup >= 7 && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { style: { padding: "0 20px 8px", fontSize: "12px", color: "var(--text-secondary-color, #888)" }, children: daysSinceBackup >= 30 ? `\u26A0\uFE0F ${t.backupReminder || "Ingen backup p\xE5"} ${daysSinceBackup} ${t.days || "dagar"}` : `${t.backupReminder || "Senaste backup:"} ${daysSinceBackup} ${t.days || "dagar sedan"}` }),
2207
2205
  /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)("div", { style: { padding: "0 20px 16px", display: "flex", gap: "8px" }, children: [
2208
2206
  /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
2209
2207
  ActionButton,
@@ -2211,7 +2209,10 @@ var DrawingsDialog = ({
2211
2209
  icon: "\u{1F4BE}",
2212
2210
  label: t.saveAllBackup,
2213
2211
  description: t.saveAllBackupDesc,
2214
- onClick: exportWorkspace
2212
+ onClick: () => {
2213
+ localStorage.setItem("rita-workspace-last-backup", Date.now().toString());
2214
+ exportWorkspace();
2215
+ }
2215
2216
  }
2216
2217
  ),
2217
2218
  /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
package/dist/index.mjs CHANGED
@@ -250,6 +250,9 @@ var sv = {
250
250
  moveToFolder: "Flytta till mapp",
251
251
  moveToRoot: "Ingen mapp",
252
252
  newFolderName: "Ny mapp",
253
+ // Backup reminder
254
+ backupReminder: "Senaste backup:",
255
+ days: "dagar sedan",
253
256
  // Shortcuts
254
257
  shortcutNewDrawing: "Ctrl+Alt+N"
255
258
  };
@@ -297,6 +300,9 @@ var en = {
297
300
  moveToFolder: "Move to folder",
298
301
  moveToRoot: "No folder",
299
302
  newFolderName: "New folder",
303
+ // Backup reminder
304
+ backupReminder: "Last backup:",
305
+ days: "days ago",
300
306
  // Shortcuts
301
307
  shortcutNewDrawing: "Ctrl+Alt+N"
302
308
  };
@@ -1362,14 +1368,18 @@ var DrawingsDialog = ({
1362
1368
  foldersRef.current = folders;
1363
1369
  useEffect3(() => {
1364
1370
  if (open) {
1365
- setIsRefreshing(true);
1366
- refreshDrawings().finally(() => setIsRefreshing(false));
1367
- if (!prevOpenRef.current) {
1371
+ const isFirstOpen = !prevOpenRef.current;
1372
+ if (isFirstOpen) {
1368
1373
  setPosition(null);
1369
1374
  setSearchQuery("");
1370
1375
  setSelectedId(null);
1371
- setExpandedFolders(new Set(foldersRef.current.map((f) => f.id)));
1372
1376
  }
1377
+ setIsRefreshing(true);
1378
+ refreshDrawings().then(() => {
1379
+ if (isFirstOpen) {
1380
+ setExpandedFolders(new Set(foldersRef.current.map((f) => f.id)));
1381
+ }
1382
+ }).finally(() => setIsRefreshing(false));
1373
1383
  }
1374
1384
  prevOpenRef.current = open;
1375
1385
  }, [open, refreshDrawings]);
@@ -1481,6 +1491,11 @@ var DrawingsDialog = ({
1481
1491
  minute: "2-digit"
1482
1492
  });
1483
1493
  };
1494
+ const daysSinceBackup = useMemo(() => {
1495
+ const lastBackup = localStorage.getItem("rita-workspace-last-backup");
1496
+ if (!lastBackup) return drawings.length > 0 ? 999 : null;
1497
+ return Math.floor((Date.now() - parseInt(lastBackup, 10)) / (1e3 * 60 * 60 * 24));
1498
+ }, [drawings.length, open]);
1484
1499
  const { rootDrawings, drawingsByFolder, filteredFolders } = useMemo(() => {
1485
1500
  const query = searchQuery.toLowerCase().trim();
1486
1501
  const filtered = query ? drawings.filter((d) => d.name.toLowerCase().includes(query)) : drawings;
@@ -1530,6 +1545,16 @@ var DrawingsDialog = ({
1530
1545
  const renderDrawingRow = (drawing) => /* @__PURE__ */ jsxs4(
1531
1546
  "div",
1532
1547
  {
1548
+ draggable: !editingId && !confirmDeleteId,
1549
+ onDragStart: (e) => {
1550
+ setDraggingDrawingId(drawing.id);
1551
+ e.dataTransfer.effectAllowed = "move";
1552
+ e.dataTransfer.setData("text/plain", drawing.id);
1553
+ },
1554
+ onDragEnd: () => {
1555
+ setDraggingDrawingId(null);
1556
+ setDropTargetFolderId(null);
1557
+ },
1533
1558
  onMouseEnter: () => setHoveredId(drawing.id),
1534
1559
  onMouseLeave: () => setHoveredId(null),
1535
1560
  onClick: (e) => {
@@ -1544,40 +1569,13 @@ var DrawingsDialog = ({
1544
1569
  gap: "12px",
1545
1570
  borderRadius: "8px",
1546
1571
  marginBottom: "4px",
1547
- cursor: "pointer",
1572
+ cursor: draggingDrawingId ? "grabbing" : "pointer",
1548
1573
  backgroundColor: activeDrawing?.id === drawing.id ? "var(--color-primary-light, rgba(108, 99, 255, 0.1))" : selectedId === drawing.id ? "var(--color-primary-light, rgba(108, 99, 255, 0.06))" : "transparent",
1549
1574
  border: selectedId === drawing.id && activeDrawing?.id !== drawing.id ? "1px solid var(--color-primary, #6c63ff)" : "1px solid transparent",
1550
1575
  transition: "background-color 0.15s, border-color 0.15s",
1551
1576
  opacity: draggingDrawingId === drawing.id ? 0.4 : switchingId && switchingId !== drawing.id ? 0.5 : 1
1552
1577
  },
1553
1578
  children: [
1554
- /* @__PURE__ */ jsx6(
1555
- "span",
1556
- {
1557
- draggable: !editingId && !confirmDeleteId,
1558
- onDragStart: (e) => {
1559
- setDraggingDrawingId(drawing.id);
1560
- e.dataTransfer.effectAllowed = "move";
1561
- e.dataTransfer.setData("text/plain", drawing.id);
1562
- },
1563
- onDragEnd: () => {
1564
- setDraggingDrawingId(null);
1565
- setDropTargetFolderId(null);
1566
- },
1567
- onClick: (e) => e.stopPropagation(),
1568
- style: {
1569
- cursor: "grab",
1570
- fontSize: "14px",
1571
- color: "var(--text-secondary-color, #aaa)",
1572
- flexShrink: 0,
1573
- userSelect: "none",
1574
- padding: "4px 2px",
1575
- visibility: hoveredId === drawing.id || selectedId === drawing.id || draggingDrawingId === drawing.id ? "visible" : "hidden"
1576
- },
1577
- title: t.moveToFolder,
1578
- children: "\u283F"
1579
- }
1580
- ),
1581
1579
  renderThumbnail && /* @__PURE__ */ jsx6("div", { style: {
1582
1580
  width: "64px",
1583
1581
  height: "48px",
@@ -2067,8 +2065,7 @@ var DrawingsDialog = ({
2067
2065
  icon: "\u{1F4C4}",
2068
2066
  label: t.createNewDrawing,
2069
2067
  description: t.createNewDrawingDesc,
2070
- onClick: () => handleCreate(),
2071
- primary: true
2068
+ onClick: () => handleCreate()
2072
2069
  }
2073
2070
  ),
2074
2071
  /* @__PURE__ */ jsx6(
@@ -2136,6 +2133,7 @@ var DrawingsDialog = ({
2136
2133
  )
2137
2134
  ] }),
2138
2135
  /* @__PURE__ */ jsx6("div", { style: sectionHeaderStyle, children: t.sectionWorkspace }),
2136
+ daysSinceBackup !== null && daysSinceBackup >= 7 && /* @__PURE__ */ jsx6("div", { style: { padding: "0 20px 8px", fontSize: "12px", color: "var(--text-secondary-color, #888)" }, children: daysSinceBackup >= 30 ? `\u26A0\uFE0F ${t.backupReminder || "Ingen backup p\xE5"} ${daysSinceBackup} ${t.days || "dagar"}` : `${t.backupReminder || "Senaste backup:"} ${daysSinceBackup} ${t.days || "dagar sedan"}` }),
2139
2137
  /* @__PURE__ */ jsxs4("div", { style: { padding: "0 20px 16px", display: "flex", gap: "8px" }, children: [
2140
2138
  /* @__PURE__ */ jsx6(
2141
2139
  ActionButton,
@@ -2143,7 +2141,10 @@ var DrawingsDialog = ({
2143
2141
  icon: "\u{1F4BE}",
2144
2142
  label: t.saveAllBackup,
2145
2143
  description: t.saveAllBackupDesc,
2146
- onClick: exportWorkspace
2144
+ onClick: () => {
2145
+ localStorage.setItem("rita-workspace-last-backup", Date.now().toString());
2146
+ exportWorkspace();
2147
+ }
2147
2148
  }
2148
2149
  ),
2149
2150
  /* @__PURE__ */ jsx6(
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "rita-workspace",
3
- "version": "0.5.14",
3
+ "version": "0.5.16",
4
4
  "description": "Multi-drawing workspace feature for Rita (Excalidraw fork)",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",