@licklist/design 0.63.0 → 0.63.1-dev.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.
- package/bitbucket-pipelines.yml +0 -8
- package/dist/date-time-button/DateTimeButton.js +1 -1
- package/dist/events/edit-event-modal/component/SelectEventProductSet/SelectEventProductSet.d.ts.map +1 -1
- package/dist/events/edit-event-modal/component/SelectEventProductSet/SelectEventProductSet.js +1 -1
- package/dist/events/edit-event-modal/component/SelectEventProductSet/component/EditEventProductSet.d.ts.map +1 -1
- package/dist/events/edit-event-modal/component/SelectEventProductSet/component/EditEventProductSet.js +1 -1
- package/dist/iframe/payment/order-items-table/utils/paymentSummary.js +1 -1
- package/dist/product-set/control/DateAndRecurrenceInput.d.ts +1 -5
- package/dist/product-set/control/DateAndRecurrenceInput.d.ts.map +1 -1
- package/dist/product-set/control/DateAndRecurrenceInput.js +1 -1
- package/dist/product-set/control/DateInput.d.ts.map +1 -1
- package/dist/product-set/control/DateInput.js +1 -1
- package/dist/product-set/control/ProductSetControl.d.ts +4 -3
- package/dist/product-set/control/ProductSetControl.d.ts.map +1 -1
- package/dist/product-set/control/ProductSetControl.js +1 -1
- package/dist/product-set/control/utils.d.ts +5 -0
- package/dist/product-set/control/utils.d.ts.map +1 -0
- package/dist/product-set/control/utils.js +1 -0
- package/dist/product-set/form/ProductCategoriesControl.d.ts +2 -1
- package/dist/product-set/form/ProductCategoriesControl.d.ts.map +1 -1
- package/dist/product-set/form/ProductCategoriesControl.js +1 -1
- package/dist/product-set/form/ProductSetForm.d.ts +4 -1
- package/dist/product-set/form/ProductSetForm.d.ts.map +1 -1
- package/dist/product-set/form/ProductsControl.d.ts +2 -1
- package/dist/product-set/form/ProductsControl.d.ts.map +1 -1
- package/dist/product-set/form/ProductsControl.js +1 -1
- package/dist/product-set/form/StepsControl.d.ts +2 -1
- package/dist/product-set/form/StepsControl.d.ts.map +1 -1
- package/dist/product-set/form/StepsControl.js +1 -1
- package/dist/product-set/hooks/useSortableTreeFunctions.d.ts.map +1 -1
- package/dist/product-set/product/ProductControl.d.ts +1 -0
- package/dist/product-set/product/ProductControl.d.ts.map +1 -1
- package/dist/product-set/product/ProductControl.js +1 -1
- package/dist/product-set/product/fixed-duration-fields/FixedDurationOptions.d.ts.map +1 -1
- package/dist/product-set/step/StepControl.d.ts +2 -1
- package/dist/product-set/step/StepControl.d.ts.map +1 -1
- package/dist/product-set/step/StepControl.js +1 -1
- package/dist/provider/working-hours-input/WorkingHoursInputDescription.d.ts.map +1 -1
- package/dist/provider/working-hours-input/WorkingHoursInputDescription.js +1 -1
- package/dist/recurring-date-picker-input/RecurrenceAndFrequencyInput.d.ts.map +1 -1
- package/dist/recurring-date-picker-input/RecurringDatePickerInput.d.ts +3 -1
- package/dist/recurring-date-picker-input/RecurringDatePickerInput.d.ts.map +1 -1
- package/dist/recurring-date-picker-input/RecurringDatePickerInput.js +1 -1
- package/dist/recurring-date-picker-input/utils.d.ts +6 -0
- package/dist/recurring-date-picker-input/utils.d.ts.map +1 -1
- package/dist/recurring-date-picker-input/utils.js +1 -1
- package/dist/sales/booking/results/components/ResultCard.d.ts.map +1 -1
- package/dist/sales/booking/results/components/ResultCard.js +1 -1
- package/dist/sales/coupon/control/CouponFormControl.d.ts +2 -1
- package/dist/sales/coupon/control/CouponFormControl.d.ts.map +1 -1
- package/dist/sales/coupon/control/CouponFormControl.js +1 -1
- package/dist/sales/coupon/form/CouponFrom.d.ts +2 -2
- package/dist/sales/coupon/form/CouponFrom.d.ts.map +1 -1
- package/dist/sales/coupon/utils/index.d.ts +7 -0
- package/dist/sales/coupon/utils/index.d.ts.map +1 -0
- package/dist/sales/coupon/utils/index.js +1 -0
- package/dist/setting/admin/AdminSettingForm.d.ts +2 -2
- package/dist/setting/admin/AdminSettingForm.d.ts.map +1 -1
- package/dist/setting/dashboard/DashboardSettingForm.d.ts +1 -0
- package/dist/setting/dashboard/DashboardSettingForm.d.ts.map +1 -1
- package/dist/setting/dashboard/DashboardSettingForm.js +1 -1
- package/dist/sortable-tree/SortableTreeItem.d.ts +1 -2
- package/dist/sortable-tree/SortableTreeItem.d.ts.map +1 -1
- package/dist/sortable-tree/SortableTreeItem.js +1 -1
- package/dist/styles/sales/BookingResults.scss +1 -1
- package/dist/typeahead/Typeahead.d.ts +2 -1
- package/dist/typeahead/Typeahead.d.ts.map +1 -1
- package/dist/typeahead/Typeahead.js +1 -1
- package/dist/zone/form/ZoneForm.d.ts +2 -2
- package/dist/zone/form/ZoneForm.d.ts.map +1 -1
- package/dist/zone/form/ZoneForm.js +1 -1
- package/dist/zone/form/components/AvailableTimesControl.d.ts +0 -2
- package/dist/zone/form/components/AvailableTimesControl.d.ts.map +1 -1
- package/dist/zone/form/components/ZoneControl.d.ts +2 -2
- package/dist/zone/form/components/ZoneControl.d.ts.map +1 -1
- package/dist/zone/form/components/ZoneControl.js +1 -1
- package/dist/zone/form/components/ZoneRecurrencesControl.d.ts +4 -4
- package/dist/zone/form/components/ZoneRecurrencesControl.d.ts.map +1 -1
- package/dist/zone/form/components/ZoneRecurrencesControl.js +1 -1
- package/dist/zone/form/utils/dates.d.ts.map +1 -1
- package/package.json +10 -35
- package/src/date-time-button/DateTimeButton.stories.tsx +2 -1
- package/src/date-time-button/DateTimeButton.tsx +7 -5
- package/src/events/edit-event-modal/component/SelectEventProductSet/SelectEventProductSet.tsx +14 -9
- package/src/events/edit-event-modal/component/SelectEventProductSet/component/EditEventProductSet.tsx +2 -0
- package/src/iframe/payment/order-items-table/utils/paymentSummary.tsx +6 -6
- package/src/product-set/control/DateAndRecurrenceInput.tsx +48 -14
- package/src/product-set/control/DateInput.tsx +2 -4
- package/src/product-set/control/ProductSetControl.stories.tsx +1 -1
- package/src/product-set/control/ProductSetControl.tsx +12 -11
- package/src/product-set/control/utils.ts +25 -0
- package/src/product-set/form/ProductCategoriesControl.tsx +8 -4
- package/src/product-set/form/ProductSetForm.stories.tsx +1 -2
- package/src/product-set/form/ProductSetForm.tsx +5 -1
- package/src/product-set/form/ProductsControl.tsx +87 -77
- package/src/product-set/form/StepsControl.tsx +11 -6
- package/src/product-set/hooks/useSortableTreeFunctions.ts +2 -0
- package/src/product-set/product/ProductControl.tsx +39 -39
- package/src/product-set/product/fixed-duration-fields/FixedDurationOptions.tsx +0 -2
- package/src/product-set/step/StepControl.tsx +4 -3
- package/src/provider/working-hours-input/WorkingHoursInputDescription.tsx +4 -18
- package/src/recurring-date-picker-input/RecurrenceAndFrequencyInput.tsx +0 -1
- package/src/recurring-date-picker-input/RecurringDatePickerInput.stories.tsx +13 -7
- package/src/recurring-date-picker-input/RecurringDatePickerInput.tsx +12 -1
- package/src/recurring-date-picker-input/utils.ts +82 -1
- package/src/sales/booking/results/BookingResults.stories.tsx +3 -2
- package/src/sales/booking/results/components/ResultCard.tsx +2 -5
- package/src/sales/coupon/control/CouponFormControl.tsx +28 -51
- package/src/sales/coupon/form/CouponFrom.tsx +5 -15
- package/src/sales/coupon/utils/index.ts +13 -0
- package/src/setting/admin/AdminSettingForm.tsx +2 -2
- package/src/setting/dashboard/DashboardSettingForm.tsx +13 -0
- package/src/sortable-tree/SortableTreeItem.tsx +1 -4
- package/src/static/switch/BooleanSwitch.tsx +1 -1
- package/src/styles/sales/BookingResults.scss +1 -1
- package/src/typeahead/Typeahead.tsx +16 -3
- package/src/zone/form/ZoneForm.tsx +3 -2
- package/src/zone/form/components/AvailableTimesControl.tsx +0 -2
- package/src/zone/form/components/ZoneControl.tsx +3 -3
- package/src/zone/form/components/ZoneRecurrencesControl.tsx +7 -5
- package/src/zone/form/utils/dates.ts +9 -10
- package/jest.config.js +0 -29
- package/tests/Auth/Authorizer.test.tsx +0 -194
- package/tests/Auth/Layout/UserNavDropDown.test.tsx +0 -43
- package/tests/Auth/Layout/UserNavDropDownToggle.test.tsx +0 -33
- package/tests/Auth/Login/LoginComponent.test.tsx +0 -246
- package/tests/Auth/Login/LoginFormComponent.test.tsx +0 -182
- package/tests/Auth/Register/RegisterComponent.test.tsx +0 -285
- package/tests/Auth/Register/RegisterFormComponent.test.tsx +0 -170
- package/tests/Auth/Settings/Dashboard/IpInput.test.tsx +0 -130
- package/tests/Auth/Social/SocialCallbackComponent.test.tsx +0 -133
- package/tests/Auth/Social/SocialFormComponent.test.tsx +0 -118
- package/tests/FileUpload/FileUpload.test.tsx +0 -42
- package/tests/Notification/EmailTemplate.test.tsx +0 -82
- package/tests/ProductSet/ProductSetPopover.test.tsx +0 -40
- package/tests/Report/Report.test.tsx +0 -48
- package/tests/Sales/Coupon.test.tsx +0 -51
- package/tests/Sales/SalesAndVIews.test.tsx +0 -63
- package/tests/SnippetTemplates/SnippetTemplates.test.tsx +0 -56
- package/tests/Table/FilterHelperComponent.test.tsx +0 -88
- package/tests/Table/PaginationHelperComponent.test.tsx +0 -109
- package/tests/Table/PerPageHelperComponent.test.tsx +0 -34
- package/tests/Table/TableHelperComponent.test.tsx +0 -295
- package/tests/TipTapEditor/TipTapEditor.test.tsx +0 -28
- package/tests/__mock__/hooks/useAuthApi.ts +0 -13
- package/tests/__mock__/hooks/useAuthMock.ts +0 -13
- package/tests/__mock__/hooks/useFormMock.ts +0 -27
- package/tests/__mock__/hooks/useNotificationMock.ts +0 -13
- package/tests/__mock__/hooks/useQueryMock.ts +0 -16
- package/tests/__mock__/hooks/useSocialApiMock.ts +0 -20
- package/tests/__mock__/hooks/useTranslationMock.ts +0 -17
- package/tests/__mock__/hooks/useUserApiMock.ts +0 -18
- package/tests/__mock__/hooks/useUserMock.ts +0 -13
- package/tests/__mock__/styleMock.js +0 -1
- package/tests/__mock__/windowMock.ts +0 -5
- package/tests/packages/react-query.tsx +0 -28
- package/tests/setupTests.ts +0 -10
|
@@ -22,14 +22,10 @@ import { SmsTemplate } from "@licklist/core/dist/DataMapper/Notification/SmsTemp
|
|
|
22
22
|
import HookFormService from "@licklist/plugins/dist/services/Form/HookFormService";
|
|
23
23
|
import { ruleForUrlWithProtocol } from "@licklist/plugins/dist/validation/Rules/urlRule";
|
|
24
24
|
import { WorkHour } from "@licklist/core/dist/DataMapper/Provider/WorkHourDataMapper";
|
|
25
|
+
import { ProductSetRecurrence } from "@licklist/core/dist/DataMapper/Product/ProductSetRecurrenceDataMapper";
|
|
25
26
|
import { WarningMessage } from "../../static";
|
|
26
27
|
import { SelectItem } from "../../types/generic/SelectItem";
|
|
27
|
-
import {
|
|
28
|
-
DateAndRecurrenceInput,
|
|
29
|
-
// TODO: Show Date Component, when reccurent date bugs are fixed
|
|
30
|
-
// DateAndRecurrenceInput,
|
|
31
|
-
DateAndRecurrenceInputValues,
|
|
32
|
-
} from "./DateAndRecurrenceInput";
|
|
28
|
+
import { DateAndRecurrenceInput } from "./DateAndRecurrenceInput";
|
|
33
29
|
import TutorialGifCard from "./TutorialGifCard";
|
|
34
30
|
import { Step } from "../types";
|
|
35
31
|
import { StepsControl } from "../form/StepsControl";
|
|
@@ -53,7 +49,7 @@ export interface TemplateItem {
|
|
|
53
49
|
label: string;
|
|
54
50
|
}
|
|
55
51
|
|
|
56
|
-
export interface ProductSetControlValues
|
|
52
|
+
export interface ProductSetControlValues {
|
|
57
53
|
name: string;
|
|
58
54
|
type: ProductSetType;
|
|
59
55
|
termsAndConditions: string;
|
|
@@ -65,6 +61,7 @@ export interface ProductSetControlValues extends DateAndRecurrenceInputValues {
|
|
|
65
61
|
steps: Step[];
|
|
66
62
|
emailTemplates?: TemplateItem[];
|
|
67
63
|
smsTemplates?: TemplateItem[];
|
|
64
|
+
menuRecurrences?: Partial<ProductSetRecurrence>[];
|
|
68
65
|
}
|
|
69
66
|
|
|
70
67
|
export interface ProductSetControlShared {
|
|
@@ -85,7 +82,7 @@ export interface ProductSetControlProps {
|
|
|
85
82
|
fieldSets?: FieldSet[];
|
|
86
83
|
showEmailTemplate?: boolean;
|
|
87
84
|
showSmsTemplate?: boolean;
|
|
88
|
-
workHours
|
|
85
|
+
workHours: WorkHour[] | undefined;
|
|
89
86
|
providerHasBookingManagement?: boolean;
|
|
90
87
|
isOverrides?: boolean;
|
|
91
88
|
}
|
|
@@ -123,7 +120,7 @@ export function ProductSetControl({
|
|
|
123
120
|
|
|
124
121
|
const showSmsTemplateSelector = showSmsTemplate && !isOverrides;
|
|
125
122
|
const showEmailTemplateSelector = showEmailTemplate && !isOverrides;
|
|
126
|
-
|
|
123
|
+
const showDateSelector = !isEventEditProductSet && isOverrides;
|
|
127
124
|
return (
|
|
128
125
|
<Row
|
|
129
126
|
className={`product-set-form ${
|
|
@@ -165,7 +162,7 @@ export function ProductSetControl({
|
|
|
165
162
|
</Form.Control.Feedback>
|
|
166
163
|
</Form.Group>
|
|
167
164
|
|
|
168
|
-
{
|
|
165
|
+
{showDateSelector ? (
|
|
169
166
|
<DateInput
|
|
170
167
|
workHours={workHours}
|
|
171
168
|
isLoading={isLoading}
|
|
@@ -188,7 +185,11 @@ export function ProductSetControl({
|
|
|
188
185
|
|
|
189
186
|
<TutorialGifCard isOverrides={isOverrides} />
|
|
190
187
|
|
|
191
|
-
<StepsControl
|
|
188
|
+
<StepsControl
|
|
189
|
+
isLoading={isLoading}
|
|
190
|
+
isEventEditProductSet={isEventEditProductSet}
|
|
191
|
+
isOverrides={isOverrides}
|
|
192
|
+
/>
|
|
192
193
|
</Col>
|
|
193
194
|
<Col md={6} sm={12}>
|
|
194
195
|
<div className="second-column">
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { TIME_FORMAT } from "@licklist/core/dist/Config";
|
|
2
|
+
import { dateTimesSortFn } from "@licklist/plugins/dist/utils/dateTime";
|
|
3
|
+
import { extractObjectWithLowestKey } from "@licklist/plugins/dist/utils/extractObjectWithLowestKey";
|
|
4
|
+
import { DateTime } from "luxon";
|
|
5
|
+
import { Product, Step } from "../types";
|
|
6
|
+
|
|
7
|
+
const getProductsFromSteps = (steps: Step[]): Product[] =>
|
|
8
|
+
steps.reduce(
|
|
9
|
+
(acc, step) =>
|
|
10
|
+
acc.concat(
|
|
11
|
+
step.productCategories.reduce(
|
|
12
|
+
(acc, productCategory) => acc.concat(productCategory.products),
|
|
13
|
+
[]
|
|
14
|
+
)
|
|
15
|
+
),
|
|
16
|
+
[]
|
|
17
|
+
);
|
|
18
|
+
|
|
19
|
+
export const getProductWithSmallestDuration = (steps: Step[]): Product =>
|
|
20
|
+
extractObjectWithLowestKey(getProductsFromSteps(steps), "duration");
|
|
21
|
+
|
|
22
|
+
export const getLatestAvailableDateTime = (array: string[]): DateTime =>
|
|
23
|
+
array
|
|
24
|
+
.map((time) => DateTime.fromFormat(time, TIME_FORMAT))
|
|
25
|
+
.sort(dateTimesSortFn("desc"))[0];
|
|
@@ -36,6 +36,7 @@ import { useSortableTreeFunctions } from "../hooks/useSortableTreeFunctions";
|
|
|
36
36
|
interface ProductCategoriesControlProps extends WithIsLoading {
|
|
37
37
|
stepIndex: number;
|
|
38
38
|
isOverrides?: boolean;
|
|
39
|
+
isEventEditProductSet?: boolean;
|
|
39
40
|
}
|
|
40
41
|
|
|
41
42
|
const getCategoryDefaultValue = (
|
|
@@ -67,6 +68,7 @@ export function ProductCategoriesControl({
|
|
|
67
68
|
isLoading,
|
|
68
69
|
stepIndex,
|
|
69
70
|
isOverrides,
|
|
71
|
+
isEventEditProductSet,
|
|
70
72
|
}: ProductCategoriesControlProps) {
|
|
71
73
|
const { t } = useTranslation("Design");
|
|
72
74
|
const {
|
|
@@ -214,6 +216,10 @@ export function ProductCategoriesControl({
|
|
|
214
216
|
? String(productCategory.id)
|
|
215
217
|
: productCategory.uniqueId;
|
|
216
218
|
|
|
219
|
+
const isOverridesCategory = productCategory.products.some((product) =>
|
|
220
|
+
isEventEditProductSet ? !!product.id : !!product.originalProductId
|
|
221
|
+
);
|
|
222
|
+
|
|
217
223
|
const onSetIsExpanded = () => {
|
|
218
224
|
setIsExpanded(productCategoryId);
|
|
219
225
|
};
|
|
@@ -269,7 +275,7 @@ export function ProductCategoriesControl({
|
|
|
269
275
|
categoryName={value}
|
|
270
276
|
stepIndex={stepIndex}
|
|
271
277
|
productCategoryIndex={index}
|
|
272
|
-
isOverride={isOverrides}
|
|
278
|
+
isOverride={isOverrides && isOverridesCategory}
|
|
273
279
|
/>
|
|
274
280
|
}
|
|
275
281
|
isOverride={isOverrides}
|
|
@@ -296,6 +302,7 @@ export function ProductCategoriesControl({
|
|
|
296
302
|
productCategoryIndex={index}
|
|
297
303
|
categoryType={productCategory.type}
|
|
298
304
|
isOverrides={isOverrides}
|
|
305
|
+
isEventEditProductSet={isEventEditProductSet}
|
|
299
306
|
/>
|
|
300
307
|
</SortableTree.Item>
|
|
301
308
|
)}
|
|
@@ -305,9 +312,7 @@ export function ProductCategoriesControl({
|
|
|
305
312
|
</SortableTree>
|
|
306
313
|
<CreateProductSetItem
|
|
307
314
|
title={t("addCategory")}
|
|
308
|
-
isOverride={isOverrides}
|
|
309
315
|
onClick={() => {
|
|
310
|
-
if (isOverrides) return;
|
|
311
316
|
setIsSelectCategoryVisible(true);
|
|
312
317
|
}}
|
|
313
318
|
/>
|
|
@@ -316,7 +321,6 @@ export function ProductCategoriesControl({
|
|
|
316
321
|
isVisible={isSelectCategoryVisible}
|
|
317
322
|
onHide={() => setIsSelectCategoryVisible(false)}
|
|
318
323
|
onCategorySelect={(categoryType) => {
|
|
319
|
-
if (isOverrides) return;
|
|
320
324
|
append(getCategoryDefaultValue(categoryType, fields.length));
|
|
321
325
|
setShowCategoryModal(true);
|
|
322
326
|
if (
|
|
@@ -63,9 +63,9 @@ Default.args = {
|
|
|
63
63
|
sort: 100,
|
|
64
64
|
type: "standard",
|
|
65
65
|
updatedAt: "2023-05-08T15:55:28.000+03:00",
|
|
66
|
+
defaultDuration: 30,
|
|
66
67
|
zoneRecurrences: [
|
|
67
68
|
{
|
|
68
|
-
availableTimes: ["10:05", "10:25", "10:45"],
|
|
69
69
|
endDate: "2022-02-22",
|
|
70
70
|
endTime: "22:00:00",
|
|
71
71
|
id: 1,
|
|
@@ -90,7 +90,6 @@ Default.args = {
|
|
|
90
90
|
updatedAt: "2023-05-08T15:55:28.000+03:00",
|
|
91
91
|
zoneRecurrences: [
|
|
92
92
|
{
|
|
93
|
-
availableTimes: ["10:05", "10:25", "10:45"],
|
|
94
93
|
endDate: "2022-02-22",
|
|
95
94
|
endTime: "22:00:00",
|
|
96
95
|
id: 1,
|
|
@@ -26,12 +26,16 @@ import { checkAvailableTimesErrors, getFilteredTemplates } from "../utils";
|
|
|
26
26
|
export interface WithIsLoading {
|
|
27
27
|
isLoading: boolean;
|
|
28
28
|
}
|
|
29
|
+
export interface WithIdOptional {
|
|
30
|
+
id?: number;
|
|
31
|
+
}
|
|
32
|
+
|
|
29
33
|
export interface WithId {
|
|
30
34
|
id: number;
|
|
31
35
|
}
|
|
32
36
|
export interface ProductSetFormValues
|
|
33
37
|
extends FormValues,
|
|
34
|
-
|
|
38
|
+
WithIdOptional,
|
|
35
39
|
ProductSetControlValues {
|
|
36
40
|
steps: Step[];
|
|
37
41
|
isOverrides?: boolean;
|
|
@@ -35,6 +35,7 @@ interface ProductsControlProps extends WithIsLoading {
|
|
|
35
35
|
categoryType: CategoryType;
|
|
36
36
|
zones?: Zone[];
|
|
37
37
|
isOverrides?: boolean;
|
|
38
|
+
isEventEditProductSet?: boolean;
|
|
38
39
|
}
|
|
39
40
|
|
|
40
41
|
const getDefaultProductValue = (sort: number): Product => ({
|
|
@@ -57,6 +58,7 @@ const getDefaultProductValue = (sort: number): Product => ({
|
|
|
57
58
|
quantitySelector: 1,
|
|
58
59
|
hasSpecialNotes: false,
|
|
59
60
|
weight: 0,
|
|
61
|
+
originalProductId: null,
|
|
60
62
|
type: DEFAULT_PRODUCT_TYPE,
|
|
61
63
|
tierId: Number(uniqueId()),
|
|
62
64
|
zoneId: null,
|
|
@@ -79,6 +81,7 @@ export function ProductsControl({
|
|
|
79
81
|
categoryType,
|
|
80
82
|
zones,
|
|
81
83
|
isOverrides,
|
|
84
|
+
isEventEditProductSet,
|
|
82
85
|
}: ProductsControlProps) {
|
|
83
86
|
const { t } = useTranslation("Design");
|
|
84
87
|
const form = useFormContext<ProductSetFormValues>();
|
|
@@ -203,90 +206,97 @@ export function ProductsControl({
|
|
|
203
206
|
onDragEnd={handleDragEnd}
|
|
204
207
|
sensors={[mouseSensor]}
|
|
205
208
|
>
|
|
206
|
-
{fields.map((product, index) =>
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
}
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
}`
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
209
|
+
{fields.map((product, index) => {
|
|
210
|
+
const isOverridesProductSet = isEventEditProductSet
|
|
211
|
+
? !!product.id
|
|
212
|
+
: isOverrides && !!product.originalProductId;
|
|
213
|
+
|
|
214
|
+
return (
|
|
215
|
+
<Controller
|
|
216
|
+
key={product._id}
|
|
217
|
+
control={control}
|
|
218
|
+
name={`${productControlFieldName}.${index}.name` as const}
|
|
219
|
+
rules={{
|
|
220
|
+
required: t("Validation:fieldRequired", {
|
|
221
|
+
attribute: t("name"),
|
|
222
|
+
}) as string,
|
|
223
|
+
}}
|
|
224
|
+
render={({ field: { value, onChange } }) => (
|
|
225
|
+
<SortableTree.Item
|
|
226
|
+
key={`product-${product._id}`}
|
|
227
|
+
id={String(product._id)}
|
|
228
|
+
isExpanded={isFirstProductAdded}
|
|
229
|
+
isInvalid={!!categoryProductErrors}
|
|
230
|
+
title={value}
|
|
231
|
+
isOverride={isOverrides}
|
|
232
|
+
badge={
|
|
233
|
+
<Badge className="product-badge">{t("product")}</Badge>
|
|
234
|
+
}
|
|
235
|
+
isIconInHeader={false}
|
|
236
|
+
cancelChanges={() => cancelChanges(index)}
|
|
237
|
+
edit={() => edit(index)}
|
|
238
|
+
secondaryBadge={getBadgeConfig(categoryType, t(categoryType))}
|
|
239
|
+
subTitle={
|
|
240
|
+
<div className="product-set-badges-container">
|
|
241
|
+
<div className="product-set-subtitle-dot product-set-subtitle-product-dot" />
|
|
242
|
+
<span>
|
|
243
|
+
{`£${prices[index]} ${t("each")} - ${t("qty")}:${
|
|
244
|
+
!isUnlimitedQuantities[index]
|
|
245
|
+
? ` ${quantities[index]}`
|
|
246
|
+
: t(" unlimited")
|
|
247
|
+
} ${
|
|
248
|
+
!isUnlimitedQuantities[index]
|
|
249
|
+
? ` - ${t("possibleRevenue")} £${
|
|
250
|
+
prices[index] * quantities[index]
|
|
251
|
+
}`
|
|
252
|
+
: ""
|
|
253
|
+
} `}
|
|
254
|
+
</span>
|
|
255
|
+
</div>
|
|
256
|
+
}
|
|
257
|
+
modalLabel={t("addNewProduct")}
|
|
258
|
+
modalClass={ProductSetModalClasses.product}
|
|
259
|
+
isNewAdded={showProductModal}
|
|
260
|
+
body={
|
|
261
|
+
<ProductControl<ProductSetFormValues>
|
|
262
|
+
isLoading={isLoading}
|
|
263
|
+
quantityType={quantityType}
|
|
264
|
+
allowDeposits={allowDeposits}
|
|
265
|
+
hasBookingManagement={false}
|
|
266
|
+
fieldNamePrefix={
|
|
267
|
+
`${productControlFieldName}.${index}` as const
|
|
268
|
+
}
|
|
269
|
+
productName={value}
|
|
270
|
+
onProductNameChange={onChange}
|
|
271
|
+
hasTicket={hasTicket}
|
|
272
|
+
categoryType={categoryType}
|
|
273
|
+
zoneDuration={catergoryZone?.defaultDuration}
|
|
274
|
+
isOverrides={isOverridesProductSet}
|
|
275
|
+
/>
|
|
276
|
+
}
|
|
277
|
+
onDelete={() => onProductRemove(index)}
|
|
278
|
+
validate={() =>
|
|
279
|
+
trigger(`${productControlFieldName}.${index}`)
|
|
280
|
+
}
|
|
281
|
+
saveValidField={saveValidField}
|
|
282
|
+
// preItem={<Popover className="d-none d-sm-block" />}
|
|
283
|
+
>
|
|
284
|
+
<SubProductsControl
|
|
253
285
|
isLoading={isLoading}
|
|
254
286
|
quantityType={quantityType}
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
`${productControlFieldName}.${index}` as const
|
|
259
|
-
}
|
|
260
|
-
productName={value}
|
|
261
|
-
onProductNameChange={onChange}
|
|
262
|
-
hasTicket={hasTicket}
|
|
263
|
-
categoryType={categoryType}
|
|
264
|
-
zoneDuration={catergoryZone?.defaultDuration}
|
|
265
|
-
isOverrides={isOverrides}
|
|
287
|
+
stepIndex={stepIndex}
|
|
288
|
+
productCategoryIndex={productCategoryIndex}
|
|
289
|
+
productIndex={index}
|
|
266
290
|
/>
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
>
|
|
273
|
-
<SubProductsControl
|
|
274
|
-
isLoading={isLoading}
|
|
275
|
-
quantityType={quantityType}
|
|
276
|
-
stepIndex={stepIndex}
|
|
277
|
-
productCategoryIndex={productCategoryIndex}
|
|
278
|
-
productIndex={index}
|
|
279
|
-
/>
|
|
280
|
-
</SortableTree.Item>
|
|
281
|
-
)}
|
|
282
|
-
/>
|
|
283
|
-
))}
|
|
291
|
+
</SortableTree.Item>
|
|
292
|
+
)}
|
|
293
|
+
/>
|
|
294
|
+
);
|
|
295
|
+
})}
|
|
284
296
|
</SortableTree>
|
|
285
297
|
<CreateProductSetItem
|
|
286
298
|
title={t("addProduct")}
|
|
287
|
-
isOverride={isOverrides}
|
|
288
299
|
onClick={() => {
|
|
289
|
-
if (isOverrides) return;
|
|
290
300
|
append(getDefaultProductValue(fields.length));
|
|
291
301
|
setShowProductModal(true);
|
|
292
302
|
|
|
@@ -19,9 +19,14 @@ import { ProductSetFormValues } from "./ProductSetForm";
|
|
|
19
19
|
interface StepsControlProps {
|
|
20
20
|
isLoading: boolean;
|
|
21
21
|
isOverrides?: boolean;
|
|
22
|
+
isEventEditProductSet?: boolean;
|
|
22
23
|
}
|
|
23
24
|
|
|
24
|
-
export function StepsControl({
|
|
25
|
+
export function StepsControl({
|
|
26
|
+
isLoading,
|
|
27
|
+
isOverrides,
|
|
28
|
+
isEventEditProductSet,
|
|
29
|
+
}: StepsControlProps) {
|
|
25
30
|
const form = useFormContext<ProductSetFormValues>();
|
|
26
31
|
const { t } = useTranslation("Design");
|
|
27
32
|
const [showStepModal, setShowStepModal] = useState(false);
|
|
@@ -68,8 +73,8 @@ export function StepsControl({ isLoading, isOverrides }: StepsControlProps) {
|
|
|
68
73
|
<>
|
|
69
74
|
{fields.map((step, index) => {
|
|
70
75
|
const stepFieldName = `steps.${index}` as const;
|
|
71
|
-
|
|
72
76
|
const stepData = getValues(stepFieldName);
|
|
77
|
+
const isOverrideStep = !!step.id;
|
|
73
78
|
|
|
74
79
|
return (
|
|
75
80
|
<Controller
|
|
@@ -92,9 +97,9 @@ export function StepsControl({ isLoading, isOverrides }: StepsControlProps) {
|
|
|
92
97
|
modalLabel={t("addNewStep")}
|
|
93
98
|
modalClass={ProductSetModalClasses.step}
|
|
94
99
|
isNewAdded={showStepModal}
|
|
95
|
-
edit={() =>
|
|
100
|
+
edit={() => edit(index)}
|
|
96
101
|
cancelChanges={() => cancelChanges(index)}
|
|
97
|
-
isOverride={
|
|
102
|
+
isOverride={isOverrideStep}
|
|
98
103
|
subTitle={
|
|
99
104
|
<div className="product-set-badges-container">
|
|
100
105
|
<div className="product-set-subtitle-dot product-set-subtitle-step-dot" />
|
|
@@ -110,6 +115,7 @@ export function StepsControl({ isLoading, isOverrides }: StepsControlProps) {
|
|
|
110
115
|
stepIndex={index}
|
|
111
116
|
stepName={value}
|
|
112
117
|
onStepNameChange={onChange}
|
|
118
|
+
isOverrides={isOverrideStep}
|
|
113
119
|
/>
|
|
114
120
|
}
|
|
115
121
|
onDelete={() => remove(index)}
|
|
@@ -140,6 +146,7 @@ export function StepsControl({ isLoading, isOverrides }: StepsControlProps) {
|
|
|
140
146
|
isLoading={isLoading}
|
|
141
147
|
stepIndex={index}
|
|
142
148
|
isOverrides={isOverrides}
|
|
149
|
+
isEventEditProductSet={isEventEditProductSet}
|
|
143
150
|
/>
|
|
144
151
|
</SortableTree.Item>
|
|
145
152
|
)}
|
|
@@ -149,9 +156,7 @@ export function StepsControl({ isLoading, isOverrides }: StepsControlProps) {
|
|
|
149
156
|
|
|
150
157
|
<CreateProductSetItem
|
|
151
158
|
title={t("addStep")}
|
|
152
|
-
isOverride={isOverrides}
|
|
153
159
|
onClick={() => {
|
|
154
|
-
if (isOverrides) return;
|
|
155
160
|
append(getDefaultStepsValues());
|
|
156
161
|
setShowStepModal(true);
|
|
157
162
|
if (errors.steps?.type === HookFormService.manualErrorType) {
|
|
@@ -24,8 +24,10 @@ export const useSortableTreeFunctions = ({
|
|
|
24
24
|
const cancelChanges = (index: number) => {
|
|
25
25
|
if (isOverrides) return;
|
|
26
26
|
if (!previousValue) {
|
|
27
|
+
// eslint-disable-next-line consistent-return
|
|
27
28
|
return remove(index);
|
|
28
29
|
}
|
|
30
|
+
// eslint-disable-next-line consistent-return
|
|
29
31
|
return setValue(`${fieldName}.${index}` as const, previousValue);
|
|
30
32
|
};
|
|
31
33
|
|
|
@@ -7,14 +7,17 @@ import {
|
|
|
7
7
|
QUANTITY_TYPE_LIST_DTO,
|
|
8
8
|
QUANTITY_TYPE_RECHARGING,
|
|
9
9
|
} from "@licklist/core/dist/DataMapper/Product/ProductCategoryDataMapper";
|
|
10
|
-
import {
|
|
10
|
+
import {
|
|
11
|
+
ProductType,
|
|
12
|
+
PRODUCT_DEfAULT_COLORS,
|
|
13
|
+
} from "@licklist/core/dist/DataMapper/Product/ProductDataMapper";
|
|
11
14
|
import HookFormService from "@licklist/plugins/dist/services/Form/HookFormService";
|
|
15
|
+
import clsx from "clsx";
|
|
12
16
|
import {
|
|
13
17
|
FieldNamePrefixPath,
|
|
14
18
|
FormValues,
|
|
15
19
|
} from "@licklist/plugins/dist/types/services/Form/hook-form-service";
|
|
16
20
|
import { useId } from "@react-aria/utils";
|
|
17
|
-
import clsx from "clsx";
|
|
18
21
|
import React, {
|
|
19
22
|
ChangeEvent,
|
|
20
23
|
useCallback,
|
|
@@ -36,7 +39,7 @@ import {
|
|
|
36
39
|
} from "react-hook-form";
|
|
37
40
|
import { useTranslation } from "react-i18next";
|
|
38
41
|
import { useImages } from "@licklist/plugins/dist/hooks/Media/useImages";
|
|
39
|
-
|
|
42
|
+
|
|
40
43
|
import {
|
|
41
44
|
Image,
|
|
42
45
|
IMAGE_TYPE_IMAGE,
|
|
@@ -86,6 +89,7 @@ export interface ProductControlValues
|
|
|
86
89
|
totalQuantity: number;
|
|
87
90
|
isAvailable: boolean;
|
|
88
91
|
isSoldOut: boolean;
|
|
92
|
+
originalProductId: number | null;
|
|
89
93
|
isUnlimited: boolean;
|
|
90
94
|
isRequired: boolean;
|
|
91
95
|
quantitySelector: number;
|
|
@@ -146,7 +150,7 @@ export function ProductControl<T extends FormValues>({
|
|
|
146
150
|
clearErrors,
|
|
147
151
|
} = useFormContext<T>();
|
|
148
152
|
|
|
149
|
-
const { setLoading } = useContext(ProductSetLoadingContext);
|
|
153
|
+
const { setLoading, productGroupList } = useContext(ProductSetLoadingContext);
|
|
150
154
|
const { t } = useTranslation(["Design", "Validation", "ProductSet"]);
|
|
151
155
|
const [expanded, setExpanded] = useState(false);
|
|
152
156
|
const [initialImages, setInitialImages] = useState<Image[] | null>(null);
|
|
@@ -156,11 +160,10 @@ export function ProductControl<T extends FormValues>({
|
|
|
156
160
|
);
|
|
157
161
|
const capacity = watch(`${fieldNamePrefix}.capacity` as Path<T>);
|
|
158
162
|
const disabledDuration = capacity === "0" || !capacity;
|
|
159
|
-
|
|
160
163
|
const advancedId = useId();
|
|
161
164
|
const nameId = useId();
|
|
162
|
-
|
|
163
|
-
|
|
165
|
+
|
|
166
|
+
const productGroupId = useId();
|
|
164
167
|
const descriptionId = useId();
|
|
165
168
|
const termsAndConditionsId = useId();
|
|
166
169
|
const isAvailableId = useId();
|
|
@@ -400,6 +403,35 @@ export function ProductControl<T extends FormValues>({
|
|
|
400
403
|
isRequired={false}
|
|
401
404
|
defaultColors={PRODUCT_DEfAULT_COLORS}
|
|
402
405
|
/>
|
|
406
|
+
|
|
407
|
+
<Form.Group controlId={productGroupId}>
|
|
408
|
+
<Form.Label>{t("productGroup")}</Form.Label>
|
|
409
|
+
<Form.Control
|
|
410
|
+
as="select"
|
|
411
|
+
{...register(`${fieldNamePrefix}.productGroupId` as Path<T>)}
|
|
412
|
+
isInvalid={HookFormService.isInvalid<T>(
|
|
413
|
+
`${fieldNamePrefix}.productGroupId` as Path<T>,
|
|
414
|
+
errors
|
|
415
|
+
)}
|
|
416
|
+
disabled={isLoading || isOverrides}
|
|
417
|
+
defaultValue=""
|
|
418
|
+
>
|
|
419
|
+
<option value="">{t("Design:selectProductGroup")}</option>
|
|
420
|
+
{productGroupList.map((productGroup) => {
|
|
421
|
+
return (
|
|
422
|
+
<option value={productGroup.id} key={productGroup.id}>
|
|
423
|
+
{productGroup.value}
|
|
424
|
+
</option>
|
|
425
|
+
);
|
|
426
|
+
})}
|
|
427
|
+
</Form.Control>
|
|
428
|
+
<Form.Control.Feedback type="invalid">
|
|
429
|
+
{HookFormService.getErrors<T>(
|
|
430
|
+
`${fieldNamePrefix}.productGroupId` as Path<T>,
|
|
431
|
+
errors
|
|
432
|
+
)}
|
|
433
|
+
</Form.Control.Feedback>
|
|
434
|
+
</Form.Group>
|
|
403
435
|
</Col>
|
|
404
436
|
</Row>
|
|
405
437
|
|
|
@@ -672,38 +704,6 @@ export function ProductControl<T extends FormValues>({
|
|
|
672
704
|
</Collapse>
|
|
673
705
|
|
|
674
706
|
<Row>
|
|
675
|
-
{/* @TODO: no need for v1 release
|
|
676
|
-
<Col xs={12} sm={6}>
|
|
677
|
-
<Form.Group controlId={productGroupId}>
|
|
678
|
-
<Form.Label>{t("productGroup")}</Form.Label>
|
|
679
|
-
<Form.Control
|
|
680
|
-
as="select"
|
|
681
|
-
{...register(`${fieldNamePrefix}.productGroupId` as Path<T>)}
|
|
682
|
-
isInvalid={HookFormService.isInvalid<T>(
|
|
683
|
-
`${fieldNamePrefix}.productGroupId` as Path<T>,
|
|
684
|
-
errors
|
|
685
|
-
)}
|
|
686
|
-
disabled={isLoading}
|
|
687
|
-
defaultValue=""
|
|
688
|
-
>
|
|
689
|
-
<option value="">{t("Design:selectProductGroup")}</option>
|
|
690
|
-
{productGroupList.map((productGroup) => {
|
|
691
|
-
return (
|
|
692
|
-
<option value={productGroup.id} key={productGroup.id}>
|
|
693
|
-
{productGroup.value}
|
|
694
|
-
</option>
|
|
695
|
-
);
|
|
696
|
-
})}
|
|
697
|
-
</Form.Control>
|
|
698
|
-
<Form.Control.Feedback type="invalid">
|
|
699
|
-
{HookFormService.getErrors<T>(
|
|
700
|
-
`${fieldNamePrefix}.productGroupId` as Path<T>,
|
|
701
|
-
errors
|
|
702
|
-
)}
|
|
703
|
-
</Form.Control.Feedback>
|
|
704
|
-
</Form.Group>
|
|
705
|
-
</Col> */}
|
|
706
|
-
|
|
707
707
|
<Col xs={12}>
|
|
708
708
|
{hasBookingManagement && (
|
|
709
709
|
<ProductBookingManagementControl<T>
|
|
@@ -5,8 +5,6 @@ import { FieldNamePrefixPath } from "@licklist/plugins/dist/types/services/Form/
|
|
|
5
5
|
import { useWatch } from "react-hook-form";
|
|
6
6
|
import { FormNumberInput } from "../../../static";
|
|
7
7
|
|
|
8
|
-
|
|
9
|
-
|
|
10
8
|
interface FixedDurationOptionsProps<T> extends FieldNamePrefixPath<T> {
|
|
11
9
|
isOverrides?: boolean;
|
|
12
10
|
}
|
|
@@ -26,6 +26,7 @@ export interface StepControlProps extends IsDeletableEvent {
|
|
|
26
26
|
stepIndex: number;
|
|
27
27
|
stepName: string;
|
|
28
28
|
onStepNameChange: (args: any) => void;
|
|
29
|
+
isOverrides?: boolean;
|
|
29
30
|
}
|
|
30
31
|
|
|
31
32
|
export function StepControl({
|
|
@@ -33,6 +34,7 @@ export function StepControl({
|
|
|
33
34
|
stepIndex,
|
|
34
35
|
stepName,
|
|
35
36
|
onStepNameChange,
|
|
37
|
+
isOverrides = false,
|
|
36
38
|
}: StepControlProps) {
|
|
37
39
|
const { providerHasMap } = useContext(ProductSetLoadingContext);
|
|
38
40
|
const {
|
|
@@ -42,7 +44,6 @@ export function StepControl({
|
|
|
42
44
|
watch,
|
|
43
45
|
} = useFormContext<ProductSetFormValues>();
|
|
44
46
|
const { t } = useTranslation("Design");
|
|
45
|
-
|
|
46
47
|
const fieldName = `steps.${stepIndex}.name` as const;
|
|
47
48
|
const productCategoriesFieldName =
|
|
48
49
|
`steps.${stepIndex}.productCategories` as const;
|
|
@@ -71,7 +72,7 @@ export function StepControl({
|
|
|
71
72
|
fieldName,
|
|
72
73
|
errors
|
|
73
74
|
)}
|
|
74
|
-
disabled={isLoading}
|
|
75
|
+
disabled={isLoading || isOverrides}
|
|
75
76
|
/>
|
|
76
77
|
)}
|
|
77
78
|
control={control}
|
|
@@ -114,7 +115,7 @@ export function StepControl({
|
|
|
114
115
|
name={name}
|
|
115
116
|
value={Boolean(value)}
|
|
116
117
|
onChange={onChange}
|
|
117
|
-
disabled={isLoading}
|
|
118
|
+
disabled={isLoading || isOverrides}
|
|
118
119
|
/>
|
|
119
120
|
)}
|
|
120
121
|
control={control}
|