@memori.ai/memori-react 7.25.0 → 7.26.0

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 (132) hide show
  1. package/CHANGELOG.md +42 -0
  2. package/dist/components/Chat/Chat.d.ts +5 -10
  3. package/dist/components/Chat/Chat.js +3 -3
  4. package/dist/components/Chat/Chat.js.map +1 -1
  5. package/dist/components/ChatBubble/ChatBubble.css +10 -0
  6. package/dist/components/ChatBubble/ChatBubble.d.ts +1 -0
  7. package/dist/components/ChatBubble/ChatBubble.js +16 -20
  8. package/dist/components/ChatBubble/ChatBubble.js.map +1 -1
  9. package/dist/components/ChatInputs/ChatInputs.d.ts +6 -10
  10. package/dist/components/ChatInputs/ChatInputs.js +37 -30
  11. package/dist/components/ChatInputs/ChatInputs.js.map +1 -1
  12. package/dist/components/FilePreview/FilePreview.css +169 -140
  13. package/dist/components/FilePreview/FilePreview.d.ts +2 -6
  14. package/dist/components/FilePreview/FilePreview.js +58 -5
  15. package/dist/components/FilePreview/FilePreview.js.map +1 -1
  16. package/dist/components/MemoriWidget/MemoriWidget.d.ts +2 -1
  17. package/dist/components/MemoriWidget/MemoriWidget.js +15 -21
  18. package/dist/components/MemoriWidget/MemoriWidget.js.map +1 -1
  19. package/dist/components/UploadButton/UploadButton.css +506 -27
  20. package/dist/components/UploadButton/UploadButton.d.ts +14 -11
  21. package/dist/components/UploadButton/UploadButton.js +110 -288
  22. package/dist/components/UploadButton/UploadButton.js.map +1 -1
  23. package/dist/components/UploadButton/UploadDocuments/UploadDocuments.d.ts +19 -0
  24. package/dist/components/UploadButton/UploadDocuments/UploadDocuments.js +211 -0
  25. package/dist/components/UploadButton/UploadDocuments/UploadDocuments.js.map +1 -0
  26. package/dist/components/UploadButton/UploadImages/UploadImages.d.ts +13 -0
  27. package/dist/components/UploadButton/UploadImages/UploadImages.js +207 -0
  28. package/dist/components/UploadButton/UploadImages/UploadImages.js.map +1 -0
  29. package/dist/components/icons/Bug.d.ts +5 -0
  30. package/dist/components/icons/Bug.js +6 -0
  31. package/dist/components/icons/Bug.js.map +1 -0
  32. package/dist/components/icons/Document.d.ts +5 -0
  33. package/dist/components/icons/Document.js +10 -0
  34. package/dist/components/icons/Document.js.map +1 -0
  35. package/dist/components/icons/Image.d.ts +4 -0
  36. package/dist/components/icons/Image.js +9 -0
  37. package/dist/components/icons/Image.js.map +1 -0
  38. package/dist/components/icons/Preview.d.ts +4 -5
  39. package/dist/components/icons/Preview.js +5 -2
  40. package/dist/components/icons/Preview.js.map +1 -1
  41. package/dist/components/icons/Upload.d.ts +4 -5
  42. package/dist/components/icons/Upload.js +5 -2
  43. package/dist/components/icons/Upload.js.map +1 -1
  44. package/dist/components/layouts/HiddenChat.js +100 -10
  45. package/dist/components/layouts/HiddenChat.js.map +1 -1
  46. package/dist/components/layouts/hidden-chat.css +189 -119
  47. package/dist/locales/de.json +16 -0
  48. package/dist/locales/en.json +24 -0
  49. package/dist/locales/es.json +16 -0
  50. package/dist/locales/fr.json +16 -0
  51. package/dist/locales/it.json +22 -0
  52. package/esm/components/Chat/Chat.d.ts +5 -10
  53. package/esm/components/Chat/Chat.js +3 -3
  54. package/esm/components/Chat/Chat.js.map +1 -1
  55. package/esm/components/ChatBubble/ChatBubble.css +10 -0
  56. package/esm/components/ChatBubble/ChatBubble.d.ts +1 -0
  57. package/esm/components/ChatBubble/ChatBubble.js +16 -20
  58. package/esm/components/ChatBubble/ChatBubble.js.map +1 -1
  59. package/esm/components/ChatInputs/ChatInputs.d.ts +6 -10
  60. package/esm/components/ChatInputs/ChatInputs.js +37 -30
  61. package/esm/components/ChatInputs/ChatInputs.js.map +1 -1
  62. package/esm/components/FilePreview/FilePreview.css +169 -140
  63. package/esm/components/FilePreview/FilePreview.d.ts +2 -6
  64. package/esm/components/FilePreview/FilePreview.js +58 -5
  65. package/esm/components/FilePreview/FilePreview.js.map +1 -1
  66. package/esm/components/MemoriWidget/MemoriWidget.d.ts +2 -1
  67. package/esm/components/MemoriWidget/MemoriWidget.js +15 -21
  68. package/esm/components/MemoriWidget/MemoriWidget.js.map +1 -1
  69. package/esm/components/UploadButton/UploadButton.css +506 -27
  70. package/esm/components/UploadButton/UploadButton.d.ts +14 -11
  71. package/esm/components/UploadButton/UploadButton.js +111 -289
  72. package/esm/components/UploadButton/UploadButton.js.map +1 -1
  73. package/esm/components/UploadButton/UploadDocuments/UploadDocuments.d.ts +19 -0
  74. package/esm/components/UploadButton/UploadDocuments/UploadDocuments.js +208 -0
  75. package/esm/components/UploadButton/UploadDocuments/UploadDocuments.js.map +1 -0
  76. package/esm/components/UploadButton/UploadImages/UploadImages.d.ts +13 -0
  77. package/esm/components/UploadButton/UploadImages/UploadImages.js +204 -0
  78. package/esm/components/UploadButton/UploadImages/UploadImages.js.map +1 -0
  79. package/esm/components/icons/Bug.d.ts +5 -0
  80. package/esm/components/icons/Bug.js +4 -0
  81. package/esm/components/icons/Bug.js.map +1 -0
  82. package/esm/components/icons/Document.d.ts +5 -0
  83. package/esm/components/icons/Document.js +6 -0
  84. package/esm/components/icons/Document.js.map +1 -0
  85. package/esm/components/icons/Image.d.ts +4 -0
  86. package/esm/components/icons/Image.js +5 -0
  87. package/esm/components/icons/Image.js.map +1 -0
  88. package/esm/components/icons/Preview.d.ts +4 -5
  89. package/esm/components/icons/Preview.js +4 -3
  90. package/esm/components/icons/Preview.js.map +1 -1
  91. package/esm/components/icons/Upload.d.ts +4 -5
  92. package/esm/components/icons/Upload.js +4 -3
  93. package/esm/components/icons/Upload.js.map +1 -1
  94. package/esm/components/layouts/HiddenChat.js +101 -11
  95. package/esm/components/layouts/HiddenChat.js.map +1 -1
  96. package/esm/components/layouts/hidden-chat.css +189 -119
  97. package/esm/locales/de.json +16 -0
  98. package/esm/locales/en.json +24 -0
  99. package/esm/locales/es.json +16 -0
  100. package/esm/locales/fr.json +16 -0
  101. package/esm/locales/it.json +22 -0
  102. package/package.json +1 -1
  103. package/src/components/Chat/Chat.tsx +8 -8
  104. package/src/components/ChatBubble/ChatBubble.css +10 -0
  105. package/src/components/ChatBubble/ChatBubble.stories.tsx +25 -0
  106. package/src/components/ChatBubble/ChatBubble.tsx +41 -17
  107. package/src/components/ChatInputs/ChatInputs.tsx +92 -43
  108. package/src/components/FilePreview/FilePreview.css +169 -140
  109. package/src/components/FilePreview/FilePreview.tsx +106 -14
  110. package/src/components/FilePreview/__snapshots__/FilePreview.test.tsx.snap +146 -29
  111. package/src/components/MemoriWidget/MemoriWidget.tsx +14 -22
  112. package/src/components/UploadButton/UploadButton.css +506 -27
  113. package/src/components/UploadButton/UploadButton.stories.tsx +122 -20
  114. package/src/components/UploadButton/UploadButton.test.tsx +1 -1
  115. package/src/components/UploadButton/UploadButton.tsx +264 -454
  116. package/src/components/UploadButton/UploadDocuments/UploadDocuments.tsx +352 -0
  117. package/src/components/UploadButton/UploadImages/UploadImages.tsx +434 -0
  118. package/src/components/UploadButton/__snapshots__/UploadButton.test.tsx.snap +140 -13
  119. package/src/components/icons/Bug.tsx +81 -0
  120. package/src/components/icons/Document.tsx +50 -0
  121. package/src/components/icons/Image.tsx +37 -0
  122. package/src/components/icons/Preview.tsx +28 -22
  123. package/src/components/icons/Upload.tsx +33 -22
  124. package/src/components/layouts/HiddenChat.tsx +143 -7
  125. package/src/components/layouts/__snapshots__/HiddenChat.test.tsx.snap +1 -1
  126. package/src/components/layouts/hidden-chat.css +189 -119
  127. package/src/index.stories.tsx +19 -19
  128. package/src/locales/de.json +16 -0
  129. package/src/locales/en.json +24 -0
  130. package/src/locales/es.json +16 -0
  131. package/src/locales/fr.json +16 -0
  132. package/src/locales/it.json +22 -0
@@ -0,0 +1,434 @@
1
+ import React, { useState, useRef, useEffect } from 'react';
2
+ import cx from 'classnames';
3
+ import Spin from '../../ui/Spin';
4
+ import Alert from '../../ui/Alert';
5
+ import { ImageIcon } from '../../icons/Image';
6
+ import Modal from '../../ui/Modal';
7
+ import memoriApiClient from '@memori.ai/memori-api-client';
8
+ import { Medium } from '@memori.ai/memori-api-client/dist/types';
9
+ import { useTranslation } from 'react-i18next';
10
+ import Button from '../../ui/Button';
11
+
12
+ // Types
13
+ type UploadError = {
14
+ message: string;
15
+ severity: 'error' | 'warning' | 'info';
16
+ fileId?: string;
17
+ };
18
+
19
+ type PreviewFile = {
20
+ name: string;
21
+ id: string;
22
+ content: string;
23
+ type: 'image';
24
+ previewUrl?: string;
25
+ uploaded?: boolean;
26
+ file?: File;
27
+ error?: boolean;
28
+ title?: string;
29
+ };
30
+
31
+ // Constants
32
+ const DEFAULT_MAX_FILE_SIZE = 10 * 1024 * 1024; // 10MB
33
+
34
+ // Props interface
35
+ interface UploadImagesProps {
36
+ authToken?: string;
37
+ apiUrl?: string;
38
+ sessionID?: string;
39
+ isMediaAccepted?: boolean;
40
+ setDocumentPreviewFiles: any;
41
+ documentPreviewFiles: any;
42
+ onLoadingChange?: (loading: boolean) => void;
43
+ maxImages?: number;
44
+ }
45
+
46
+ const ALLOWED_FILE_TYPES = ['.jpg', '.jpeg', '.png'];
47
+
48
+ const UploadImages: React.FC<UploadImagesProps> = ({
49
+ authToken = '',
50
+ apiUrl = '',
51
+ sessionID = '',
52
+ isMediaAccepted = false,
53
+ setDocumentPreviewFiles,
54
+ documentPreviewFiles,
55
+ onLoadingChange,
56
+ maxImages = 5, // Default value if not provided
57
+ }) => {
58
+ const { t, i18n } = useTranslation();
59
+ // Client
60
+ const client = apiUrl ? memoriApiClient(apiUrl) : null;
61
+ const { backend, dialog } = client || {
62
+ backend: { uploadAsset: null },
63
+ dialog: { postMediumSelectedEvent: null, postMediumDeselectedEvent: null },
64
+ };
65
+
66
+ // State
67
+ const [isLoading, setIsLoading] = useState(false);
68
+ const [errors, setErrors] = useState<UploadError[]>([]);
69
+ const [selectedFile, setSelectedFile] = useState<File | null>(null);
70
+ const [filePreview, setFilePreview] = useState<string | null>(null);
71
+ const [imageTitle, setImageTitle] = useState('');
72
+ const [showUploadModal, setShowUploadModal] = useState(false);
73
+
74
+ // Refs
75
+ const imageInputRef = useRef<HTMLInputElement>(null);
76
+
77
+ // Update loading state in parent component
78
+ useEffect(() => {
79
+ if (onLoadingChange) {
80
+ onLoadingChange(isLoading);
81
+ }
82
+ }, [isLoading, onLoadingChange]);
83
+
84
+ // Error handling
85
+ const clearErrors = () => setErrors([]);
86
+
87
+ const removeError = (errorMessage: string) => {
88
+ setErrors(prev => prev.filter(e => e.message !== errorMessage));
89
+ };
90
+
91
+ const addError = (error: UploadError) => {
92
+ setErrors(prev => [...prev, error]);
93
+ setTimeout(() => removeError(error.message), 5000);
94
+ };
95
+
96
+ // Check current image count
97
+ const currentImageCount = documentPreviewFiles.filter(
98
+ (file: any) => file.type === 'image'
99
+ ).length;
100
+
101
+ // Image upload
102
+ const validateImageFile = (file: File): boolean => {
103
+ const fileExt = `.${file.name.split('.').pop()?.toLowerCase()}`;
104
+
105
+ if (
106
+ !ALLOWED_FILE_TYPES.includes(fileExt) &&
107
+ !file.type.startsWith('image/')
108
+ ) {
109
+ addError({
110
+ message: `File type "${fileExt}" is not supported. Please use: ${ALLOWED_FILE_TYPES.join(
111
+ ', '
112
+ )}`,
113
+ severity: 'error',
114
+ fileId: file.name,
115
+ });
116
+ return false;
117
+ }
118
+
119
+ if (file.size > DEFAULT_MAX_FILE_SIZE) {
120
+ addError({
121
+ message: `File "${file.name}" exceeds ${
122
+ DEFAULT_MAX_FILE_SIZE / 1024 / 1024
123
+ }MB limit`,
124
+ severity: 'error',
125
+ fileId: file.name,
126
+ });
127
+ return false;
128
+ }
129
+
130
+ return true;
131
+ };
132
+
133
+ const handleImageUpload = async (e: React.ChangeEvent<HTMLInputElement>) => {
134
+ const files = Array.from(e.target.files || []);
135
+ if (files.length === 0) return;
136
+
137
+ // Check if adding these files would exceed the limit
138
+ const availableSlots = maxImages - currentImageCount;
139
+
140
+ if (availableSlots <= 0) {
141
+ // This check should rarely be needed since the button should be disabled
142
+ return;
143
+ }
144
+
145
+ // If we can't upload all files, only upload what we can and show warning
146
+ let filesToUpload = files;
147
+ if (files.length > availableSlots) {
148
+ filesToUpload = files.slice(0, availableSlots);
149
+ addError({
150
+ message:
151
+ t('upload.partialUpload', {
152
+ uploaded: availableSlots,
153
+ total: files.length,
154
+ }) ??
155
+ `Only ${availableSlots} out of ${files.length} images will be uploaded. Maximum ${maxImages} images allowed.`,
156
+ severity: 'warning',
157
+ });
158
+ }
159
+
160
+ clearErrors();
161
+
162
+ // For simplicity, we'll handle one file at a time
163
+ const file = filesToUpload[0];
164
+
165
+ if (!validateImageFile(file)) {
166
+ if (imageInputRef.current) {
167
+ imageInputRef.current.value = '';
168
+ }
169
+ return;
170
+ }
171
+
172
+ // Set file and create preview
173
+ console.log('file', file);
174
+ setSelectedFile(file);
175
+ setFilePreview(URL.createObjectURL(file));
176
+
177
+ // Set initial title as filename without extension
178
+ const fileName = file.name.split('.').slice(0, -1).join('.');
179
+ setImageTitle(fileName);
180
+
181
+ // Show upload modal with preview
182
+ setShowUploadModal(true);
183
+
184
+ if (imageInputRef.current) {
185
+ imageInputRef.current.value = '';
186
+ }
187
+ };
188
+
189
+ const handleTitleSubmit = async () => {
190
+ if (!selectedFile || !imageTitle.trim()) return;
191
+
192
+ setIsLoading(true);
193
+ setShowUploadModal(false);
194
+
195
+ try {
196
+ // Read the file as a data URL
197
+ const reader = new FileReader();
198
+
199
+ reader.onload = async e => {
200
+ const fileDataUrl = e.target?.result as string;
201
+ const fileId = Math.random().toString(36).substr(2, 9);
202
+
203
+ if (backend?.uploadAsset && authToken) {
204
+ try {
205
+ // Upload the asset
206
+ const { asset, ...resp } = await backend.uploadAsset(
207
+ selectedFile.name,
208
+ fileDataUrl,
209
+ authToken
210
+ );
211
+
212
+ if (resp.resultCode !== 0) {
213
+ throw new Error(resp.resultMessage || 'Upload failed');
214
+ }
215
+
216
+ // Call the MediumSelected event if dialog API is available
217
+ let medium: any = null;
218
+ if (dialog?.postMediumSelectedEvent && sessionID) {
219
+ medium = await dialog.postMediumSelectedEvent(sessionID, {
220
+ url: asset.assetURL,
221
+ mimeType: asset.mimeType,
222
+ } as Medium);
223
+ }
224
+
225
+ // Find mediumID that isn't already in documentPreviewFiles
226
+ let finalMediumID: string | undefined = undefined;
227
+ if (medium?.currentState?.currentMedia) {
228
+ // create a set of existing mediumIDs
229
+ const existingMediumIDs = new Set(
230
+ documentPreviewFiles.map((file: any) => file.mediumID)
231
+ );
232
+
233
+ // find the first mediumID that isn't already in the set
234
+ finalMediumID = medium.currentState.currentMedia.find(
235
+ (media: any) => !existingMediumIDs.has(media.mediumID)
236
+ )?.mediumID;
237
+ }
238
+
239
+ // Update parent component with the new file
240
+ setDocumentPreviewFiles(
241
+ (
242
+ prevFiles: {
243
+ name: string;
244
+ id: string;
245
+ content: string;
246
+ type: string;
247
+ mediumID: string | undefined;
248
+ url: string;
249
+ mimeType: string;
250
+ }[]
251
+ ) => [
252
+ ...prevFiles,
253
+ {
254
+ name: imageTitle,
255
+ id: fileId,
256
+ url: asset.assetURL,
257
+ content: asset.assetURL,
258
+ type: 'image',
259
+ mediumID: finalMediumID,
260
+ mimeType: asset.mimeType,
261
+ },
262
+ ]
263
+ );
264
+ } catch (error) {
265
+ addError({
266
+ message: t('upload.uploadFailed') ?? 'Upload failed',
267
+ severity: 'error',
268
+ fileId: selectedFile.name,
269
+ });
270
+ }
271
+ } else {
272
+ addError({
273
+ message:
274
+ t('upload.apiClientNotConfigured') ??
275
+ 'API client not configured properly for media upload',
276
+ severity: 'warning',
277
+ });
278
+ }
279
+
280
+ setIsLoading(false);
281
+ };
282
+
283
+ reader.onerror = () => {
284
+ addError({
285
+ message: t('upload.fileReadingFailed') ?? 'File reading failed',
286
+ severity: 'error',
287
+ fileId: selectedFile.name,
288
+ });
289
+ setIsLoading(false);
290
+ };
291
+
292
+ reader.readAsDataURL(selectedFile);
293
+ } catch (error) {
294
+ addError({
295
+ message: t('upload.uploadFailed') ?? 'Upload failed',
296
+ severity: 'error',
297
+ fileId: selectedFile.name,
298
+ });
299
+ setIsLoading(false);
300
+ }
301
+ };
302
+
303
+ const handleCancelUpload = () => {
304
+ setShowUploadModal(false);
305
+ setSelectedFile(null);
306
+ setFilePreview(null);
307
+ setImageTitle('');
308
+ };
309
+
310
+ return (
311
+ <div className="memori--image-upload-wrapper">
312
+ {/* Hidden file input */}
313
+ <input
314
+ ref={imageInputRef}
315
+ type="file"
316
+ accept={ALLOWED_FILE_TYPES.join(',')}
317
+ className="memori--upload-file-input"
318
+ onChange={handleImageUpload}
319
+ disabled={
320
+ isLoading ||
321
+ !isMediaAccepted ||
322
+ !authToken ||
323
+ currentImageCount >= maxImages
324
+ }
325
+ multiple
326
+ />
327
+
328
+ {/* Upload image button */}
329
+ <button
330
+ className={cx(
331
+ 'memori-button',
332
+ 'memori-button--circle',
333
+ 'memori-button--icon-only',
334
+ 'memori-share-button--button',
335
+ 'memori--conversation-button',
336
+ 'memori--image-upload-button'
337
+ )}
338
+ onClick={() => imageInputRef.current?.click()}
339
+ disabled={
340
+ isLoading ||
341
+ !isMediaAccepted ||
342
+ !authToken ||
343
+ currentImageCount >= maxImages
344
+ }
345
+ >
346
+ {isLoading ? (
347
+ <Spin spinning className="memori--upload-icon" />
348
+ ) : (
349
+ <ImageIcon className="memori--upload-icon" />
350
+ )}
351
+ </button>
352
+
353
+ {/* Upload Modal with Title Input */}
354
+ <Modal
355
+ width="80%"
356
+ widthMd="80%"
357
+ open={showUploadModal && !!selectedFile}
358
+ className="memori--modal-preview-file"
359
+ onClose={handleCancelUpload}
360
+ closable
361
+ title={t('upload.titleImage', { title: imageTitle })}
362
+ // description={t('upload.imageTitleDescription')}
363
+ >
364
+ <div
365
+ className="memori--preview-content"
366
+ style={{
367
+ maxHeight: '70vh',
368
+ overflowY: 'auto',
369
+ textAlign: 'center',
370
+ }}
371
+ >
372
+ {filePreview && (
373
+ <img
374
+ src={filePreview}
375
+ alt={selectedFile?.name || 'Preview'}
376
+ style={{
377
+ maxWidth: '100%',
378
+ maxHeight: '40vh',
379
+ marginBottom: '20px',
380
+ }}
381
+ />
382
+ )}
383
+
384
+ <div
385
+ style={{ maxWidth: '400px', margin: '0 auto', textAlign: 'left' }}
386
+ >
387
+ <p style={{ marginBottom: '10px', color: '#666' }}>
388
+ {t('upload.titleHelp')}
389
+ </p>
390
+ <input
391
+ value={imageTitle}
392
+ onChange={e => setImageTitle(e.target.value)}
393
+ placeholder={t('upload.titlePlaceholder') ?? 'Enter image title'}
394
+ style={{ width: '90%', marginBottom: '20px' }}
395
+ className="memori--upload-title-input"
396
+ />
397
+ <div style={{ display: 'flex', gap: '10px' }}>
398
+ <Button
399
+ onClick={handleTitleSubmit}
400
+ disabled={!selectedFile || !imageTitle.trim()}
401
+ className="memori-button memori-button--primary"
402
+ >
403
+ {t('confirm') ?? 'Confirm'}
404
+ </Button>
405
+ <Button
406
+ onClick={handleCancelUpload}
407
+ className="memori-button memori-button--secondary"
408
+ >
409
+ {t('cancel') ?? 'Cancel'}
410
+ </Button>
411
+ </div>
412
+ </div>
413
+ </div>
414
+ </Modal>
415
+
416
+ {/* Error messages container */}
417
+ <div className="memori--error-message-container">
418
+ {errors.map((error, index) => (
419
+ <Alert
420
+ key={`${error.message}-${index}`}
421
+ open={true}
422
+ type={error.severity}
423
+ title={'Upload notification'}
424
+ description={error.message}
425
+ onClose={() => removeError(error.message)}
426
+ width="350px"
427
+ />
428
+ ))}
429
+ </div>
430
+ </div>
431
+ );
432
+ };
433
+
434
+ export default UploadImages;
@@ -3,31 +3,158 @@
3
3
  exports[`renders UploadButton unchanged 1`] = `
4
4
  <div>
5
5
  <div
6
- class="relative file-upload-wrapper"
6
+ class="memori--unified-upload-wrapper"
7
7
  >
8
- <input
9
- accept=".pdf,.txt,.md,.json,.xlsx,.csv"
10
- class="memori--upload-file-input"
11
- multiple=""
12
- type="file"
13
- />
14
8
  <button
15
- class="memori-button memori-button--circle memori-button--icon-only memori-share-button--button memori--conversation-button"
16
- title="Upload file"
9
+ class="memori-button memori-button--circle memori-button--icon-only memori-share-button--button memori--conversation-button memori--unified-upload-button"
10
+ title="upload.uploadFiles"
17
11
  >
18
12
  <svg
19
- aria-hidden="true"
20
13
  class="memori--upload-icon"
21
- focusable="false"
22
- role="img"
14
+ fill="none"
23
15
  viewBox="0 0 24 24"
24
16
  xmlns="http://www.w3.org/2000/svg"
25
17
  >
26
18
  <path
27
- d="M19.35 10.04C18.67 6.59 15.64 4 12 4 9.11 4 6.6 5.64 5.35 8.04 2.34 8.36 0 10.91 0 14c0 3.31 2.69 6 6 6h13c2.76 0 5-2.24 5-5 0-2.64-2.05-4.78-4.65-4.96zM14 13v4h-4v-4H7l5-5 5 5h-3z"
19
+ d="M21 15V19C21 19.5304 20.7893 20.0391 20.4142 20.4142C20.0391 20.7893 19.5304 21 19 21H5C4.46957 21 3.96086 20.7893 3.58579 20.4142C3.21071 20.0391 3 19.5304 3 19V15"
20
+ stroke="currentColor"
21
+ stroke-linecap="round"
22
+ stroke-linejoin="round"
23
+ stroke-width="1.5"
24
+ />
25
+ <path
26
+ d="M17 8L12 3L7 8"
27
+ stroke="currentColor"
28
+ stroke-linecap="round"
29
+ stroke-linejoin="round"
30
+ stroke-width="1.5"
31
+ />
32
+ <path
33
+ d="M12 3V15"
34
+ stroke="currentColor"
35
+ stroke-linecap="round"
36
+ stroke-linejoin="round"
37
+ stroke-width="1.5"
28
38
  />
29
39
  </svg>
30
40
  </button>
41
+ <div
42
+ class="memori--hidden-uploader"
43
+ >
44
+ <div
45
+ class="memori--document-upload-wrapper"
46
+ >
47
+ <input
48
+ accept=".pdf,.txt,.md,.json,.xlsx,.csv"
49
+ class="memori--upload-file-input"
50
+ type="file"
51
+ />
52
+ <button
53
+ class="memori-button memori-button--circle memori-button--icon-only memori-share-button--button memori--conversation-button memori--document-upload-button"
54
+ title="Upload documents"
55
+ >
56
+ <svg
57
+ class="memori--upload-icon"
58
+ fill="none"
59
+ viewBox="0 0 24 24"
60
+ xmlns="http://www.w3.org/2000/svg"
61
+ >
62
+ <path
63
+ d="M14 2.5H6C5.60218 2.5 5.22064 2.65804 4.93934 2.93934C4.65804 3.22064 4.5 3.60218 4.5 4V20C4.5 20.3978 4.65804 20.7794 4.93934 21.0607C5.22064 21.342 5.60218 21.5 6 21.5H18C18.3978 21.5 18.7794 21.342 19.0607 21.0607C19.342 20.7794 19.5 20.3978 19.5 20V8L14 2.5Z"
64
+ stroke="currentColor"
65
+ stroke-linecap="round"
66
+ stroke-linejoin="round"
67
+ stroke-width="1.5"
68
+ />
69
+ <path
70
+ d="M14 2.5V8H19.5"
71
+ stroke="currentColor"
72
+ stroke-linecap="round"
73
+ stroke-linejoin="round"
74
+ stroke-width="1.5"
75
+ />
76
+ <path
77
+ d="M16 13H8"
78
+ stroke="currentColor"
79
+ stroke-linecap="round"
80
+ stroke-linejoin="round"
81
+ stroke-width="1.5"
82
+ />
83
+ <path
84
+ d="M16 17H8"
85
+ stroke="currentColor"
86
+ stroke-linecap="round"
87
+ stroke-linejoin="round"
88
+ stroke-width="1.5"
89
+ />
90
+ <path
91
+ d="M10 9H8"
92
+ stroke="currentColor"
93
+ stroke-linecap="round"
94
+ stroke-linejoin="round"
95
+ stroke-width="1.5"
96
+ />
97
+ </svg>
98
+ </button>
99
+ <div
100
+ class="memori--error-message-container"
101
+ />
102
+ </div>
103
+ </div>
104
+ <div
105
+ class="memori--hidden-uploader"
106
+ >
107
+ <div
108
+ class="memori--image-upload-wrapper"
109
+ >
110
+ <input
111
+ accept=".jpg,.jpeg,.png"
112
+ class="memori--upload-file-input"
113
+ disabled=""
114
+ multiple=""
115
+ type="file"
116
+ />
117
+ <button
118
+ class="memori-button memori-button--circle memori-button--icon-only memori-share-button--button memori--conversation-button memori--image-upload-button"
119
+ disabled=""
120
+ >
121
+ <svg
122
+ class="memori--upload-icon"
123
+ fill="none"
124
+ viewBox="0 0 24 24"
125
+ xmlns="http://www.w3.org/2000/svg"
126
+ >
127
+ <rect
128
+ height="18"
129
+ rx="2"
130
+ stroke="currentColor"
131
+ stroke-linecap="round"
132
+ stroke-linejoin="round"
133
+ stroke-width="1.5"
134
+ width="18"
135
+ x="3"
136
+ y="3"
137
+ />
138
+ <circle
139
+ cx="8.5"
140
+ cy="8.5"
141
+ fill="currentColor"
142
+ r="1.5"
143
+ />
144
+ <path
145
+ d="M21 15L16 10L5 21"
146
+ stroke="currentColor"
147
+ stroke-linecap="round"
148
+ stroke-linejoin="round"
149
+ stroke-width="1.5"
150
+ />
151
+ </svg>
152
+ </button>
153
+ <div
154
+ class="memori--error-message-container"
155
+ />
156
+ </div>
157
+ </div>
31
158
  <div
32
159
  class="memori--error-message-container"
33
160
  />
@@ -0,0 +1,81 @@
1
+ import React from 'react';
2
+
3
+ const Bug = ({ className, title }: { className?: string; title?: string }) => (
4
+ <svg
5
+ width="800px"
6
+ height="800px"
7
+ viewBox="0 0 24 24"
8
+ fill="none"
9
+ xmlns="http://www.w3.org/2000/svg"
10
+ className={className}
11
+ aria-label={title}
12
+ color="currentColor"
13
+ >
14
+ <path
15
+ d="M19 15V11.9375C19 9.76288 17.2371 8 15.0625 8H8.9375C6.76288 8 5 9.76288 5 11.9375V15C5 18.866 8.13401 22 12 22C15.866 22 19 18.866 19 15Z"
16
+ stroke="currentColor"
17
+ strokeWidth="1.5"
18
+ />
19
+ <path
20
+ d="M16.5 8.5V7.5C16.5 5.01472 14.4853 3 12 3C9.51472 3 7.5 5.01472 7.5 7.5V8.5"
21
+ stroke="currentColor"
22
+ strokeWidth="1.5"
23
+ />
24
+ <path
25
+ d="M19 14H22"
26
+ stroke="currentColor"
27
+ strokeWidth="1.5"
28
+ strokeLinecap="round"
29
+ />
30
+ <path
31
+ d="M5 14H2"
32
+ stroke="currentColor"
33
+ strokeWidth="1.5"
34
+ strokeLinecap="round"
35
+ />
36
+ <path
37
+ d="M14.5 3.5L17 2"
38
+ stroke="currentColor"
39
+ strokeWidth="1.5"
40
+ strokeLinecap="round"
41
+ />
42
+ <path
43
+ d="M9.5 3.5L7 2"
44
+ stroke="currentColor"
45
+ strokeWidth="1.5"
46
+ strokeLinecap="round"
47
+ />
48
+ <path
49
+ d="M20.5 20.0002L18.5 19.2002"
50
+ stroke="currentColor"
51
+ strokeWidth="1.5"
52
+ strokeLinecap="round"
53
+ />
54
+ <path
55
+ d="M20.5 7.9998L18.5 8.7998"
56
+ stroke="currentColor"
57
+ strokeWidth="1.5"
58
+ strokeLinecap="round"
59
+ />
60
+ <path
61
+ d="M3.5 20.0002L5.5 19.2002"
62
+ stroke="currentColor"
63
+ strokeWidth="1.5"
64
+ strokeLinecap="round"
65
+ />
66
+ <path
67
+ d="M3.5 7.9998L5.5 8.7998"
68
+ stroke="currentColor"
69
+ strokeWidth="1.5"
70
+ strokeLinecap="round"
71
+ />
72
+ <path
73
+ d="M12 21.5V15"
74
+ stroke="currentColor"
75
+ strokeWidth="1.5"
76
+ strokeLinecap="round"
77
+ />
78
+ </svg>
79
+ );
80
+
81
+ export default Bug;