@dyrected/admin 2.4.0 → 2.4.1

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 (170) hide show
  1. package/dist/App.d.ts +1 -0
  2. package/dist/admin.css +2 -0
  3. package/dist/components/auth/auth-gate.d.ts +13 -0
  4. package/dist/components/error-boundary.d.ts +16 -0
  5. package/dist/components/forms/field-renderer.d.ts +22 -0
  6. package/dist/components/forms/fields/block-builder.d.ts +9 -0
  7. package/dist/components/forms/fields/date-picker.d.ts +8 -0
  8. package/dist/components/forms/fields/json-editor.d.ts +8 -0
  9. package/dist/components/forms/fields/media-picker.d.ts +12 -0
  10. package/dist/components/forms/fields/multi-select.d.ts +19 -0
  11. package/dist/components/forms/fields/radio-field.d.ts +8 -0
  12. package/dist/components/forms/fields/relationship-picker.d.ts +10 -0
  13. package/dist/components/forms/fields/rich-text-editor.d.ts +9 -0
  14. package/dist/components/forms/fields/select-field.d.ts +8 -0
  15. package/dist/components/forms/fields/switch-field.d.ts +6 -0
  16. package/dist/components/forms/fields/text-area-field.d.ts +8 -0
  17. package/dist/components/forms/fields/text-field.d.ts +8 -0
  18. package/dist/components/forms/form-engine.d.ts +14 -0
  19. package/dist/components/forms/form-field-renderer.d.ts +20 -0
  20. package/dist/components/forms/utils.d.ts +11 -0
  21. package/dist/components/layout/admin-shell.d.ts +5 -0
  22. package/dist/components/layout/branding-provider.d.ts +4 -0
  23. package/dist/components/live-preview/LivePreviewPane.d.ts +7 -0
  24. package/dist/components/media/focal-point-picker.d.ts +12 -0
  25. package/dist/components/media/media-card.d.ts +8 -0
  26. package/dist/components/media/media-grid.d.ts +8 -0
  27. package/dist/components/media/media-library-dialog.d.ts +11 -0
  28. package/dist/components/ui/aspect-ratio.d.ts +3 -0
  29. package/dist/components/ui/badge.d.ts +9 -0
  30. package/dist/components/ui/button.d.ts +11 -0
  31. package/dist/components/ui/calendar.d.ts +8 -0
  32. package/dist/components/ui/card.d.ts +8 -0
  33. package/dist/components/ui/checkbox.d.ts +4 -0
  34. package/dist/components/ui/command.d.ts +80 -0
  35. package/dist/components/ui/data-table.d.ts +14 -0
  36. package/dist/components/ui/dialog.d.ts +19 -0
  37. package/dist/components/ui/dropdown-menu.d.ts +27 -0
  38. package/dist/components/ui/form.d.ts +23 -0
  39. package/dist/components/ui/input.d.ts +3 -0
  40. package/dist/components/ui/label.d.ts +5 -0
  41. package/dist/components/ui/page-header.d.ts +10 -0
  42. package/dist/components/ui/pagination.d.ts +11 -0
  43. package/dist/components/ui/popover.d.ts +6 -0
  44. package/dist/components/ui/progress.d.ts +4 -0
  45. package/dist/components/ui/radio-group.d.ts +5 -0
  46. package/dist/components/ui/render-cell.d.ts +8 -0
  47. package/dist/components/ui/scroll-area.d.ts +5 -0
  48. package/dist/components/ui/select.d.ts +13 -0
  49. package/dist/components/ui/separator.d.ts +4 -0
  50. package/dist/components/ui/sheet.d.ts +25 -0
  51. package/dist/components/ui/sidebar.d.ts +65 -0
  52. package/dist/components/ui/skeleton.d.ts +2 -0
  53. package/dist/components/ui/sonner.d.ts +4 -0
  54. package/dist/components/ui/switch.d.ts +4 -0
  55. package/dist/components/ui/table.d.ts +10 -0
  56. package/dist/components/ui/tabs.d.ts +7 -0
  57. package/dist/components/ui/textarea.d.ts +3 -0
  58. package/dist/components/ui/toggle.d.ts +12 -0
  59. package/dist/components/ui/tooltip.d.ts +7 -0
  60. package/dist/hooks/use-mobile.d.ts +1 -0
  61. package/dist/hooks/use-preferences.d.ts +6 -0
  62. package/dist/index.d.ts +38 -0
  63. package/dist/index.mjs +69091 -0
  64. package/dist/lib/utils.d.ts +3 -0
  65. package/dist/main.d.ts +0 -0
  66. package/dist/pages/auth/first-user-page.d.ts +4 -0
  67. package/dist/pages/auth/login-page.d.ts +4 -0
  68. package/dist/pages/collections/edit-page.d.ts +1 -0
  69. package/dist/pages/collections/list-page.d.ts +5 -0
  70. package/dist/pages/dashboard/dashboard.d.ts +1 -0
  71. package/dist/pages/globals/editor-page.d.ts +1 -0
  72. package/dist/pages/media/media-page.d.ts +4 -0
  73. package/dist/pages/setup/setup-prompt.d.ts +6 -0
  74. package/dist/providers/dyrected-provider.d.ts +29 -0
  75. package/dist/providers/query-provider.d.ts +3 -0
  76. package/package.json +6 -3
  77. package/CHANGELOG.md +0 -153
  78. package/components.json +0 -17
  79. package/eslint.config.js +0 -22
  80. package/index.html +0 -13
  81. package/postcss.config.js +0 -6
  82. package/scripts/prefix-tailwind-precision.py +0 -98
  83. package/scripts/prefix-tailwind.py +0 -67
  84. package/src/App.css +0 -184
  85. package/src/App.tsx +0 -25
  86. package/src/assets/dyrected.svg +0 -155
  87. package/src/assets/hero.png +0 -0
  88. package/src/assets/react.svg +0 -1
  89. package/src/assets/vite.svg +0 -1
  90. package/src/components/auth/auth-gate.tsx +0 -64
  91. package/src/components/error-boundary.tsx +0 -45
  92. package/src/components/forms/field-renderer.tsx +0 -111
  93. package/src/components/forms/fields/block-builder.tsx +0 -213
  94. package/src/components/forms/fields/date-picker.tsx +0 -60
  95. package/src/components/forms/fields/json-editor.tsx +0 -62
  96. package/src/components/forms/fields/media-picker.tsx +0 -286
  97. package/src/components/forms/fields/multi-select.tsx +0 -145
  98. package/src/components/forms/fields/radio-field.tsx +0 -51
  99. package/src/components/forms/fields/relationship-picker.tsx +0 -143
  100. package/src/components/forms/fields/rich-text-editor.tsx +0 -224
  101. package/src/components/forms/fields/select-field.tsx +0 -35
  102. package/src/components/forms/fields/switch-field.tsx +0 -16
  103. package/src/components/forms/fields/text-area-field.tsx +0 -15
  104. package/src/components/forms/fields/text-field.tsx +0 -24
  105. package/src/components/forms/form-engine.tsx +0 -87
  106. package/src/components/forms/form-field-renderer.tsx +0 -269
  107. package/src/components/forms/utils.ts +0 -97
  108. package/src/components/layout/admin-shell.tsx +0 -479
  109. package/src/components/layout/branding-provider.tsx +0 -112
  110. package/src/components/live-preview/LivePreviewPane.tsx +0 -128
  111. package/src/components/media/focal-point-picker.tsx +0 -66
  112. package/src/components/media/media-card.tsx +0 -44
  113. package/src/components/media/media-grid.tsx +0 -32
  114. package/src/components/media/media-library-dialog.tsx +0 -465
  115. package/src/components/ui/aspect-ratio.tsx +0 -7
  116. package/src/components/ui/badge.tsx +0 -36
  117. package/src/components/ui/button.tsx +0 -56
  118. package/src/components/ui/calendar.tsx +0 -214
  119. package/src/components/ui/card.tsx +0 -79
  120. package/src/components/ui/checkbox.tsx +0 -28
  121. package/src/components/ui/command.tsx +0 -151
  122. package/src/components/ui/data-table.tsx +0 -219
  123. package/src/components/ui/dialog.tsx +0 -122
  124. package/src/components/ui/dropdown-menu.tsx +0 -200
  125. package/src/components/ui/form.tsx +0 -178
  126. package/src/components/ui/input.tsx +0 -24
  127. package/src/components/ui/label.tsx +0 -24
  128. package/src/components/ui/page-header.tsx +0 -30
  129. package/src/components/ui/pagination.tsx +0 -57
  130. package/src/components/ui/popover.tsx +0 -29
  131. package/src/components/ui/progress.tsx +0 -26
  132. package/src/components/ui/radio-group.tsx +0 -42
  133. package/src/components/ui/render-cell.tsx +0 -110
  134. package/src/components/ui/scroll-area.tsx +0 -46
  135. package/src/components/ui/select.tsx +0 -160
  136. package/src/components/ui/separator.tsx +0 -29
  137. package/src/components/ui/sheet.tsx +0 -140
  138. package/src/components/ui/sidebar.tsx +0 -771
  139. package/src/components/ui/skeleton.tsx +0 -15
  140. package/src/components/ui/sonner.tsx +0 -27
  141. package/src/components/ui/switch.tsx +0 -27
  142. package/src/components/ui/table.tsx +0 -117
  143. package/src/components/ui/tabs.tsx +0 -53
  144. package/src/components/ui/textarea.tsx +0 -22
  145. package/src/components/ui/toggle.tsx +0 -43
  146. package/src/components/ui/tooltip.tsx +0 -28
  147. package/src/hooks/use-mobile.tsx +0 -19
  148. package/src/hooks/use-preferences.ts +0 -56
  149. package/src/index.css +0 -111
  150. package/src/index.tsx +0 -198
  151. package/src/lib/utils.ts +0 -36
  152. package/src/main.tsx +0 -10
  153. package/src/pages/auth/first-user-page.tsx +0 -115
  154. package/src/pages/auth/login-page.tsx +0 -91
  155. package/src/pages/collections/edit-page.tsx +0 -280
  156. package/src/pages/collections/list-page.tsx +0 -343
  157. package/src/pages/dashboard/dashboard.tsx +0 -150
  158. package/src/pages/globals/editor-page.tsx +0 -122
  159. package/src/pages/media/media-page.tsx +0 -564
  160. package/src/pages/setup/setup-prompt.tsx +0 -181
  161. package/src/providers/dyrected-provider.tsx +0 -122
  162. package/src/providers/query-provider.tsx +0 -19
  163. package/src/types/jexl.d.ts +0 -11
  164. package/tailwind.config.ts +0 -103
  165. package/tsconfig.app.json +0 -28
  166. package/tsconfig.json +0 -12
  167. package/tsconfig.node.json +0 -25
  168. package/vite.config.ts +0 -39
  169. /package/{public → dist}/favicon.svg +0 -0
  170. /package/{public → dist}/icons.svg +0 -0
@@ -1,128 +0,0 @@
1
- import { useEffect, useRef, useState } from 'react';
2
- import { Button } from '../ui/button';
3
- import { ExternalLink, Smartphone, Monitor, RotateCcw } from 'lucide-react';
4
-
5
- interface LivePreviewPaneProps {
6
- previewUrl: string;
7
- data: any;
8
- mode?: 'postMessage' | 'token';
9
- }
10
-
11
- export function LivePreviewPane({ previewUrl, data, mode = 'postMessage' }: LivePreviewPaneProps) {
12
- const iframeRef = useRef<HTMLIFrameElement>(null);
13
- const [isReady, setIsReady] = useState(false);
14
- const [viewMode, setViewMode] = useState<'desktop' | 'mobile'>('desktop');
15
- const [zoom, setZoom] = useState(0.50); // 85% zoom by default for desktop
16
-
17
- // Handle postMessage communication
18
- useEffect(() => {
19
- if (mode !== 'postMessage') return;
20
-
21
- const handleMessage = (event: MessageEvent) => {
22
- if (event.data?.type === 'dyrected-live-preview-ready') {
23
- setIsReady(true);
24
- // Send initial data once ready
25
- iframeRef.current?.contentWindow?.postMessage(
26
- { type: 'dyrected-live-preview', data },
27
- '*'
28
- );
29
- }
30
- };
31
-
32
- window.addEventListener('message', handleMessage);
33
- return () => window.removeEventListener('message', handleMessage);
34
- }, [mode, data]);
35
-
36
- // Sync data whenever it changes
37
- useEffect(() => {
38
- if (mode === 'postMessage' && isReady) {
39
- iframeRef.current?.contentWindow?.postMessage(
40
- { type: 'dyrected-live-preview', data },
41
- '*'
42
- );
43
- }
44
- }, [data, isReady, mode]);
45
-
46
- const reload = () => {
47
- if (iframeRef.current) {
48
- iframeRef.current.src = previewUrl;
49
- setIsReady(false);
50
- }
51
- };
52
-
53
- return (
54
- <div className="dy-flex dy-flex-col dy-h-full dy-bg-muted/20 dy-border-l dy-border-border/60">
55
- <div className="dy-flex dy-items-center dy-justify-between dy-px-4 dy-py-2 dy-bg-white dy-border-b dy-border-border/40">
56
- <div className="dy-flex dy-items-center dy-gap-2">
57
- <Button
58
- variant="ghost"
59
- size="icon"
60
- className={`h-8 w-8 ${viewMode === 'desktop' ? 'bg-muted' : ''}`}
61
- onClick={() => setViewMode('desktop')}
62
- >
63
- <Monitor className="dy-h-4 dy-w-4" />
64
- </Button>
65
- <Button
66
- variant="ghost"
67
- size="icon"
68
- className={`h-8 w-8 ${viewMode === 'mobile' ? 'bg-muted' : ''}`}
69
- onClick={() => setViewMode('mobile')}
70
- >
71
- <Smartphone className="dy-h-4 dy-w-4" />
72
- </Button>
73
-
74
- {viewMode === 'desktop' && (
75
- <div className="dy-flex dy-items-center dy-gap-1 dy-ml-2 dy-pl-2 dy-border-l dy-border-border/40">
76
- <span className="dy-text-[10px] dy-font-bold dy-text-muted-foreground/50 dy-uppercase dy-tracking-wider dy-mr-1">Zoom</span>
77
- {[0.50, 0.75, 1.0].map((z) => (
78
- <Button
79
- key={z}
80
- variant="ghost"
81
- size="sm"
82
- className={`h-7 px-2 text-[10px] font-medium ${zoom === z ? 'bg-primary/10 text-primary' : 'text-muted-foreground/60'}`}
83
- onClick={() => setZoom(z)}
84
- >
85
- {Math.round(z * 100)}%
86
- </Button>
87
- ))}
88
- </div>
89
- )}
90
- </div>
91
-
92
- <div className="dy-flex dy-items-center dy-gap-2">
93
- <Button variant="ghost" size="icon" className="dy-h-8 dy-w-8" onClick={reload}>
94
- <RotateCcw className="dy-h-3.5 dy-w-3.5" />
95
- </Button>
96
- <Button variant="ghost" size="icon" className="dy-h-8 dy-w-8" asChild>
97
- <a href={previewUrl} target="_blank" rel="noreferrer">
98
- <ExternalLink className="dy-h-3.5 dy-w-3.5" />
99
- </a>
100
- </Button>
101
- </div>
102
- </div>
103
-
104
- <div className="dy-flex-1 dy-flex dy-items-center dy-justify-center dy-p-0 dy-overflow-hidden dy-bg-muted/5">
105
- <div
106
- className={`bg-white shadow-[0_20px_50px_rgba(0,0,0,0.1)] transition-all duration-500 overflow-hidden border border-border/40 ${viewMode === 'mobile' ? 'w-[375px] h-[667px]' : 'w-full h-full'
107
- }`}
108
- >
109
- <iframe
110
- ref={iframeRef}
111
- src={previewUrl}
112
- className="dy-border-none dy-transition-transform dy-duration-300"
113
- style={viewMode === 'desktop' ? {
114
- width: `${100 / zoom}%`,
115
- height: `${100 / zoom}%`,
116
- transform: `scale(${zoom})`,
117
- transformOrigin: 'top left',
118
- } : {
119
- width: '100%',
120
- height: '100%',
121
- }}
122
- title="Live Preview"
123
- />
124
- </div>
125
- </div>
126
- </div>
127
- );
128
- }
@@ -1,66 +0,0 @@
1
- import * as React from "react"
2
- import { cn } from "../../lib/utils"
3
-
4
- interface FocalPoint {
5
- x: number;
6
- y: number;
7
- }
8
-
9
- interface FocalPointPickerProps {
10
- url: string;
11
- value?: FocalPoint;
12
- onChange: (value: FocalPoint) => void;
13
- className?: string;
14
- }
15
-
16
- export function FocalPointPicker({ url, value, onChange, className }: FocalPointPickerProps) {
17
- const containerRef = React.useRef<HTMLDivElement>(null);
18
-
19
- const focalPoint = value || { x: 50, y: 50 };
20
-
21
- const handleClick = (e: React.MouseEvent) => {
22
- if (!containerRef.current) return;
23
- const rect = containerRef.current.getBoundingClientRect();
24
- const x = Math.round(((e.clientX - rect.left) / rect.width) * 100);
25
- const y = Math.round(((e.clientY - rect.top) / rect.height) * 100);
26
-
27
- // Clamp values between 0 and 100
28
- const clampedX = Math.max(0, Math.min(100, x));
29
- const clampedY = Math.max(0, Math.min(100, y));
30
-
31
- onChange({ x: clampedX, y: clampedY });
32
- };
33
-
34
- return (
35
- <div className="dy-space-y-2">
36
- <div
37
- ref={containerRef}
38
- className={cn("dy-relative dy-cursor-crosshair dy-overflow-hidden dy-rounded-xl dy-border dy-border-border/40 dy-bg-muted/20 dy-group", className)}
39
- onClick={handleClick}
40
- >
41
- <img
42
- src={url}
43
- alt="Focal point picker"
44
- className="dy-w-full dy-h-auto dy-pointer-events-none dy-select-none dy-max-h-[400px] dy-object-contain dy-bg-checkered"
45
- />
46
-
47
- {/* Focal point indicator */}
48
- <div
49
- className="dy-absolute dy-w-8 dy-h-8 dy--ml-4 dy--mt-4 dy-border-2 dy-border-white dy-rounded-full dy-shadow-2xl dy-flex dy-items-center dy-justify-center dy-pointer-events-none dy-transition-all dy-duration-200 dy-ease-out"
50
- style={{ left: `${focalPoint.x}%`, top: `${focalPoint.y}%` }}
51
- >
52
- <div className="dy-w-1.5 dy-h-1.5 dy-bg-white dy-rounded-full dy-shadow-sm" />
53
- <div className="dy-absolute dy-w-full dy-h-px dy-bg-white/40" />
54
- <div className="dy-absolute dy-h-full dy-w-px dy-bg-white/40" />
55
- </div>
56
-
57
- <div className="dy-absolute dy-bottom-3 dy-left-3 dy-bg-black/60 dy-backdrop-blur-md dy-px-2.5 dy-py-1 dy-rounded-lg dy-text-[10px] dy-text-white dy-font-bold dy-tracking-widest dy-border dy-border-white/10 dy-opacity-0 dy-group-hover:dy-opacity-100 dy-transition-opacity">
58
- X: {focalPoint.x}% / Y: {focalPoint.y}%
59
- </div>
60
- </div>
61
- <p className="dy-text-[10px] dy-text-muted-foreground dy-font-medium dy-px-1">
62
- Click on the image to set the focal point for smart cropping.
63
- </p>
64
- </div>
65
- );
66
- }
@@ -1,44 +0,0 @@
1
- import { Link } from "react-router-dom"
2
- import { Pencil, Trash2 } from "lucide-react"
3
- import { Button } from "../ui/button"
4
- import { getMediaUrl } from "../../lib/utils"
5
-
6
- interface MediaCardProps {
7
- item: any
8
- baseUrl: string
9
- onDelete: (id: string) => void
10
- editPath: string
11
- }
12
-
13
- export function MediaCard({ item, baseUrl, onDelete, editPath }: MediaCardProps) {
14
- const url = getMediaUrl(item, baseUrl)
15
-
16
- return (
17
- <div className="dy-group dy-relative dy-aspect-square dy-rounded-2xl dy-overflow-hidden dy-bg-white dy-border dy-border-border/40 dy-shadow-sm hover:dy-shadow-xl hover:dy-border-primary/20 dy-transition-all dy-duration-300">
18
- <img
19
- src={url}
20
- alt={item.filename}
21
- className="dy-w-full dy-h-full dy-object-cover dy-transition-transform dy-duration-500 dy-group-hover:dy-scale-110"
22
- />
23
- <div className="dy-absolute dy-inset-0 dy-bg-black/40 dy-opacity-0 dy-group-hover:dy-opacity-100 dy-transition-all dy-duration-300 dy-flex dy-items-center dy-justify-center dy-gap-3 dy-backdrop-blur-[2px]">
24
- <Link to={editPath}>
25
- <Button size="icon" variant="secondary" className="dy-h-9 dy-w-9 dy-rounded-full dy-bg-white/90 hover:dy-bg-white dy-text-foreground dy-shadow-lg dy-transform dy-translate-y-2 dy-group-hover:dy-translate-y-0 dy-transition-transform dy-duration-300">
26
- <Pencil className="dy-h-4 dy-w-4" />
27
- </Button>
28
- </Link>
29
- <Button
30
- size="icon"
31
- variant="destructive"
32
- className="dy-h-9 dy-w-9 dy-rounded-full dy-bg-destructive/90 hover:dy-bg-destructive dy-shadow-lg dy-transform dy-translate-y-2 dy-group-hover:dy-translate-y-0 dy-transition-transform dy-duration-300 dy-delay-75"
33
- onClick={() => onDelete(item.id)}
34
- >
35
- <Trash2 className="dy-h-4 dy-w-4" />
36
- </Button>
37
- </div>
38
- <div className="dy-absolute dy-bottom-0 dy-left-0 dy-right-0 dy-p-3 dy-bg-gradient-to-t dy-from-black/80 dy-via-black/40 dy-to-transparent dy-opacity-0 dy-group-hover:dy-opacity-100 dy-transition-opacity dy-duration-300">
39
- <p className="dy-text-[10px] dy-text-white dy-truncate dy-font-medium">{item.filename}</p>
40
- <p className="dy-text-[8px] dy-text-white/60 dy-uppercase dy-tracking-wider dy-mt-0.5">{item.mimeType}</p>
41
- </div>
42
- </div>
43
- )
44
- }
@@ -1,32 +0,0 @@
1
- import { MediaCard } from "./media-card"
2
-
3
- interface MediaGridProps {
4
- items: any[]
5
- baseUrl: string
6
- onDelete: (id: string) => void
7
- slug: string
8
- }
9
-
10
- export function MediaGrid({ items, baseUrl, onDelete, slug }: MediaGridProps) {
11
- if (!items || items.length === 0) {
12
- return (
13
- <div className="dy-flex dy-flex-col dy-items-center dy-justify-center dy-h-[300px] dy-border-2 dy-border-dashed dy-border-border/60 dy-rounded-3xl dy-bg-muted/5">
14
- <p className="dy-text-sm dy-text-muted-foreground dy-font-medium">No media assets found</p>
15
- </div>
16
- )
17
- }
18
-
19
- return (
20
- <div className="dy-grid dy-grid-cols-2 sm:dy-grid-cols-3 md:dy-grid-cols-4 lg:dy-grid-cols-6 dy-gap-6">
21
- {items.map((item) => (
22
- <MediaCard
23
- key={item.id}
24
- item={item}
25
- baseUrl={baseUrl}
26
- onDelete={onDelete}
27
- editPath={`/collections/${slug}/edit/${item.id}`}
28
- />
29
- ))}
30
- </div>
31
- )
32
- }