@lasterp/shared 1.0.0-alpha.12 → 1.0.0-alpha.13
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/node/index.d.ts +97 -72
- package/dist/node/index.js +81 -0
- package/dist/rn/index.d.ts +97 -72
- package/dist/rn/index.js +81 -0
- package/package.json +1 -1
package/dist/node/index.d.ts
CHANGED
|
@@ -24,6 +24,79 @@ interface Colour {
|
|
|
24
24
|
hex: string;
|
|
25
25
|
color_system: string;
|
|
26
26
|
}
|
|
27
|
+
interface Globals {
|
|
28
|
+
header: Header;
|
|
29
|
+
footer: Footer;
|
|
30
|
+
}
|
|
31
|
+
interface Brand {
|
|
32
|
+
brandImage?: string;
|
|
33
|
+
}
|
|
34
|
+
interface NavbarItem {
|
|
35
|
+
label: string;
|
|
36
|
+
enableDropdown: boolean;
|
|
37
|
+
enableLink: boolean;
|
|
38
|
+
link?: string;
|
|
39
|
+
dropdownDescription?: string;
|
|
40
|
+
dropdownCTALabel?: string;
|
|
41
|
+
dropdownCTALink?: string;
|
|
42
|
+
groups?: NavbarSubItemGroup[];
|
|
43
|
+
}
|
|
44
|
+
interface NavbarSubItemGroup {
|
|
45
|
+
title: string;
|
|
46
|
+
items: NavbarSubItem[];
|
|
47
|
+
}
|
|
48
|
+
interface NavbarSubItem {
|
|
49
|
+
label: string;
|
|
50
|
+
description?: string;
|
|
51
|
+
image?: string;
|
|
52
|
+
link?: string;
|
|
53
|
+
}
|
|
54
|
+
interface Topbar {
|
|
55
|
+
enabled: boolean;
|
|
56
|
+
layout: string;
|
|
57
|
+
items: TopbarItem[];
|
|
58
|
+
}
|
|
59
|
+
interface TopbarItem {
|
|
60
|
+
icon?: string;
|
|
61
|
+
label: string;
|
|
62
|
+
link?: string;
|
|
63
|
+
}
|
|
64
|
+
interface Header {
|
|
65
|
+
headerType?: string;
|
|
66
|
+
brand: Brand;
|
|
67
|
+
tabs: NavbarItem[];
|
|
68
|
+
topbar: Topbar;
|
|
69
|
+
}
|
|
70
|
+
interface FooterItemGroup {
|
|
71
|
+
title: string;
|
|
72
|
+
items: FooterItem[];
|
|
73
|
+
}
|
|
74
|
+
interface FooterItem {
|
|
75
|
+
label: string;
|
|
76
|
+
link?: string;
|
|
77
|
+
}
|
|
78
|
+
interface Footer {
|
|
79
|
+
footerType?: string;
|
|
80
|
+
groups: FooterItemGroup[];
|
|
81
|
+
copyright?: string;
|
|
82
|
+
address?: string;
|
|
83
|
+
country?: string;
|
|
84
|
+
phone?: string;
|
|
85
|
+
email?: string;
|
|
86
|
+
}
|
|
87
|
+
interface Hero {
|
|
88
|
+
type: string;
|
|
89
|
+
data: Record<string, unknown>;
|
|
90
|
+
}
|
|
91
|
+
interface Block {
|
|
92
|
+
type: string;
|
|
93
|
+
data: Record<string, unknown>;
|
|
94
|
+
}
|
|
95
|
+
interface Page {
|
|
96
|
+
slug: string;
|
|
97
|
+
hero?: Hero;
|
|
98
|
+
blocks: Block[];
|
|
99
|
+
}
|
|
27
100
|
import { FrappeApp, FrappeAuth, FrappeCall } from "frappe-js-sdk";
|
|
28
101
|
import { FrappeDB } from "frappe-js-sdk/lib/db";
|
|
29
102
|
import { FrappeFileUpload } from "frappe-js-sdk/lib/file";
|
|
@@ -513,79 +586,31 @@ declare const useFrappeUpdateDoc: <T = any>() => {
|
|
|
513
586
|
isCompleted: boolean;
|
|
514
587
|
reset: () => void;
|
|
515
588
|
};
|
|
516
|
-
interface
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
}
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
groups?: NavbarSubItemGroup[];
|
|
532
|
-
}
|
|
533
|
-
interface NavbarSubItemGroup {
|
|
534
|
-
title: string;
|
|
535
|
-
items: NavbarSubItem[];
|
|
536
|
-
}
|
|
537
|
-
interface NavbarSubItem {
|
|
538
|
-
label: string;
|
|
539
|
-
description?: string;
|
|
540
|
-
image?: string;
|
|
541
|
-
link?: string;
|
|
542
|
-
}
|
|
543
|
-
interface Topbar {
|
|
544
|
-
enabled: boolean;
|
|
545
|
-
layout: string;
|
|
546
|
-
items: TopbarItem[];
|
|
547
|
-
}
|
|
548
|
-
interface TopbarItem {
|
|
549
|
-
icon?: string;
|
|
550
|
-
label: string;
|
|
551
|
-
link?: string;
|
|
552
|
-
}
|
|
553
|
-
interface Header {
|
|
554
|
-
headerType?: string;
|
|
555
|
-
brand: Brand;
|
|
556
|
-
tabs: NavbarItem[];
|
|
557
|
-
topbar: Topbar;
|
|
558
|
-
}
|
|
559
|
-
interface FooterItemGroup {
|
|
560
|
-
title: string;
|
|
561
|
-
items: FooterItem[];
|
|
562
|
-
}
|
|
563
|
-
interface FooterItem {
|
|
564
|
-
label: string;
|
|
565
|
-
link?: string;
|
|
566
|
-
}
|
|
567
|
-
interface Footer {
|
|
568
|
-
footerType?: string;
|
|
569
|
-
groups: FooterItemGroup[];
|
|
570
|
-
copyright?: string;
|
|
571
|
-
address?: string;
|
|
572
|
-
country?: string;
|
|
573
|
-
phone?: string;
|
|
574
|
-
email?: string;
|
|
575
|
-
}
|
|
576
|
-
interface Hero {
|
|
577
|
-
type: string;
|
|
578
|
-
data: Record<string, unknown>;
|
|
579
|
-
}
|
|
580
|
-
interface Block {
|
|
581
|
-
type: string;
|
|
582
|
-
data: Record<string, unknown>;
|
|
589
|
+
interface VariantSelectorProps<T extends {
|
|
590
|
+
id: string;
|
|
591
|
+
specs: Record<string, string>;
|
|
592
|
+
}> {
|
|
593
|
+
variants: T[];
|
|
594
|
+
attributes: {
|
|
595
|
+
key: string;
|
|
596
|
+
values: string[];
|
|
597
|
+
}[];
|
|
598
|
+
defaultId?: string;
|
|
599
|
+
}
|
|
600
|
+
interface VariantSelectorOption {
|
|
601
|
+
key: string;
|
|
602
|
+
value: string;
|
|
603
|
+
state: "selected" | "available" | "unavailable";
|
|
583
604
|
}
|
|
584
|
-
interface
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
605
|
+
interface VariantSelectorResult {
|
|
606
|
+
variantId?: string;
|
|
607
|
+
onOptionSelect: (option: VariantSelectorOption) => void;
|
|
608
|
+
getOptions: (key: string) => VariantSelectorOption[];
|
|
588
609
|
}
|
|
610
|
+
declare const useVariantSelector: <T extends {
|
|
611
|
+
id: string;
|
|
612
|
+
specs: Record<string, string>;
|
|
613
|
+
}>(props: VariantSelectorProps<T>) => VariantSelectorResult;
|
|
589
614
|
interface Category {
|
|
590
615
|
name: string;
|
|
591
616
|
}
|
|
@@ -608,4 +633,4 @@ interface ShopContext {
|
|
|
608
633
|
}
|
|
609
634
|
import { camelize, decamelize, camelizeKeys, decamelizeKeys } from "humps";
|
|
610
635
|
declare function equalsIgnoreCase(str1: string, str2: string): boolean;
|
|
611
|
-
export { useSearch, useFrappeUpdateDoc, useFrappePutCall, useFrappePrefetchDoc, useFrappePostCall, useFrappeGetDocList, useFrappeGetDocCount, useFrappeGetDoc, useFrappeGetCall, useFrappeFileUpload, useFrappeEventListener, useFrappeDocumentEventListener, useFrappeDocTypeEventListener, useFrappeDeleteDoc, useFrappeDeleteCall, useFrappeCreateDoc, useFrappeAuth, equalsIgnoreCase, decamelizeKeys, decamelize, camelizeKeys, camelize, ViewerEventData, UseFrappeFileUploadReturnType, TopbarItem, Topbar, TokenParams, ShopContext, SearchResult, ProductVariant, Product, Page, NavbarSubItemGroup, NavbarSubItem, NavbarItem, Model, ItemVariant, Item, Hero, Header, Globals, FrappeProviderProps, FrappeProvider, FrappeMutationResult, FrappeFileUploadResponse, FrappeError, FrappeContext, FrappeConfig, FooterItemGroup, FooterItem, Footer, DocumentUpdateEventData, DocTypeListUpdateEventData, Colour, Category, Brand, Block };
|
|
636
|
+
export { useVariantSelector, useSearch, useFrappeUpdateDoc, useFrappePutCall, useFrappePrefetchDoc, useFrappePostCall, useFrappeGetDocList, useFrappeGetDocCount, useFrappeGetDoc, useFrappeGetCall, useFrappeFileUpload, useFrappeEventListener, useFrappeDocumentEventListener, useFrappeDocTypeEventListener, useFrappeDeleteDoc, useFrappeDeleteCall, useFrappeCreateDoc, useFrappeAuth, equalsIgnoreCase, decamelizeKeys, decamelize, camelizeKeys, camelize, ViewerEventData, VariantSelectorResult, VariantSelectorProps, VariantSelectorOption, UseFrappeFileUploadReturnType, TopbarItem, Topbar, TokenParams, ShopContext, SearchResult, ProductVariant, Product, Page, NavbarSubItemGroup, NavbarSubItem, NavbarItem, Model, ItemVariant, Item, Hero, Header, Globals, FrappeProviderProps, FrappeProvider, FrappeMutationResult, FrappeFileUploadResponse, FrappeError, FrappeContext, FrappeConfig, FooterItemGroup, FooterItem, Footer, DocumentUpdateEventData, DocTypeListUpdateEventData, Colour, Category, Brand, Block };
|
package/dist/node/index.js
CHANGED
|
@@ -465,12 +465,93 @@ var useFrappeUpdateDoc = () => {
|
|
|
465
465
|
reset
|
|
466
466
|
};
|
|
467
467
|
};
|
|
468
|
+
// src/hooks/use-variant-selector/hook.ts
|
|
469
|
+
import { useCallback as useCallback4, useMemo as useMemo2, useState as useState5 } from "react";
|
|
470
|
+
|
|
471
|
+
// src/hooks/use-variant-selector/utils.ts
|
|
472
|
+
function findVariant(variants, specs, caseInsensitive) {
|
|
473
|
+
return variants.find((variant) => {
|
|
474
|
+
return Object.entries(specs).every(([key, value]) => {
|
|
475
|
+
const vv = variant.specs[key];
|
|
476
|
+
if (!vv)
|
|
477
|
+
return false;
|
|
478
|
+
if (caseInsensitive) {
|
|
479
|
+
return vv.toLowerCase() === value.toLowerCase();
|
|
480
|
+
}
|
|
481
|
+
return vv === value;
|
|
482
|
+
});
|
|
483
|
+
});
|
|
484
|
+
}
|
|
485
|
+
function findVariants(variants, specs, caseInsensitive) {
|
|
486
|
+
return variants.filter((variant) => {
|
|
487
|
+
return Object.entries(specs).every(([key, value]) => {
|
|
488
|
+
const vv = variant.specs[key];
|
|
489
|
+
if (!vv)
|
|
490
|
+
return false;
|
|
491
|
+
if (caseInsensitive) {
|
|
492
|
+
return vv.toLowerCase() === value.toLowerCase();
|
|
493
|
+
}
|
|
494
|
+
return vv === value;
|
|
495
|
+
});
|
|
496
|
+
});
|
|
497
|
+
}
|
|
498
|
+
|
|
499
|
+
// src/hooks/use-variant-selector/hook.ts
|
|
500
|
+
var useVariantSelector = (props) => {
|
|
501
|
+
const { variants, attributes, defaultId } = props;
|
|
502
|
+
const [selectedSpecs, setSelectedSpecs] = useState5(() => {
|
|
503
|
+
if (defaultId) {
|
|
504
|
+
const variant = variants.find((v) => v.id === defaultId);
|
|
505
|
+
return variant?.specs || {};
|
|
506
|
+
}
|
|
507
|
+
return {};
|
|
508
|
+
});
|
|
509
|
+
const variantId = useMemo2(() => {
|
|
510
|
+
const complete = attributes.every((attr) => selectedSpecs[attr.key]);
|
|
511
|
+
if (!complete)
|
|
512
|
+
return;
|
|
513
|
+
const variant = findVariant(variants, selectedSpecs);
|
|
514
|
+
return variant?.id;
|
|
515
|
+
}, [variants, selectedSpecs, attributes]);
|
|
516
|
+
const options = useMemo2(() => {
|
|
517
|
+
const result = {};
|
|
518
|
+
attributes.forEach((attr) => {
|
|
519
|
+
result[attr.key] = attr.values.map((value) => {
|
|
520
|
+
const isSelected = selectedSpecs[attr.key] === value;
|
|
521
|
+
const specs = { ...selectedSpecs };
|
|
522
|
+
delete specs[attr.key];
|
|
523
|
+
const matchingVariants = findVariants(variants, specs);
|
|
524
|
+
const availableValuesForAttr = new Set(matchingVariants.map((v) => v.specs[attr.key]));
|
|
525
|
+
const isAvailable = availableValuesForAttr.has(value);
|
|
526
|
+
return {
|
|
527
|
+
key: attr.key,
|
|
528
|
+
value,
|
|
529
|
+
state: isSelected ? "selected" : isAvailable ? "available" : "unavailable"
|
|
530
|
+
};
|
|
531
|
+
});
|
|
532
|
+
});
|
|
533
|
+
return result;
|
|
534
|
+
}, [variants, attributes, selectedSpecs]);
|
|
535
|
+
const onOptionSelect = useCallback4((option) => {
|
|
536
|
+
setSelectedSpecs((prev) => {
|
|
537
|
+
const specs = { ...prev };
|
|
538
|
+
specs[option.key] = option.value;
|
|
539
|
+
return specs;
|
|
540
|
+
});
|
|
541
|
+
}, []);
|
|
542
|
+
return {
|
|
543
|
+
variantId,
|
|
544
|
+
onOptionSelect,
|
|
545
|
+
getOptions: (key) => options[key] || []
|
|
546
|
+
};
|
|
547
|
+
};
|
|
468
548
|
// src/utils/char.ts
|
|
469
549
|
import { camelize, decamelize, camelizeKeys, decamelizeKeys } from "humps";
|
|
470
550
|
function equalsIgnoreCase(str1, str2) {
|
|
471
551
|
return str1.localeCompare(str2, undefined, { sensitivity: "accent" }) === 0;
|
|
472
552
|
}
|
|
473
553
|
export {
|
|
554
|
+
useVariantSelector,
|
|
474
555
|
useSearch,
|
|
475
556
|
useFrappeUpdateDoc,
|
|
476
557
|
useFrappePutCall,
|
package/dist/rn/index.d.ts
CHANGED
|
@@ -24,6 +24,79 @@ interface Colour {
|
|
|
24
24
|
hex: string;
|
|
25
25
|
color_system: string;
|
|
26
26
|
}
|
|
27
|
+
interface Globals {
|
|
28
|
+
header: Header;
|
|
29
|
+
footer: Footer;
|
|
30
|
+
}
|
|
31
|
+
interface Brand {
|
|
32
|
+
brandImage?: string;
|
|
33
|
+
}
|
|
34
|
+
interface NavbarItem {
|
|
35
|
+
label: string;
|
|
36
|
+
enableDropdown: boolean;
|
|
37
|
+
enableLink: boolean;
|
|
38
|
+
link?: string;
|
|
39
|
+
dropdownDescription?: string;
|
|
40
|
+
dropdownCTALabel?: string;
|
|
41
|
+
dropdownCTALink?: string;
|
|
42
|
+
groups?: NavbarSubItemGroup[];
|
|
43
|
+
}
|
|
44
|
+
interface NavbarSubItemGroup {
|
|
45
|
+
title: string;
|
|
46
|
+
items: NavbarSubItem[];
|
|
47
|
+
}
|
|
48
|
+
interface NavbarSubItem {
|
|
49
|
+
label: string;
|
|
50
|
+
description?: string;
|
|
51
|
+
image?: string;
|
|
52
|
+
link?: string;
|
|
53
|
+
}
|
|
54
|
+
interface Topbar {
|
|
55
|
+
enabled: boolean;
|
|
56
|
+
layout: string;
|
|
57
|
+
items: TopbarItem[];
|
|
58
|
+
}
|
|
59
|
+
interface TopbarItem {
|
|
60
|
+
icon?: string;
|
|
61
|
+
label: string;
|
|
62
|
+
link?: string;
|
|
63
|
+
}
|
|
64
|
+
interface Header {
|
|
65
|
+
headerType?: string;
|
|
66
|
+
brand: Brand;
|
|
67
|
+
tabs: NavbarItem[];
|
|
68
|
+
topbar: Topbar;
|
|
69
|
+
}
|
|
70
|
+
interface FooterItemGroup {
|
|
71
|
+
title: string;
|
|
72
|
+
items: FooterItem[];
|
|
73
|
+
}
|
|
74
|
+
interface FooterItem {
|
|
75
|
+
label: string;
|
|
76
|
+
link?: string;
|
|
77
|
+
}
|
|
78
|
+
interface Footer {
|
|
79
|
+
footerType?: string;
|
|
80
|
+
groups: FooterItemGroup[];
|
|
81
|
+
copyright?: string;
|
|
82
|
+
address?: string;
|
|
83
|
+
country?: string;
|
|
84
|
+
phone?: string;
|
|
85
|
+
email?: string;
|
|
86
|
+
}
|
|
87
|
+
interface Hero {
|
|
88
|
+
type: string;
|
|
89
|
+
data: Record<string, unknown>;
|
|
90
|
+
}
|
|
91
|
+
interface Block {
|
|
92
|
+
type: string;
|
|
93
|
+
data: Record<string, unknown>;
|
|
94
|
+
}
|
|
95
|
+
interface Page {
|
|
96
|
+
slug: string;
|
|
97
|
+
hero?: Hero;
|
|
98
|
+
blocks: Block[];
|
|
99
|
+
}
|
|
27
100
|
import { FrappeApp, FrappeAuth, FrappeCall } from "frappe-js-sdk";
|
|
28
101
|
import { FrappeDB } from "frappe-js-sdk/lib/db";
|
|
29
102
|
import { FrappeFileUpload } from "frappe-js-sdk/lib/file";
|
|
@@ -513,79 +586,31 @@ declare const useFrappeUpdateDoc: <T = any>() => {
|
|
|
513
586
|
isCompleted: boolean;
|
|
514
587
|
reset: () => void;
|
|
515
588
|
};
|
|
516
|
-
interface
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
}
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
groups?: NavbarSubItemGroup[];
|
|
532
|
-
}
|
|
533
|
-
interface NavbarSubItemGroup {
|
|
534
|
-
title: string;
|
|
535
|
-
items: NavbarSubItem[];
|
|
536
|
-
}
|
|
537
|
-
interface NavbarSubItem {
|
|
538
|
-
label: string;
|
|
539
|
-
description?: string;
|
|
540
|
-
image?: string;
|
|
541
|
-
link?: string;
|
|
542
|
-
}
|
|
543
|
-
interface Topbar {
|
|
544
|
-
enabled: boolean;
|
|
545
|
-
layout: string;
|
|
546
|
-
items: TopbarItem[];
|
|
547
|
-
}
|
|
548
|
-
interface TopbarItem {
|
|
549
|
-
icon?: string;
|
|
550
|
-
label: string;
|
|
551
|
-
link?: string;
|
|
552
|
-
}
|
|
553
|
-
interface Header {
|
|
554
|
-
headerType?: string;
|
|
555
|
-
brand: Brand;
|
|
556
|
-
tabs: NavbarItem[];
|
|
557
|
-
topbar: Topbar;
|
|
558
|
-
}
|
|
559
|
-
interface FooterItemGroup {
|
|
560
|
-
title: string;
|
|
561
|
-
items: FooterItem[];
|
|
562
|
-
}
|
|
563
|
-
interface FooterItem {
|
|
564
|
-
label: string;
|
|
565
|
-
link?: string;
|
|
566
|
-
}
|
|
567
|
-
interface Footer {
|
|
568
|
-
footerType?: string;
|
|
569
|
-
groups: FooterItemGroup[];
|
|
570
|
-
copyright?: string;
|
|
571
|
-
address?: string;
|
|
572
|
-
country?: string;
|
|
573
|
-
phone?: string;
|
|
574
|
-
email?: string;
|
|
575
|
-
}
|
|
576
|
-
interface Hero {
|
|
577
|
-
type: string;
|
|
578
|
-
data: Record<string, unknown>;
|
|
579
|
-
}
|
|
580
|
-
interface Block {
|
|
581
|
-
type: string;
|
|
582
|
-
data: Record<string, unknown>;
|
|
589
|
+
interface VariantSelectorProps<T extends {
|
|
590
|
+
id: string;
|
|
591
|
+
specs: Record<string, string>;
|
|
592
|
+
}> {
|
|
593
|
+
variants: T[];
|
|
594
|
+
attributes: {
|
|
595
|
+
key: string;
|
|
596
|
+
values: string[];
|
|
597
|
+
}[];
|
|
598
|
+
defaultId?: string;
|
|
599
|
+
}
|
|
600
|
+
interface VariantSelectorOption {
|
|
601
|
+
key: string;
|
|
602
|
+
value: string;
|
|
603
|
+
state: "selected" | "available" | "unavailable";
|
|
583
604
|
}
|
|
584
|
-
interface
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
605
|
+
interface VariantSelectorResult {
|
|
606
|
+
variantId?: string;
|
|
607
|
+
onOptionSelect: (option: VariantSelectorOption) => void;
|
|
608
|
+
getOptions: (key: string) => VariantSelectorOption[];
|
|
588
609
|
}
|
|
610
|
+
declare const useVariantSelector: <T extends {
|
|
611
|
+
id: string;
|
|
612
|
+
specs: Record<string, string>;
|
|
613
|
+
}>(props: VariantSelectorProps<T>) => VariantSelectorResult;
|
|
589
614
|
interface Category {
|
|
590
615
|
name: string;
|
|
591
616
|
}
|
|
@@ -608,4 +633,4 @@ interface ShopContext {
|
|
|
608
633
|
}
|
|
609
634
|
import { camelize, decamelize, camelizeKeys, decamelizeKeys } from "humps";
|
|
610
635
|
declare function equalsIgnoreCase(str1: string, str2: string): boolean;
|
|
611
|
-
export { useSearch, useFrappeUpdateDoc, useFrappePutCall, useFrappePrefetchDoc, useFrappePostCall, useFrappeGetDocList, useFrappeGetDocCount, useFrappeGetDoc, useFrappeGetCall, useFrappeFileUpload, useFrappeEventListener, useFrappeDocumentEventListener, useFrappeDocTypeEventListener, useFrappeDeleteDoc, useFrappeDeleteCall, useFrappeCreateDoc, useFrappeAuth, equalsIgnoreCase, decamelizeKeys, decamelize, camelizeKeys, camelize, ViewerEventData, UseFrappeFileUploadReturnType, TopbarItem, Topbar, TokenParams, ShopContext, SearchResult, ProductVariant, Product, Page, NavbarSubItemGroup, NavbarSubItem, NavbarItem, Model, ItemVariant, Item, Hero, Header, Globals, FrappeProviderProps, FrappeProvider, FrappeMutationResult, FrappeFileUploadResponse, FrappeError, FrappeContext, FrappeConfig, FooterItemGroup, FooterItem, Footer, DocumentUpdateEventData, DocTypeListUpdateEventData, Colour, Category, Brand, Block };
|
|
636
|
+
export { useVariantSelector, useSearch, useFrappeUpdateDoc, useFrappePutCall, useFrappePrefetchDoc, useFrappePostCall, useFrappeGetDocList, useFrappeGetDocCount, useFrappeGetDoc, useFrappeGetCall, useFrappeFileUpload, useFrappeEventListener, useFrappeDocumentEventListener, useFrappeDocTypeEventListener, useFrappeDeleteDoc, useFrappeDeleteCall, useFrappeCreateDoc, useFrappeAuth, equalsIgnoreCase, decamelizeKeys, decamelize, camelizeKeys, camelize, ViewerEventData, VariantSelectorResult, VariantSelectorProps, VariantSelectorOption, UseFrappeFileUploadReturnType, TopbarItem, Topbar, TokenParams, ShopContext, SearchResult, ProductVariant, Product, Page, NavbarSubItemGroup, NavbarSubItem, NavbarItem, Model, ItemVariant, Item, Hero, Header, Globals, FrappeProviderProps, FrappeProvider, FrappeMutationResult, FrappeFileUploadResponse, FrappeError, FrappeContext, FrappeConfig, FooterItemGroup, FooterItem, Footer, DocumentUpdateEventData, DocTypeListUpdateEventData, Colour, Category, Brand, Block };
|
package/dist/rn/index.js
CHANGED
|
@@ -465,12 +465,93 @@ var useFrappeUpdateDoc = () => {
|
|
|
465
465
|
reset
|
|
466
466
|
};
|
|
467
467
|
};
|
|
468
|
+
// src/hooks/use-variant-selector/hook.ts
|
|
469
|
+
import { useCallback as useCallback4, useMemo as useMemo2, useState as useState5 } from "react";
|
|
470
|
+
|
|
471
|
+
// src/hooks/use-variant-selector/utils.ts
|
|
472
|
+
function findVariant(variants, specs, caseInsensitive) {
|
|
473
|
+
return variants.find((variant) => {
|
|
474
|
+
return Object.entries(specs).every(([key, value]) => {
|
|
475
|
+
const vv = variant.specs[key];
|
|
476
|
+
if (!vv)
|
|
477
|
+
return false;
|
|
478
|
+
if (caseInsensitive) {
|
|
479
|
+
return vv.toLowerCase() === value.toLowerCase();
|
|
480
|
+
}
|
|
481
|
+
return vv === value;
|
|
482
|
+
});
|
|
483
|
+
});
|
|
484
|
+
}
|
|
485
|
+
function findVariants(variants, specs, caseInsensitive) {
|
|
486
|
+
return variants.filter((variant) => {
|
|
487
|
+
return Object.entries(specs).every(([key, value]) => {
|
|
488
|
+
const vv = variant.specs[key];
|
|
489
|
+
if (!vv)
|
|
490
|
+
return false;
|
|
491
|
+
if (caseInsensitive) {
|
|
492
|
+
return vv.toLowerCase() === value.toLowerCase();
|
|
493
|
+
}
|
|
494
|
+
return vv === value;
|
|
495
|
+
});
|
|
496
|
+
});
|
|
497
|
+
}
|
|
498
|
+
|
|
499
|
+
// src/hooks/use-variant-selector/hook.ts
|
|
500
|
+
var useVariantSelector = (props) => {
|
|
501
|
+
const { variants, attributes, defaultId } = props;
|
|
502
|
+
const [selectedSpecs, setSelectedSpecs] = useState5(() => {
|
|
503
|
+
if (defaultId) {
|
|
504
|
+
const variant = variants.find((v) => v.id === defaultId);
|
|
505
|
+
return variant?.specs || {};
|
|
506
|
+
}
|
|
507
|
+
return {};
|
|
508
|
+
});
|
|
509
|
+
const variantId = useMemo2(() => {
|
|
510
|
+
const complete = attributes.every((attr) => selectedSpecs[attr.key]);
|
|
511
|
+
if (!complete)
|
|
512
|
+
return;
|
|
513
|
+
const variant = findVariant(variants, selectedSpecs);
|
|
514
|
+
return variant?.id;
|
|
515
|
+
}, [variants, selectedSpecs, attributes]);
|
|
516
|
+
const options = useMemo2(() => {
|
|
517
|
+
const result = {};
|
|
518
|
+
attributes.forEach((attr) => {
|
|
519
|
+
result[attr.key] = attr.values.map((value) => {
|
|
520
|
+
const isSelected = selectedSpecs[attr.key] === value;
|
|
521
|
+
const specs = { ...selectedSpecs };
|
|
522
|
+
delete specs[attr.key];
|
|
523
|
+
const matchingVariants = findVariants(variants, specs);
|
|
524
|
+
const availableValuesForAttr = new Set(matchingVariants.map((v) => v.specs[attr.key]));
|
|
525
|
+
const isAvailable = availableValuesForAttr.has(value);
|
|
526
|
+
return {
|
|
527
|
+
key: attr.key,
|
|
528
|
+
value,
|
|
529
|
+
state: isSelected ? "selected" : isAvailable ? "available" : "unavailable"
|
|
530
|
+
};
|
|
531
|
+
});
|
|
532
|
+
});
|
|
533
|
+
return result;
|
|
534
|
+
}, [variants, attributes, selectedSpecs]);
|
|
535
|
+
const onOptionSelect = useCallback4((option) => {
|
|
536
|
+
setSelectedSpecs((prev) => {
|
|
537
|
+
const specs = { ...prev };
|
|
538
|
+
specs[option.key] = option.value;
|
|
539
|
+
return specs;
|
|
540
|
+
});
|
|
541
|
+
}, []);
|
|
542
|
+
return {
|
|
543
|
+
variantId,
|
|
544
|
+
onOptionSelect,
|
|
545
|
+
getOptions: (key) => options[key] || []
|
|
546
|
+
};
|
|
547
|
+
};
|
|
468
548
|
// src/utils/char.ts
|
|
469
549
|
import { camelize, decamelize, camelizeKeys, decamelizeKeys } from "humps";
|
|
470
550
|
function equalsIgnoreCase(str1, str2) {
|
|
471
551
|
return str1.localeCompare(str2, undefined, { sensitivity: "accent" }) === 0;
|
|
472
552
|
}
|
|
473
553
|
export {
|
|
554
|
+
useVariantSelector,
|
|
474
555
|
useSearch,
|
|
475
556
|
useFrappeUpdateDoc,
|
|
476
557
|
useFrappePutCall,
|