@visns-studio/visns-components 4.4.2 → 4.4.4
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/components/crm/auth/Login.jsx +33 -16
- package/components/crm/auth/styles/Login.module.css +218 -0
- package/components/crm/generic/GenericDetail.jsx +150 -51
- package/components/crm/generic/GenericMain.jsx +6 -5
- package/components/crm/generic/styles/GenericDetail.module.css +578 -0
- package/components/crm/generic/styles/GenericIndex.module.css +178 -183
- package/components/crm/generic/styles/GenericMain.module.css +77 -0
- package/components/crm/styles/AsyncSelect.module.css +6 -10
- package/components/crm/styles/Autocomplete.module.css +3 -3
- package/components/crm/styles/DataGrid.module.css +59 -59
- package/components/crm/styles/Form.module.css +17 -19
- package/components/crm/styles/MultiSelect.module.css +6 -10
- package/components/crm/styles/TableFilter.module.css +1 -0
- package/package.json +1 -1
|
@@ -8,6 +8,7 @@ import Dropzone from 'react-dropzone';
|
|
|
8
8
|
import { confirmAlert } from 'react-confirm-alert';
|
|
9
9
|
import truncate from 'truncate';
|
|
10
10
|
import { CopyToClipboard } from 'react-copy-to-clipboard';
|
|
11
|
+
import { toast } from 'react-toastify';
|
|
11
12
|
import { CircleCheck, Copy, File, TrashCan } from 'akar-icons';
|
|
12
13
|
|
|
13
14
|
import 'react-confirm-alert/src/react-confirm-alert.css';
|
|
@@ -19,7 +20,8 @@ import GenericDynamic from './GenericDynamic';
|
|
|
19
20
|
import QrCode from '../QrCode';
|
|
20
21
|
import Table from '../DataGrid';
|
|
21
22
|
import TableFilter from '../TableFilter';
|
|
22
|
-
|
|
23
|
+
|
|
24
|
+
import styles from './styles/GenericDetail.module.css';
|
|
23
25
|
|
|
24
26
|
function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
25
27
|
const gridRef = useRef(null);
|
|
@@ -115,7 +117,7 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
115
117
|
setDataReload(randomNumber);
|
|
116
118
|
};
|
|
117
119
|
|
|
118
|
-
const getValueFromData = (data, path, id) => {
|
|
120
|
+
const getValueFromData = (data, path, id, type) => {
|
|
119
121
|
let value =
|
|
120
122
|
path.reduce((result, key) => (result ? result[key] : ''), data) ??
|
|
121
123
|
'';
|
|
@@ -128,7 +130,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
128
130
|
.join(', ');
|
|
129
131
|
} else {
|
|
130
132
|
if (Array.isArray(id)) {
|
|
131
|
-
|
|
133
|
+
if (type === 'checkbox') {
|
|
134
|
+
return value[id];
|
|
135
|
+
} else {
|
|
136
|
+
return id.map((key) => value[key]).join(' ');
|
|
137
|
+
}
|
|
132
138
|
} else {
|
|
133
139
|
return value[id];
|
|
134
140
|
}
|
|
@@ -166,8 +172,9 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
166
172
|
} = item;
|
|
167
173
|
const value =
|
|
168
174
|
relation && relation.length > 0 && type !== 'total'
|
|
169
|
-
? getValueFromData(data, [...relation], id)
|
|
170
|
-
: getValueFromData(data, [], id);
|
|
175
|
+
? getValueFromData(data, [...relation], id, type)
|
|
176
|
+
: getValueFromData(data, [], id, type);
|
|
177
|
+
|
|
171
178
|
const stringValue = String(value ?? ''); // Convert value to a string
|
|
172
179
|
|
|
173
180
|
// Conditionally truncate the value if the 'truncate' key is present
|
|
@@ -229,9 +236,45 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
229
236
|
|
|
230
237
|
const renderBoolean = () => (value ? 'Yes' : 'No');
|
|
231
238
|
|
|
232
|
-
const renderCheckbox = (
|
|
233
|
-
|
|
234
|
-
|
|
239
|
+
const renderCheckbox = () => {
|
|
240
|
+
if (!value || typeof value !== 'object') {
|
|
241
|
+
return '';
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
const formatKey = (key) => {
|
|
245
|
+
return key
|
|
246
|
+
.toLowerCase()
|
|
247
|
+
.split('_')
|
|
248
|
+
.map((word) => word.charAt(0).toUpperCase() + word.slice(1))
|
|
249
|
+
.join(' ');
|
|
250
|
+
};
|
|
251
|
+
|
|
252
|
+
const keys = Object.keys(value)
|
|
253
|
+
.filter((key) => value[key] && key !== 'notes')
|
|
254
|
+
.sort((a, b) => {
|
|
255
|
+
if (a === 'other') return 1;
|
|
256
|
+
if (b === 'other') return -1;
|
|
257
|
+
return a.localeCompare(b);
|
|
258
|
+
});
|
|
259
|
+
|
|
260
|
+
const formattedKeys = keys.map((key) => {
|
|
261
|
+
let formattedKey = formatKey(key);
|
|
262
|
+
if (key === 'other') {
|
|
263
|
+
const otherValue = getValueFromData(
|
|
264
|
+
data,
|
|
265
|
+
[...relation],
|
|
266
|
+
`${id}_other`,
|
|
267
|
+
type
|
|
268
|
+
);
|
|
269
|
+
|
|
270
|
+
if (otherValue) {
|
|
271
|
+
formattedKey += `: ${otherValue}`;
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
return formattedKey;
|
|
275
|
+
});
|
|
276
|
+
|
|
277
|
+
return formattedKeys.join(', ');
|
|
235
278
|
};
|
|
236
279
|
|
|
237
280
|
const renderDate = () => formatDateValue(value);
|
|
@@ -371,15 +414,15 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
371
414
|
};
|
|
372
415
|
|
|
373
416
|
return (
|
|
374
|
-
<div className=
|
|
375
|
-
<div className=
|
|
417
|
+
<div className={styles.gridtxt}>
|
|
418
|
+
<div className={styles.gridtxt__header}>
|
|
376
419
|
{activeTabConfig.label
|
|
377
420
|
? activeTabConfig.label
|
|
378
421
|
: 'Files'}
|
|
379
422
|
</div>
|
|
380
|
-
<div className=
|
|
423
|
+
<div className={styles.progress}>
|
|
381
424
|
<motion.div
|
|
382
|
-
className=
|
|
425
|
+
className={styles.progress__bar}
|
|
383
426
|
initial={{ width: '0%' }}
|
|
384
427
|
animate={{
|
|
385
428
|
width: loadingProgress + '%',
|
|
@@ -436,7 +479,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
436
479
|
getInputProps,
|
|
437
480
|
isDragActive,
|
|
438
481
|
}) => (
|
|
439
|
-
<section
|
|
482
|
+
<section
|
|
483
|
+
className={
|
|
484
|
+
styles.dropzone__container
|
|
485
|
+
}
|
|
486
|
+
>
|
|
440
487
|
<div {...getRootProps()}>
|
|
441
488
|
<input
|
|
442
489
|
{...getInputProps()}
|
|
@@ -457,7 +504,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
457
504
|
{activeTabConfig.filetype ===
|
|
458
505
|
'image' ? (
|
|
459
506
|
<div>
|
|
460
|
-
<ul
|
|
507
|
+
<ul
|
|
508
|
+
className={
|
|
509
|
+
styles.sortlist
|
|
510
|
+
}
|
|
511
|
+
>
|
|
461
512
|
{files.map(
|
|
462
513
|
(a, b) =>
|
|
463
514
|
a.base64_encoded_image && (
|
|
@@ -467,7 +518,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
467
518
|
{
|
|
468
519
|
a.file_name
|
|
469
520
|
}
|
|
470
|
-
<div
|
|
521
|
+
<div
|
|
522
|
+
className={
|
|
523
|
+
styles.sortimg
|
|
524
|
+
}
|
|
525
|
+
>
|
|
471
526
|
<img
|
|
472
527
|
src={
|
|
473
528
|
a.base64_encoded_image
|
|
@@ -499,7 +554,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
499
554
|
</ul>
|
|
500
555
|
</div>
|
|
501
556
|
) : (
|
|
502
|
-
<ul
|
|
557
|
+
<ul
|
|
558
|
+
className={
|
|
559
|
+
styles.dropzone__files
|
|
560
|
+
}
|
|
561
|
+
>
|
|
503
562
|
{files.map((a, b) => (
|
|
504
563
|
<li
|
|
505
564
|
onClick={() => {
|
|
@@ -622,9 +681,13 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
622
681
|
return (
|
|
623
682
|
<>
|
|
624
683
|
{formConfig.stages?.data?.length > 0 && (
|
|
625
|
-
<div className=
|
|
626
|
-
<div className=
|
|
627
|
-
<div
|
|
684
|
+
<div className={styles.grid}>
|
|
685
|
+
<div className={styles.grid__row}>
|
|
686
|
+
<div
|
|
687
|
+
className={
|
|
688
|
+
styles.grid__full
|
|
689
|
+
}
|
|
690
|
+
>
|
|
628
691
|
{formConfig.stages.data.map(
|
|
629
692
|
(stage) =>
|
|
630
693
|
parseInt(
|
|
@@ -634,12 +697,20 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
634
697
|
key={`stage-form-${stage.id}`}
|
|
635
698
|
>
|
|
636
699
|
{stage.form && (
|
|
637
|
-
<div
|
|
700
|
+
<div
|
|
701
|
+
className={
|
|
702
|
+
styles.gridtxt
|
|
703
|
+
}
|
|
704
|
+
>
|
|
638
705
|
{stage
|
|
639
706
|
.form
|
|
640
707
|
.update
|
|
641
708
|
.title && (
|
|
642
|
-
<div
|
|
709
|
+
<div
|
|
710
|
+
className={
|
|
711
|
+
styles.gridtxt__header
|
|
712
|
+
}
|
|
713
|
+
>
|
|
643
714
|
<span>
|
|
644
715
|
{
|
|
645
716
|
stage
|
|
@@ -694,8 +765,12 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
694
765
|
)}
|
|
695
766
|
|
|
696
767
|
{formConfig.form && (
|
|
697
|
-
<div className=
|
|
698
|
-
<div
|
|
768
|
+
<div className={styles.gridtxt}>
|
|
769
|
+
<div
|
|
770
|
+
className={
|
|
771
|
+
styles.gridtxt__header
|
|
772
|
+
}
|
|
773
|
+
>
|
|
699
774
|
<span>{formConfig.title}</span>
|
|
700
775
|
</div>
|
|
701
776
|
<Form
|
|
@@ -722,13 +797,17 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
722
797
|
case 'overview':
|
|
723
798
|
return (
|
|
724
799
|
<>
|
|
725
|
-
<div className=
|
|
800
|
+
<div className={styles.gridtxt}>
|
|
726
801
|
{activeTabConfig.sections.map(
|
|
727
802
|
(section, sectionIndex) => (
|
|
728
803
|
<React.Fragment
|
|
729
804
|
key={`section-${activeTabConfig.id}-${sectionIndex}`}
|
|
730
805
|
>
|
|
731
|
-
<div
|
|
806
|
+
<div
|
|
807
|
+
className={
|
|
808
|
+
styles.gridtxt__header
|
|
809
|
+
}
|
|
810
|
+
>
|
|
732
811
|
<span>
|
|
733
812
|
{section.title}
|
|
734
813
|
</span>
|
|
@@ -736,7 +815,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
736
815
|
{section.content &&
|
|
737
816
|
section.content.length >
|
|
738
817
|
0 && (
|
|
739
|
-
<ul
|
|
818
|
+
<ul
|
|
819
|
+
className={
|
|
820
|
+
styles.customer__overview
|
|
821
|
+
}
|
|
822
|
+
>
|
|
740
823
|
{section.content.map(
|
|
741
824
|
(
|
|
742
825
|
item,
|
|
@@ -747,7 +830,7 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
747
830
|
className={
|
|
748
831
|
item.size ===
|
|
749
832
|
'full'
|
|
750
|
-
? 'fw-grid-item notecolor
|
|
833
|
+
? `${styles['fw-grid-item']} ${styles.notecolor}`
|
|
751
834
|
: null
|
|
752
835
|
}
|
|
753
836
|
>
|
|
@@ -798,9 +881,9 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
798
881
|
)}
|
|
799
882
|
</div>
|
|
800
883
|
{activeTabConfig.form && (
|
|
801
|
-
<div className=
|
|
884
|
+
<div className={styles.polActions}>
|
|
802
885
|
<button
|
|
803
|
-
className=
|
|
886
|
+
className={styles.btn}
|
|
804
887
|
onClick={() =>
|
|
805
888
|
modalOpen(
|
|
806
889
|
'update',
|
|
@@ -835,8 +918,14 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
835
918
|
.relationship &&
|
|
836
919
|
activeTabConfig.dropzone.url !==
|
|
837
920
|
'' && (
|
|
838
|
-
<div
|
|
839
|
-
|
|
921
|
+
<div
|
|
922
|
+
className={styles.grid__row}
|
|
923
|
+
>
|
|
924
|
+
<div
|
|
925
|
+
className={
|
|
926
|
+
styles.grid__full
|
|
927
|
+
}
|
|
928
|
+
>
|
|
840
929
|
<Dropzone
|
|
841
930
|
onDrop={(
|
|
842
931
|
acceptedFiles
|
|
@@ -915,7 +1004,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
915
1004
|
getInputProps,
|
|
916
1005
|
isDragActive,
|
|
917
1006
|
}) => (
|
|
918
|
-
<section
|
|
1007
|
+
<section
|
|
1008
|
+
className={
|
|
1009
|
+
styles.dropzone__container
|
|
1010
|
+
}
|
|
1011
|
+
>
|
|
919
1012
|
<div
|
|
920
1013
|
{...getRootProps()}
|
|
921
1014
|
>
|
|
@@ -949,9 +1042,15 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
949
1042
|
</section>
|
|
950
1043
|
)}
|
|
951
1044
|
</Dropzone>
|
|
952
|
-
<div
|
|
1045
|
+
<div
|
|
1046
|
+
className={
|
|
1047
|
+
styles.progress
|
|
1048
|
+
}
|
|
1049
|
+
>
|
|
953
1050
|
<motion.div
|
|
954
|
-
className=
|
|
1051
|
+
className={
|
|
1052
|
+
styles.progress__bar
|
|
1053
|
+
}
|
|
955
1054
|
initial={{
|
|
956
1055
|
width: '0%',
|
|
957
1056
|
}}
|
|
@@ -974,8 +1073,8 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
974
1073
|
</div>
|
|
975
1074
|
</div>
|
|
976
1075
|
)}
|
|
977
|
-
<div className=
|
|
978
|
-
<div className=
|
|
1076
|
+
<div className={styles.grid__row}>
|
|
1077
|
+
<div className={styles.grid__full}>
|
|
979
1078
|
<Table
|
|
980
1079
|
{...config}
|
|
981
1080
|
ref={gridRef}
|
|
@@ -1007,7 +1106,7 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
1007
1106
|
|
|
1008
1107
|
{activeTabConfig.functions
|
|
1009
1108
|
?.checkboxUpdate && (
|
|
1010
|
-
<div className=
|
|
1109
|
+
<div className={styles.polActions}>
|
|
1011
1110
|
<button
|
|
1012
1111
|
className="btn"
|
|
1013
1112
|
onClick={
|
|
@@ -1240,12 +1339,12 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
1240
1339
|
|
|
1241
1340
|
return (
|
|
1242
1341
|
<>
|
|
1243
|
-
<div className=
|
|
1244
|
-
<div className=
|
|
1245
|
-
<div className=
|
|
1342
|
+
<div className={styles.grid}>
|
|
1343
|
+
<div className={styles.grid__row}>
|
|
1344
|
+
<div className={`${styles.grid__full} ${styles.crmtitle}`}>
|
|
1246
1345
|
<Breadcrumb data={data} page={page} />
|
|
1247
1346
|
{total > 0 && (
|
|
1248
|
-
<div className=
|
|
1347
|
+
<div className={styles.titleInfo}>
|
|
1249
1348
|
<span>
|
|
1250
1349
|
[<strong>{total}</strong> Total]
|
|
1251
1350
|
</span>
|
|
@@ -1256,11 +1355,11 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
1256
1355
|
</div>
|
|
1257
1356
|
|
|
1258
1357
|
{stages?.data?.length > 0 && (
|
|
1259
|
-
<div className=
|
|
1260
|
-
<div className=
|
|
1261
|
-
<div className=
|
|
1262
|
-
<div className=
|
|
1263
|
-
<ul className=
|
|
1358
|
+
<div className={styles.grid}>
|
|
1359
|
+
<div className={styles.grid__row}>
|
|
1360
|
+
<div className={styles.grid__full}>
|
|
1361
|
+
<div className={styles.oppstatus}>
|
|
1362
|
+
<ul className={styles.opppath}>
|
|
1264
1363
|
{stages.data.map((stage) => {
|
|
1265
1364
|
if (!stage.id) {
|
|
1266
1365
|
return null; // Skip rendering this stage
|
|
@@ -1274,7 +1373,7 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
1274
1373
|
key={`stage-${stage.id}`}
|
|
1275
1374
|
className={
|
|
1276
1375
|
isStageComplete
|
|
1277
|
-
? 'opp-complete'
|
|
1376
|
+
? `${styles['opp-complete']}`
|
|
1278
1377
|
: ''
|
|
1279
1378
|
}
|
|
1280
1379
|
onClick={(e) => {
|
|
@@ -1305,12 +1404,12 @@ function GenericDetail({ extraUrlParam, setting, urlParam, userProfile }) {
|
|
|
1305
1404
|
</div>
|
|
1306
1405
|
)}
|
|
1307
1406
|
|
|
1308
|
-
<div className=
|
|
1309
|
-
<div className=
|
|
1310
|
-
<div className=
|
|
1407
|
+
<div className={styles.grid}>
|
|
1408
|
+
<div className={styles.grid__subrow}>
|
|
1409
|
+
<div className={styles.grid__subnav}>
|
|
1311
1410
|
<TableFilter filters={subnav} setFilters={setSubnav} />
|
|
1312
1411
|
</div>
|
|
1313
|
-
<div className=
|
|
1412
|
+
<div className={styles.grid__subcontent}>
|
|
1314
1413
|
{config ? renderContent() : null}
|
|
1315
1414
|
</div>
|
|
1316
1415
|
</div>
|
|
@@ -4,7 +4,8 @@ import { Routes, Route, Navigate } from 'react-router-dom';
|
|
|
4
4
|
import Call from '../Call';
|
|
5
5
|
import Loader from '../Loader';
|
|
6
6
|
import Navigation from '../Navigation';
|
|
7
|
-
|
|
7
|
+
|
|
8
|
+
import styles from './styles/GenericMain.module.css';
|
|
8
9
|
|
|
9
10
|
const GenericMain = ({
|
|
10
11
|
layout = 'full',
|
|
@@ -65,7 +66,7 @@ const GenericMain = ({
|
|
|
65
66
|
|
|
66
67
|
return (
|
|
67
68
|
<div>
|
|
68
|
-
<header className=
|
|
69
|
+
<header className={styles.header}>
|
|
69
70
|
<Navigation
|
|
70
71
|
layout={layout}
|
|
71
72
|
logo={logo}
|
|
@@ -74,9 +75,9 @@ const GenericMain = ({
|
|
|
74
75
|
userProfile={userProfile}
|
|
75
76
|
/>
|
|
76
77
|
</header>
|
|
77
|
-
<main className=
|
|
78
|
-
<div className=
|
|
79
|
-
<div className=
|
|
78
|
+
<main className={styles.content}>
|
|
79
|
+
<div className={styles['content-main']} id="app">
|
|
80
|
+
<div className={styles.padding}>
|
|
80
81
|
<Routes>
|
|
81
82
|
{renderRoutes(routeConfig)}
|
|
82
83
|
{/* Add a wildcard route for handling unknown paths */}
|