@akinon/projectzero 2.0.0-beta.20 → 2.0.0-beta.22

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 (140) hide show
  1. package/CHANGELOG.md +14 -0
  2. package/app-template/CHANGELOG.md +170 -0
  3. package/app-template/next.config.mjs +0 -1
  4. package/app-template/package.json +31 -30
  5. package/app-template/src/app/[pz]/[...prettyurl]/page.tsx +2 -2
  6. package/app-template/src/app/[pz]/account/layout.tsx +2 -1
  7. package/app-template/src/app/{[commerce]/[locale]/[currency] → [pz]}/blog/[slug]/page.tsx +4 -2
  8. package/app-template/src/app/[pz]/category/[pk]/page.tsx +11 -1
  9. package/app-template/src/app/[pz]/group-product/[pk]/page.tsx +2 -2
  10. package/app-template/src/app/[pz]/layout.tsx +3 -1
  11. package/app-template/src/app/[pz]/list/page.tsx +11 -1
  12. package/app-template/src/app/[pz]/page.tsx +13 -35
  13. package/app-template/src/app/[pz]/pages/[slug]/page.tsx +19 -0
  14. package/app-template/src/app/[pz]/product/[pk]/page.tsx +2 -2
  15. package/app-template/src/app/api/barcode-search/route.ts +1 -1
  16. package/app-template/src/app/api/cache/route.ts +1 -1
  17. package/app-template/src/app/api/image-proxy/route.ts +1 -1
  18. package/app-template/src/app/api/logout/route.ts +1 -1
  19. package/app-template/src/app/api/product-categories/route.ts +1 -1
  20. package/app-template/src/app/api/similar-product-list/route.ts +1 -1
  21. package/app-template/src/app/api/similar-products/route.ts +1 -1
  22. package/app-template/src/app/api/virtual-try-on/route.ts +1 -1
  23. package/app-template/src/app/api/web-vitals/route.ts +1 -1
  24. package/app-template/src/components/quantity-selector.tsx +16 -4
  25. package/app-template/src/components/widget-content.tsx +3 -3
  26. package/app-template/src/routes/index.ts +6 -6
  27. package/app-template/src/utils/__tests__/theme-page-context.test.ts +145 -0
  28. package/app-template/src/utils/theme-page-context.ts +309 -0
  29. package/app-template/src/views/basket/basket-item.tsx +107 -691
  30. package/app-template/src/views/basket/index.ts +0 -2
  31. package/app-template/src/views/basket/summary.tsx +75 -496
  32. package/app-template/src/views/breadcrumb.tsx +38 -13
  33. package/app-template/src/views/category/category-header.tsx +66 -289
  34. package/app-template/src/views/category/category-info.tsx +24 -173
  35. package/app-template/src/views/category/filters/index.tsx +48 -208
  36. package/app-template/src/views/category/layout.tsx +5 -7
  37. package/app-template/src/views/checkout/index.tsx +0 -5
  38. package/app-template/src/views/checkout/steps/payment/index.tsx +2 -5
  39. package/app-template/src/views/checkout/steps/payment/options/credit-card/index.tsx +1 -72
  40. package/app-template/src/views/checkout/steps/payment/payment-option-buttons.tsx +40 -171
  41. package/app-template/src/views/checkout/steps/shipping/address-box.tsx +12 -74
  42. package/app-template/src/views/checkout/steps/shipping/addresses.tsx +45 -128
  43. package/app-template/src/views/checkout/steps/shipping/shipping-options.tsx +27 -232
  44. package/app-template/src/views/checkout/summary.tsx +29 -303
  45. package/app-template/src/views/footer.tsx +13 -415
  46. package/app-template/src/views/guest-login/index.tsx +1 -1
  47. package/app-template/src/views/header/action-menu.tsx +45 -277
  48. package/app-template/src/views/header/band.tsx +21 -6
  49. package/app-template/src/views/header/index.tsx +47 -109
  50. package/app-template/src/views/header/mini-basket.tsx +45 -820
  51. package/app-template/src/views/header/navbar.tsx +111 -178
  52. package/app-template/src/views/header/search/index.tsx +32 -71
  53. package/app-template/src/views/header/search/results.tsx +65 -127
  54. package/app-template/src/views/product/accordion-wrapper.tsx +43 -135
  55. package/app-template/src/views/product/index.ts +1 -1
  56. package/app-template/src/views/product/layout.tsx +7 -2
  57. package/app-template/src/views/product/misc-buttons.tsx +25 -339
  58. package/app-template/src/views/product/product-actions.tsx +8 -137
  59. package/app-template/src/views/product/product-info.tsx +31 -69
  60. package/app-template/src/views/product/product-share.tsx +8 -11
  61. package/app-template/src/views/product/slider.tsx +79 -117
  62. package/app-template/src/views/product-item/index.tsx +46 -119
  63. package/app-template/src/widgets/footer-social.tsx +16 -47
  64. package/app-template/src/widgets/footer-subscription/index.tsx +17 -183
  65. package/codemods/migrate-auth-v5/index.js +339 -0
  66. package/codemods/migrate-auth-v5/transform.js +86 -0
  67. package/dist/commands/plugins.js +23 -2
  68. package/package.json +1 -1
  69. package/app-template/src/app/[commerce]/[locale]/[currency]/pages/[slug]/page.tsx +0 -15
  70. package/app-template/src/views/basket/basket-summary-context.tsx +0 -560
  71. package/app-template/src/views/basket/designer-context.tsx +0 -617
  72. package/app-template/src/views/breadcrumb/breadcrumb-client.tsx +0 -190
  73. package/app-template/src/views/breadcrumb/breadcrumb-registrar.tsx +0 -286
  74. package/app-template/src/views/breadcrumb/constants.ts +0 -15
  75. package/app-template/src/views/breadcrumb/index.tsx +0 -127
  76. package/app-template/src/views/category/native-widget-context.tsx +0 -257
  77. package/app-template/src/views/category/product-list-registrar.tsx +0 -665
  78. package/app-template/src/views/checkout/checkout-address-registrar.tsx +0 -254
  79. package/app-template/src/views/checkout/checkout-buttons-registrar.tsx +0 -183
  80. package/app-template/src/views/checkout/checkout-delivery-method-registrar.tsx +0 -259
  81. package/app-template/src/views/checkout/checkout-payment-options-registrar.tsx +0 -253
  82. package/app-template/src/views/checkout/checkout-summary-registrar.tsx +0 -183
  83. package/app-template/src/views/checkout/constants.ts +0 -5
  84. package/app-template/src/views/checkout/steps/payment/options/masterpass-rest.tsx +0 -15
  85. package/app-template/src/views/checkout/steps/payment/options/saved-card.tsx +0 -18
  86. package/app-template/src/views/footer/footer-app-banner-context.tsx +0 -326
  87. package/app-template/src/views/footer/footer-bottom-context.tsx +0 -215
  88. package/app-template/src/views/footer/footer-bottom-wrapper.tsx +0 -74
  89. package/app-template/src/views/footer/footer-layout-constants.ts +0 -35
  90. package/app-template/src/views/footer/footer-layout-registrar.tsx +0 -342
  91. package/app-template/src/views/footer/footer-layout-switcher.tsx +0 -110
  92. package/app-template/src/views/footer/footer-menu-context.tsx +0 -211
  93. package/app-template/src/views/footer/footer-native-widgets.tsx +0 -60
  94. package/app-template/src/views/footer/footer-social-context.tsx +0 -254
  95. package/app-template/src/views/footer/footer-subscription-context.tsx +0 -210
  96. package/app-template/src/views/footer/footer-utils.ts +0 -43
  97. package/app-template/src/views/footer/footer-value-props-context.tsx +0 -326
  98. package/app-template/src/views/footer/logo-settings.ts +0 -183
  99. package/app-template/src/views/footer/native-widget-config.ts +0 -262
  100. package/app-template/src/views/footer/subscription-settings.ts +0 -122
  101. package/app-template/src/views/footer/use-footer-logo.ts +0 -162
  102. package/app-template/src/views/header/designer-context.tsx +0 -261
  103. package/app-template/src/views/header/header-announcement-registrar.tsx +0 -267
  104. package/app-template/src/views/header/header-client-wrapper.tsx +0 -496
  105. package/app-template/src/views/header/header-content.tsx +0 -1026
  106. package/app-template/src/views/header/header-currency-registrar.tsx +0 -348
  107. package/app-template/src/views/header/header-icons-context.tsx +0 -262
  108. package/app-template/src/views/header/header-language-registrar.tsx +0 -348
  109. package/app-template/src/views/header/header-layout-context.tsx +0 -143
  110. package/app-template/src/views/header/header-layout-registrar.tsx +0 -658
  111. package/app-template/src/views/header/header-logo-context.tsx +0 -228
  112. package/app-template/src/views/header/header-logo.tsx +0 -118
  113. package/app-template/src/views/header/header-mini-basket-context.tsx +0 -524
  114. package/app-template/src/views/header/header-search-registrar.tsx +0 -511
  115. package/app-template/src/views/header/header-text-slider-registrar.tsx +0 -382
  116. package/app-template/src/views/header/inline-search.tsx +0 -262
  117. package/app-template/src/views/header/navbar-menu-context.tsx +0 -219
  118. package/app-template/src/views/header/search/search-input.tsx +0 -61
  119. package/app-template/src/views/header/server-settings-parser.ts +0 -1105
  120. package/app-template/src/views/header/use-header-icons.ts +0 -241
  121. package/app-template/src/views/header/use-header-logo.ts +0 -213
  122. package/app-template/src/views/header/use-navbar-menu.ts +0 -179
  123. package/app-template/src/views/product/accordion-section.tsx +0 -61
  124. package/app-template/src/views/product/custom-button-group.tsx +0 -69
  125. package/app-template/src/views/product/favorites-button-section.tsx +0 -69
  126. package/app-template/src/views/product/find-in-store-section.tsx +0 -60
  127. package/app-template/src/views/product/product-info-section.tsx +0 -140
  128. package/app-template/src/views/product/quantity-section.tsx +0 -73
  129. package/app-template/src/views/product/sale-tag.tsx +0 -10
  130. package/app-template/src/views/product/share-section.tsx +0 -357
  131. package/app-template/src/views/product/variants-section.tsx +0 -126
  132. package/app-template/src/views/product-detail/constants.ts +0 -272
  133. package/app-template/src/views/product-detail/index.ts +0 -10
  134. package/app-template/src/views/product-detail/product-detail-registrar.tsx +0 -616
  135. package/app-template/src/widgets/footer-app-banner.tsx +0 -444
  136. package/app-template/src/widgets/footer-bottom.tsx +0 -127
  137. package/app-template/src/widgets/footer-menu-compact.tsx +0 -238
  138. package/app-template/src/widgets/footer-menu-two.tsx +0 -298
  139. package/app-template/src/widgets/footer-social-client.tsx +0 -251
  140. package/app-template/src/widgets/footer-value-props.tsx +0 -201
@@ -18,7 +18,6 @@ import { useLocalization } from '@akinon/next/hooks';
18
18
  import { Image } from '@akinon/next/components/image';
19
19
  import { getPosError, checkPaymentWillRedirect } from '@akinon/next/utils';
20
20
  import PluginModule, { Component } from '@akinon/next/components/plugin-module';
21
- import { useCheckoutButtons } from '@theme/views/checkout/checkout-buttons-registrar';
22
21
  import { PaymentOption } from '@akinon/next/types';
23
22
 
24
23
  const creditCardFormSchema = (
@@ -96,19 +95,6 @@ const CheckoutCreditCard = () => {
96
95
  const { cardType } = useAppSelector((state: RootState) => state.checkout);
97
96
  const masterpass = useAppSelector((state: RootState) => state.masterpass);
98
97
  const { t } = useLocalization();
99
- const { sectionStyles: buttonStyles } = useCheckoutButtons();
100
-
101
- // Helper to get button style value
102
- const getButtonStyle = (
103
- key: string,
104
- fallback: string | number = ''
105
- ): string | number => {
106
- const value = buttonStyles[key];
107
- if (value === undefined || value === null || value === '') {
108
- return fallback;
109
- }
110
- return value;
111
- };
112
98
  const {
113
99
  register,
114
100
  handleSubmit,
@@ -419,64 +405,7 @@ const CheckoutCreditCard = () => {
419
405
  </div>
420
406
  )}
421
407
  <Button
422
- className="group mt-4 inline-flex items-center justify-center"
423
- style={{
424
- width: getButtonStyle('button-width', 'auto') as string,
425
- backgroundColor: getButtonStyle(
426
- 'primary-background-color',
427
- '#000000'
428
- ) as string,
429
- color: getButtonStyle(
430
- 'primary-text-color',
431
- '#ffffff'
432
- ) as string,
433
- borderWidth: getButtonStyle('primary-border-width', 0),
434
- borderStyle: 'solid',
435
- borderColor: getButtonStyle(
436
- 'primary-border-color',
437
- '#000000'
438
- ) as string,
439
- borderRadius: getButtonStyle('primary-border-radius', 4),
440
- paddingLeft: getButtonStyle('primary-padding-x', 24),
441
- paddingRight: getButtonStyle('primary-padding-x', 24),
442
- paddingTop: getButtonStyle('primary-padding-y', 12),
443
- paddingBottom: getButtonStyle('primary-padding-y', 12),
444
- fontSize: getButtonStyle('primary-font-size', 14),
445
- fontWeight: getButtonStyle('primary-font-weight', '500'),
446
- textTransform: getButtonStyle(
447
- 'primary-text-transform',
448
- 'uppercase'
449
- ) as any,
450
- transition: 'all 0.2s ease'
451
- }}
452
- onMouseEnter={(e) => {
453
- e.currentTarget.style.backgroundColor = getButtonStyle(
454
- 'primary-hover-background-color',
455
- '#1a1a1a'
456
- ) as string;
457
- e.currentTarget.style.color = getButtonStyle(
458
- 'primary-hover-text-color',
459
- '#ffffff'
460
- ) as string;
461
- e.currentTarget.style.borderColor = getButtonStyle(
462
- 'primary-hover-border-color',
463
- '#1a1a1a'
464
- ) as string;
465
- }}
466
- onMouseLeave={(e) => {
467
- e.currentTarget.style.backgroundColor = getButtonStyle(
468
- 'primary-background-color',
469
- '#000000'
470
- ) as string;
471
- e.currentTarget.style.color = getButtonStyle(
472
- 'primary-text-color',
473
- '#ffffff'
474
- ) as string;
475
- e.currentTarget.style.borderColor = getButtonStyle(
476
- 'primary-border-color',
477
- '#000000'
478
- ) as string;
479
- }}
408
+ className="group uppercase mt-4 inline-flex items-center justify-center"
480
409
  type="submit"
481
410
  disabled={isButtonDisabled}
482
411
  data-testid="checkout-credit-card-place-order"
@@ -3,9 +3,9 @@ import { useAppSelector } from '@akinon/next/redux/hooks';
3
3
  import { RootState } from '@theme/redux/store';
4
4
  import { useSetPaymentOptionMutation } from '@akinon/next/data/client/checkout';
5
5
  import { CheckoutPaymentOption } from '@akinon/next/types';
6
+ import { Radio } from '@theme/components';
6
7
  import { usePaymentOptions } from '@akinon/next/hooks/use-payment-options';
7
8
  import { useMemo } from 'react';
8
- import { useCheckoutPaymentOptions } from '@theme/views/checkout/checkout-payment-options-registrar';
9
9
 
10
10
  const PaymentOptionButtons = () => {
11
11
  const { preOrder, attributeBasedShippingOptions } = useAppSelector(
@@ -13,19 +13,6 @@ const PaymentOptionButtons = () => {
13
13
  );
14
14
  const [setPaymentOption] = useSetPaymentOptionMutation();
15
15
  const { filteredPaymentOptions } = usePaymentOptions();
16
- const { isDesigner, viewType, sectionStyles } = useCheckoutPaymentOptions();
17
-
18
- // Helper to get style value (already includes unit if needed)
19
- const getStyleValue = (
20
- key: string,
21
- fallback: string | number = ''
22
- ): string | number => {
23
- const value = sectionStyles[key];
24
- if (value === undefined || value === null || value === '') {
25
- return fallback;
26
- }
27
- return value;
28
- };
29
16
 
30
17
  const onClickHandler = (option: CheckoutPaymentOption) => {
31
18
  setPaymentOption(option.pk);
@@ -53,166 +40,48 @@ const PaymentOptionButtons = () => {
53
40
 
54
41
  return (
55
42
  <>
56
- {/* Dropdown View - Real select dropdown */}
57
- {(!isDesigner || viewType === 'dropdown') && (
58
- <div
59
- className={clsx('w-full p-4', {
60
- 'md:hidden': !isDesigner
61
- })}
62
- >
63
- <select
64
- className="w-full block"
65
- style={{
66
- width: '100%',
67
- boxSizing: 'border-box',
68
- borderWidth: getStyleValue('dropdown-border-width', 1),
69
- borderStyle: 'solid',
70
- borderColor: getStyleValue(
71
- 'dropdown-border-color',
72
- '#e5e7eb'
73
- ) as string,
74
- borderRadius: getStyleValue('dropdown-border-radius', 0),
75
- backgroundColor: getStyleValue(
76
- 'dropdown-background-color',
77
- 'transparent'
78
- ) as string,
79
- paddingLeft: getStyleValue('dropdown-padding-x', 16),
80
- paddingRight: getStyleValue('dropdown-padding-x', 16),
81
- paddingTop: getStyleValue('dropdown-padding-y', 12),
82
- paddingBottom: getStyleValue('dropdown-padding-y', 12),
83
- marginBottom: getStyleValue('dropdown-spacing', 32),
84
- color: getStyleValue('dropdown-text-color', '#1f2937') as string,
85
- fontSize: getStyleValue('dropdown-font-size', 18),
86
- fontWeight: getStyleValue('dropdown-font-weight', '300'),
87
- cursor: 'pointer',
88
- outline: 'none'
89
- }}
90
- value={preOrder?.payment_option?.pk || ''}
91
- onChange={(e) => {
92
- const selectedPk = parseInt(e.target.value);
93
- const selectedOption = displayedPaymentOptions.find(
94
- (opt) => opt.pk === selectedPk
95
- );
96
- if (selectedOption) {
97
- onClickHandler(selectedOption);
98
- scrollToTop();
99
- }
100
- }}
43
+ <div className="w-full space-y-4 px-4 flex flex-col mb-8 md:hidden">
44
+ {displayedPaymentOptions.map((option) => (
45
+ <label
46
+ key={`payment-option-${option.pk}`}
47
+ className="border px-4 py-3 mt-3 flex h-12"
48
+ onClick={scrollToTop}
101
49
  >
102
- <option value="" disabled>
103
- Ödeme Yöntemi Seçin
104
- </option>
105
- {displayedPaymentOptions.map((option) => (
106
- <option
107
- key={`payment-option-dropdown-${option.pk}`}
108
- value={option.pk}
109
- >
110
- {option.name}
111
- </option>
112
- ))}
113
- </select>
114
- </div>
115
- )}
50
+ <Radio
51
+ type="radio"
52
+ name="payment-option"
53
+ value={option.pk}
54
+ checked={preOrder?.payment_option?.pk === option.pk}
55
+ onChange={() => onClickHandler(option)}
56
+ className="mr-2 mt-1"
57
+ />
58
+ <span className="flex text-primary-800 font-light text-lg">
59
+ {option.name}
60
+ </span>
61
+ </label>
62
+ ))}
63
+ </div>
116
64
 
117
- {/* Tab View - Show in designer when selected OR always on desktop in production */}
118
- {(!isDesigner || viewType === 'tab') && (
119
- <div
120
- className={clsx('flex overflow-x-auto', {
121
- 'hidden md:flex': !isDesigner
122
- })}
123
- >
124
- {displayedPaymentOptions.map((option) => (
125
- <button
126
- key={`payment-option-tab-${option.pk}`}
127
- onClick={() => onClickHandler(option)}
128
- className="flex items-center justify-center transition-colors"
129
- style={{
130
- borderRightWidth: getStyleValue('tab-border-width', 1),
131
- borderStyle: 'solid',
132
- borderColor: getStyleValue(
133
- 'tab-border-color',
134
- '#d1d5db'
135
- ) as string,
136
- borderBottomColor:
137
- preOrder?.payment_option?.pk === option.pk
138
- ? (getStyleValue(
139
- 'tab-active-border-bottom-color',
140
- 'transparent'
141
- ) as string)
142
- : (getStyleValue('tab-border-color', '#d1d5db') as string),
143
- borderBottomWidth:
65
+ <div className="hidden md:flex">
66
+ {displayedPaymentOptions.map((option) => (
67
+ <button
68
+ key={`payment-option-${option.pk}`}
69
+ onClick={() => onClickHandler(option)}
70
+ className={clsx(
71
+ 'flex items-center justify-center border-r border-b border-solid',
72
+ 'border-gray-400 text-xs uppercase text-black-800 font-medium',
73
+ 'text-opacity-60 bg-white h-11 px-5 transition-colors sm:h-15 sm:px-8 sm:py-8 hover:text-secondary',
74
+ {
75
+ 'text-opacity-100 border-b-transparent':
144
76
  preOrder?.payment_option?.pk === option.pk
145
- ? getStyleValue('tab-active-border-bottom-width', 0)
146
- : getStyleValue('tab-border-width', 1),
147
- backgroundColor:
148
- preOrder?.payment_option?.pk === option.pk
149
- ? (getStyleValue(
150
- 'tab-active-background-color',
151
- '#ffffff'
152
- ) as string)
153
- : (getStyleValue(
154
- 'tab-background-color',
155
- '#ffffff'
156
- ) as string),
157
- color:
158
- preOrder?.payment_option?.pk === option.pk
159
- ? (getStyleValue(
160
- 'tab-active-text-color',
161
- '#1a1a1a'
162
- ) as string)
163
- : (getStyleValue(
164
- 'tab-text-color',
165
- 'rgba(26, 26, 26, 0.6)'
166
- ) as string),
167
- height: getStyleValue('tab-height', 60),
168
- paddingLeft: getStyleValue('tab-padding-x', 32),
169
- paddingRight: getStyleValue('tab-padding-x', 32),
170
- paddingTop: getStyleValue('tab-padding-y', 32),
171
- paddingBottom: getStyleValue('tab-padding-y', 32),
172
- fontSize: getStyleValue('tab-font-size', 12),
173
- fontWeight: getStyleValue('tab-font-weight', '500'),
174
- textTransform: getStyleValue(
175
- 'tab-text-transform',
176
- 'uppercase'
177
- ) as string as
178
- | 'none'
179
- | 'capitalize'
180
- | 'uppercase'
181
- | 'lowercase'
182
- | 'initial'
183
- | 'inherit'
184
- }}
185
- onMouseEnter={(e) => {
186
- if (preOrder?.payment_option?.pk !== option.pk) {
187
- e.currentTarget.style.color = getStyleValue(
188
- 'tab-hover-text-color',
189
- '#ef4444'
190
- ) as string;
191
- e.currentTarget.style.backgroundColor = getStyleValue(
192
- 'tab-hover-background-color',
193
- '#ffffff'
194
- ) as string;
195
- }
196
- }}
197
- onMouseLeave={(e) => {
198
- if (preOrder?.payment_option?.pk !== option.pk) {
199
- e.currentTarget.style.color = getStyleValue(
200
- 'tab-text-color',
201
- 'rgba(26, 26, 26, 0.6)'
202
- ) as string;
203
- e.currentTarget.style.backgroundColor = getStyleValue(
204
- 'tab-background-color',
205
- '#ffffff'
206
- ) as string;
207
- }
208
- }}
209
- data-testid={`checkout-payment-tab-${option.pk}`}
210
- >
211
- {option.name}
212
- </button>
213
- ))}
214
- </div>
215
- )}
77
+ }
78
+ )}
79
+ data-testid={`checkout-payment-tab-${option.pk}`}
80
+ >
81
+ {option.name}
82
+ </button>
83
+ ))}
84
+ </div>
216
85
  </>
217
86
  );
218
87
  };
@@ -16,7 +16,6 @@ import { Button, Modal, Radio } from '@theme/components';
16
16
  import { resetCheckoutState } from '@akinon/next/redux/reducers/checkout';
17
17
  import { AddressForm } from '@theme/views/account/address-form';
18
18
  import { useLocalization } from '@akinon/next/hooks';
19
- import { useCheckoutAddress } from '@theme/views/checkout/checkout-address-registrar';
20
19
 
21
20
  interface AddressBoxProps {
22
21
  addressType: CheckoutAddressType;
@@ -32,20 +31,6 @@ const AddressBox = ({
32
31
  disabled
33
32
  }: AddressBoxProps) => {
34
33
  const { t } = useLocalization();
35
- const { sectionStyles } = useCheckoutAddress();
36
-
37
- // Helper to get style value (already includes unit if needed)
38
- const getStyleValue = (
39
- key: string,
40
- fallback: string | number = ''
41
- ): string | number => {
42
- const value = sectionStyles[key];
43
- if (value === undefined || value === null || value === '') {
44
- return fallback;
45
- }
46
- return value;
47
- };
48
-
49
34
  const [isEditAddressModalOpen, setIsEditAddressModalOpen] = useState(false);
50
35
  const [isRemoveAddressModalOpen, setRemoveAddressModalOpen] = useState(false);
51
36
  const { shipping_address, billing_address, delivery_option, retail_store } =
@@ -140,71 +125,24 @@ const AddressBox = ({
140
125
  }
141
126
  };
142
127
 
143
- const isSelected = addressType.value === address.pk;
144
-
145
- // Build dynamic styles from theme editor (values already include units)
146
- const boxStyles: React.CSSProperties = {
147
- borderColor: isSelected
148
- ? (getStyleValue('box-selected-border-color', '#030712') as string)
149
- : (getStyleValue('box-border-color', '#e5e7eb') as string),
150
- borderWidth: getStyleValue('box-border-width', '1px'),
151
- borderRadius: getStyleValue('box-border-radius', '8px'),
152
- backgroundColor: isSelected
153
- ? (getStyleValue('box-selected-background-color', '#ffffff') as string)
154
- : (getStyleValue('box-background-color', '#ffffff') as string),
155
- padding: getStyleValue('box-padding', '16px')
156
- };
157
-
158
- const titleStyles: React.CSSProperties = {
159
- fontSize: getStyleValue('box-title-font-size', '14px'),
160
- fontWeight: getStyleValue('box-title-font-weight', '600'),
161
- color: getStyleValue('box-title-color', '#030712') as string
162
- };
163
-
164
- const textStyles: React.CSSProperties = {
165
- fontSize: getStyleValue('box-text-font-size', '13px'),
166
- color: getStyleValue('box-text-color', '#6b7280') as string
167
- };
168
-
169
128
  return (
170
129
  <div
171
130
  onClick={() => handleAddressClick(addressType, address)}
172
131
  key={address.pk}
173
- style={boxStyles}
174
132
  className={clsx(
175
- 'cursor-pointer relative w-full border shadow min-h-[8rem] transition-all duration-200',
133
+ 'cursor-pointer relative w-full border shadow p-4 min-h-[8rem]',
134
+ "hover:after:content-[''] hover:after:border-4 hover:after:opacity-30 hover:after:transition-opacity",
135
+ 'after:border-secondary-400 after:absolute after:inset-0 after:duration-150 after:-z-10',
136
+ {
137
+ 'after:opacity-0': addressType.value !== address.pk
138
+ },
139
+ {
140
+ 'after:border-4 after:opacity-100': addressType.value === address.pk
141
+ },
176
142
  {
177
143
  'opacity-30 select-none pointer-events-none': disabled
178
144
  }
179
145
  )}
180
- onMouseEnter={(e) => {
181
- if (!isSelected && !disabled) {
182
- const hoverBorderColor = getStyleValue(
183
- 'box-hover-border-color',
184
- '#9ca3af'
185
- ) as string;
186
- const hoverBgColor = getStyleValue(
187
- 'box-hover-background-color',
188
- '#f9fafb'
189
- ) as string;
190
- e.currentTarget.style.borderColor = hoverBorderColor;
191
- e.currentTarget.style.backgroundColor = hoverBgColor;
192
- }
193
- }}
194
- onMouseLeave={(e) => {
195
- if (!isSelected && !disabled) {
196
- const borderColor = getStyleValue(
197
- 'box-border-color',
198
- '#e5e7eb'
199
- ) as string;
200
- const bgColor = getStyleValue(
201
- 'box-background-color',
202
- '#ffffff'
203
- ) as string;
204
- e.currentTarget.style.borderColor = borderColor;
205
- e.currentTarget.style.backgroundColor = bgColor;
206
- }
207
- }}
208
146
  >
209
147
  <Radio
210
148
  className="mb-2"
@@ -212,12 +150,12 @@ const AddressBox = ({
212
150
  checked={addressType.value === address.pk}
213
151
  onChange={() => null}
214
152
  >
215
- <span className="text-xs font-normal italic" style={textStyles}>
153
+ <span className="text-xs font-normal italic">
216
154
  {t('checkout.address.box.shipping_to')}:
217
155
  </span>
218
156
  </Radio>
219
- <div className="text-xs mb-3 leading-4" style={textStyles}>
220
- <p style={titleStyles}>{address.title}</p>
157
+ <div className="text-xs mb-3 leading-4">
158
+ <p>{address.title}</p>
221
159
  <p>{address.phone_number}</p>
222
160
  <p className="overflow-hidden text-ellipsis whitespace-nowrap">
223
161
  {address.line}
@@ -11,11 +11,9 @@ import { AddressForm } from '@theme/views/account/address-form';
11
11
  import { useLocalization } from '@akinon/next/hooks';
12
12
  import PluginModule, { Component } from '@akinon/next/components/plugin-module';
13
13
  import { Trans } from '@akinon/next/components/trans';
14
- import { useCheckoutAddress } from '@theme/views/checkout/checkout-address-registrar';
15
14
 
16
15
  const Addresses = () => {
17
16
  const { t } = useLocalization();
18
- const { viewType, sectionStyles } = useCheckoutAddress();
19
17
 
20
18
  const [isModalOpen, setIsModalOpen] = useState(false);
21
19
  const addressList = useAppSelector(
@@ -95,24 +93,6 @@ const Addresses = () => {
95
93
  return props.title;
96
94
  };
97
95
 
98
- const handleAddressSelect = (
99
- addressPk: string,
100
- addressType: CheckoutAddressType
101
- ) => {
102
- const pk = Number(addressPk);
103
- if (addressType.requestParam === 'shippingAddressPk') {
104
- if (isBillingAddressSame) {
105
- setAddresses({ shippingAddressPk: pk, billingAddressPk: pk });
106
- } else {
107
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
108
- setAddresses({ shippingAddressPk: pk } as any);
109
- }
110
- } else {
111
- // eslint-disable-next-line @typescript-eslint/no-explicit-any
112
- setAddresses({ billingAddressPk: pk } as any);
113
- }
114
- };
115
-
116
96
  return (
117
97
  <div className="w-full lg:w-3/5 lg:border-r lg:border-gray-400">
118
98
  {addressTypes
@@ -148,120 +128,57 @@ const Addresses = () => {
148
128
  }}
149
129
  />
150
130
  </p>
131
+ <div className="grid grid-cols-1 md:grid-cols-2 gap-4">
132
+ {addressList.map((address) => (
133
+ <AddressBox
134
+ key={address.pk}
135
+ addressType={addressType}
136
+ address={address}
137
+ isBillingAddressSame={isBillingAddressSame}
138
+ data-testid={`checkout-address-${address.pk}`}
139
+ disabled={
140
+ delivery_option?.delivery_option_type ===
141
+ 'retail_store' &&
142
+ addressType.requestParam === 'shippingAddressPk'
143
+ }
144
+ />
145
+ ))}
151
146
 
152
- {viewType === 'dropdown' ? (
153
- <div className="space-y-4">
154
- <div className="w-full">
155
- <select
156
- className="w-full p-2 border border-gray-300 rounded-md"
157
- value={addressType.value || ''}
158
- onChange={(e) =>
159
- handleAddressSelect(e.target.value, addressType)
160
- }
161
- disabled={
162
- delivery_option?.delivery_option_type ===
163
- 'retail_store' &&
164
- addressType.requestParam === 'shippingAddressPk'
165
- }
166
- >
167
- <option value="" disabled>
168
- {t('checkout.address.select_label') || 'Select Address'}
169
- </option>
170
- {addressList.map((address) => (
171
- <option key={address.pk} value={address.pk}>
172
- {address.title} - {address.first_name}{' '}
173
- {address.last_name}
174
- </option>
175
- ))}
176
- </select>
177
- </div>
178
- {addressList.find((a) => a.pk === addressType.value) && (
179
- <div className="p-4 bg-gray-50 rounded-md text-sm text-gray-600">
180
- {(() => {
181
- const addr = addressList.find(
182
- (a) => a.pk === addressType.value
183
- );
184
- return addr ? (
185
- <>
186
- <p className="font-semibold">{addr.title}</p>
187
- <p>{addr.line}</p>
188
- <p>
189
- {addr.township?.name} / {addr.city?.name}
190
- </p>
191
- </>
192
- ) : null;
193
- })()}
194
- </div>
147
+ <PluginModule
148
+ component={Component.ClickCollect}
149
+ props={{ addressTypeParam: addressType.requestParam }}
150
+ />
151
+
152
+ <div
153
+ role="button"
154
+ onClick={() => setIsModalOpen(true)}
155
+ className={clsx(
156
+ 'relative cursor-pointer w-full min-h-[8rem] border shadow p-4',
157
+ "hover:after:content-[''] hover:after:border-4 hover:after:opacity-30 hover:after:transition-opacity",
158
+ 'after:border-secondary-400 after:absolute after:inset-0 after:opacity-0 after:duration-150 after:-z-10',
159
+ {
160
+ 'opacity-30 select-none pointer-events-none':
161
+ delivery_option?.delivery_option_type === 'retail_store'
162
+ }
195
163
  )}
196
- <div className="mt-4">
197
- <button
198
- onClick={() => setIsModalOpen(true)}
199
- className="text-primary-500 underline text-sm flex items-center gap-1"
200
- >
201
- <Icon name="plus" size={12} />
164
+ >
165
+ <div className="text-xs flex justify-center items-center h-full gap-x-2">
166
+ <Icon name="plus" size={12} />
167
+ <span data-testid="checkout-add-new-address">
202
168
  {t('checkout.address.add_new_address')}
203
- </button>
169
+ </span>
204
170
  </div>
205
171
  </div>
206
- ) : (
207
- <div
208
- className="grid grid-cols-1 md:grid-cols-2"
209
- style={{
210
- gap: sectionStyles['box-gap'] || '12px'
211
- }}
172
+ <Modal
173
+ portalId="orders-checkout-new-address-modal"
174
+ title={t('checkout.address.add_new_address')}
175
+ open={isModalOpen}
176
+ setOpen={setIsModalOpen}
177
+ className="w-full sm:w-[28rem] max-h-[90vh] overflow-y-auto"
212
178
  >
213
- {addressList.map((address) => (
214
- <AddressBox
215
- key={address.pk}
216
- addressType={addressType}
217
- address={address}
218
- isBillingAddressSame={isBillingAddressSame}
219
- data-testid={`checkout-address-${address.pk}`}
220
- disabled={
221
- delivery_option?.delivery_option_type ===
222
- 'retail_store' &&
223
- addressType.requestParam === 'shippingAddressPk'
224
- }
225
- />
226
- ))}
227
-
228
- <PluginModule
229
- component={Component.ClickCollect}
230
- props={{ addressTypeParam: addressType.requestParam }}
231
- />
232
-
233
- <div
234
- role="button"
235
- onClick={() => setIsModalOpen(true)}
236
- className={clsx(
237
- 'relative cursor-pointer w-full min-h-[8rem] border shadow p-4',
238
- "hover:after:content-[''] hover:after:border-4 hover:after:opacity-30 hover:after:transition-opacity",
239
- 'after:border-secondary-400 after:absolute after:inset-0 after:opacity-0 after:duration-150 after:-z-10',
240
- {
241
- 'opacity-30 select-none pointer-events-none':
242
- delivery_option?.delivery_option_type ===
243
- 'retail_store'
244
- }
245
- )}
246
- >
247
- <div className="text-xs flex justify-center items-center h-full gap-x-2">
248
- <Icon name="plus" size={12} />
249
- <span data-testid="checkout-add-new-address">
250
- {t('checkout.address.add_new_address')}
251
- </span>
252
- </div>
253
- </div>
254
- </div>
255
- )}
256
- <Modal
257
- portalId="orders-checkout-new-address-modal"
258
- title={t('checkout.address.add_new_address')}
259
- open={isModalOpen}
260
- setOpen={setIsModalOpen}
261
- className="w-full sm:w-[28rem] max-h-[90vh] overflow-y-auto"
262
- >
263
- <AddressForm onSubmit={onSubmit} />
264
- </Modal>
179
+ <AddressForm onSubmit={onSubmit} />
180
+ </Modal>
181
+ </div>
265
182
  </div>
266
183
  </div>
267
184
  ))}