ordering-ui-react-native 0.16.48 → 0.16.49-release

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 (208) hide show
  1. package/package.json +6 -5
  2. package/src/DeliveryApp.tsx +43 -1
  3. package/src/components/ActiveOrders/index.tsx +61 -63
  4. package/src/components/ActiveOrders/styles.tsx +8 -14
  5. package/src/components/BusinessBasicInformation/index.tsx +11 -19
  6. package/src/components/BusinessInformation/index.tsx +33 -4
  7. package/src/components/BusinessInformation/styles.tsx +2 -2
  8. package/src/components/BusinessProductsList/index.tsx +10 -10
  9. package/src/components/BusinessesListing/index.tsx +1 -1
  10. package/src/components/Checkout/index.tsx +2 -1
  11. package/src/components/LanguageSelector/index.tsx +21 -16
  12. package/src/components/Messages/index.tsx +2 -2
  13. package/src/components/NotificationSetting/index.tsx +85 -0
  14. package/src/components/OrdersOption/index.tsx +54 -56
  15. package/src/components/PaymentOptions/index.tsx +298 -345
  16. package/src/components/PaymentOptionsWebView/index.tsx +120 -121
  17. package/src/components/ReviewDriver/index.tsx +1 -1
  18. package/src/components/ReviewOrder/index.tsx +2 -2
  19. package/src/components/ReviewProducts/index.tsx +11 -0
  20. package/src/components/SingleProductReview/index.tsx +8 -5
  21. package/src/components/StripeElementsForm/index.tsx +25 -16
  22. package/src/components/VerifyPhone/styles.tsx +1 -2
  23. package/src/components/shared/OBottomPopup.tsx +6 -2
  24. package/src/components/shared/OToast.tsx +4 -4
  25. package/src/index.tsx +2 -0
  26. package/src/types/@fatnlazycat/react-native-recaptcha-v3/index.d.ts +1 -0
  27. package/src/utils/index.tsx +2 -1
  28. package/themes/business/src/components/AcceptOrRejectOrder/index.tsx +259 -238
  29. package/themes/business/src/components/AcceptOrRejectOrder/styles.tsx +6 -4
  30. package/themes/business/src/components/BusinessController/index.tsx +2 -2
  31. package/themes/business/src/components/Chat/index.tsx +40 -32
  32. package/themes/business/src/components/DriverMap/index.tsx +7 -5
  33. package/themes/business/src/components/DriverSchedule/index.tsx +36 -19
  34. package/themes/business/src/components/LoginForm/index.tsx +111 -74
  35. package/themes/business/src/components/MapView/index.tsx +12 -1
  36. package/themes/business/src/components/MessagesOption/index.tsx +11 -1
  37. package/themes/business/src/components/NewOrderNotification/index.tsx +26 -41
  38. package/themes/business/src/components/OrderDetails/OrderContentComponent.tsx +40 -30
  39. package/themes/business/src/components/OrderDetails/OrderHeaderComponent.tsx +3 -3
  40. package/themes/business/src/components/OrdersListManager/index.tsx +10 -3
  41. package/themes/business/src/components/OrdersOption/index.tsx +76 -77
  42. package/themes/business/src/components/OrdersOption/styles.tsx +5 -1
  43. package/themes/business/src/components/OrdersOptionBusiness/index.tsx +15 -1
  44. package/themes/business/src/components/OrdersOptionCity/index.tsx +15 -1
  45. package/themes/business/src/components/OrdersOptionDate/index.tsx +19 -6
  46. package/themes/business/src/components/OrdersOptionDelivery/index.tsx +15 -1
  47. package/themes/business/src/components/OrdersOptionDriver/index.tsx +15 -1
  48. package/themes/business/src/components/OrdersOptionPaymethod/index.tsx +15 -1
  49. package/themes/business/src/components/OrdersOptionStatus/index.tsx +10 -1
  50. package/themes/business/src/components/PreviousMessages/index.tsx +17 -18
  51. package/themes/business/src/components/PreviousOrders/OrderItem.tsx +250 -0
  52. package/themes/business/src/components/PreviousOrders/OrdersGroupedItem.tsx +115 -0
  53. package/themes/business/src/components/PreviousOrders/index.tsx +332 -244
  54. package/themes/business/src/components/PreviousOrders/styles.tsx +30 -2
  55. package/themes/business/src/components/ProductItemAccordion/index.tsx +3 -2
  56. package/themes/business/src/components/ReviewCustomer/index.tsx +39 -15
  57. package/themes/business/src/components/ScheduleBlocked/index.tsx +2 -2
  58. package/themes/business/src/components/UserFormDetails/index.tsx +5 -2
  59. package/themes/business/src/components/UserProfileForm/index.tsx +2 -0
  60. package/themes/business/src/components/shared/ODropDown.tsx +42 -8
  61. package/themes/business/src/components/shared/ODropDownCalendar.tsx +36 -7
  62. package/themes/business/src/components/shared/OLink.tsx +24 -12
  63. package/themes/business/src/components/shared/OText.tsx +3 -2
  64. package/themes/business/src/types/index.tsx +25 -11
  65. package/themes/business/src/utils/index.tsx +10 -0
  66. package/themes/doordash/src/components/BusinessesListing/index.tsx +1 -1
  67. package/themes/doordash/src/components/LoginForm/index.tsx +1 -2
  68. package/themes/instacart/src/components/BusinessesListing/index.tsx +1 -1
  69. package/themes/kiosk/src/components/BusinessesListing/index.tsx +2 -1
  70. package/themes/kiosk/src/components/Checkout/index.tsx +6 -0
  71. package/themes/kiosk/src/components/LoginForm/index.tsx +121 -10
  72. package/themes/kiosk/src/components/LoginForm/styles.tsx +5 -0
  73. package/themes/kiosk/src/components/NavBar/index.tsx +14 -14
  74. package/themes/kiosk/src/components/OptionCard/index.tsx +1 -1
  75. package/themes/kiosk/src/components/OrderTypeCardSelector/index.tsx +8 -10
  76. package/themes/kiosk/src/components/ProductForm/index.tsx +1 -14
  77. package/themes/kiosk/src/components/shared/OButton.tsx +5 -18
  78. package/themes/kiosk/src/types/index.d.ts +2 -0
  79. package/themes/original/index.tsx +8 -0
  80. package/themes/original/src/components/AddressDetails/index.tsx +10 -8
  81. package/themes/original/src/components/AddressForm/index.tsx +157 -140
  82. package/themes/original/src/components/AddressList/index.tsx +1 -1
  83. package/themes/original/src/components/AppleLogin/index.tsx +4 -4
  84. package/themes/original/src/components/BusinessBasicInformation/index.tsx +218 -147
  85. package/themes/original/src/components/BusinessBasicInformation/styles.tsx +2 -2
  86. package/themes/original/src/components/BusinessController/index.tsx +231 -114
  87. package/themes/original/src/components/BusinessController/styles.tsx +14 -9
  88. package/themes/original/src/components/BusinessInformation/index.tsx +10 -31
  89. package/themes/original/src/components/BusinessItemAccordion/index.tsx +12 -6
  90. package/themes/original/src/components/BusinessListingSearch/BusinessControllerSkeletons/index.tsx +57 -0
  91. package/themes/original/src/components/BusinessListingSearch/MaxSectionItem/index.tsx +59 -0
  92. package/themes/original/src/components/BusinessListingSearch/MaxSectionItem/styles.tsx +13 -0
  93. package/themes/original/src/components/BusinessListingSearch/index.tsx +109 -139
  94. package/themes/original/src/components/BusinessListingSearch/styles.tsx +10 -12
  95. package/themes/original/src/components/BusinessProductsList/SubcategoriesComponent/index.tsx +87 -0
  96. package/themes/original/src/components/BusinessProductsList/SubcategoriesComponent/styles.tsx +12 -0
  97. package/themes/original/src/components/BusinessProductsList/index.tsx +59 -60
  98. package/themes/original/src/components/BusinessProductsList/styles.tsx +0 -3
  99. package/themes/original/src/components/BusinessProductsListing/index.tsx +177 -80
  100. package/themes/original/src/components/BusinessProductsListing/styles.tsx +18 -11
  101. package/themes/original/src/components/BusinessTypeFilter/index.tsx +3 -2
  102. package/themes/original/src/components/BusinessesListing/Layout/Appointment/index.tsx +35 -23
  103. package/themes/original/src/components/BusinessesListing/Layout/Appointment/styles.tsx +3 -2
  104. package/themes/original/src/components/BusinessesListing/Layout/Original/index.tsx +275 -120
  105. package/themes/original/src/components/BusinessesListing/Layout/Original/styles.tsx +47 -10
  106. package/themes/original/src/components/BusinessesListing/index.tsx +80 -25
  107. package/themes/original/src/components/Cart/index.tsx +82 -15
  108. package/themes/original/src/components/Cart/styles.tsx +4 -0
  109. package/themes/original/src/components/CartContent/index.tsx +22 -16
  110. package/themes/original/src/components/Checkout/index.tsx +114 -118
  111. package/themes/original/src/components/Checkout/styles.tsx +4 -3
  112. package/themes/original/src/components/CitiesControl/index.tsx +89 -0
  113. package/themes/original/src/components/CitiesControl/styles.tsx +17 -0
  114. package/themes/original/src/components/DriverTips/index.tsx +4 -4
  115. package/themes/original/src/components/DriverTips/styles.tsx +2 -1
  116. package/themes/original/src/components/FavoriteList/index.tsx +69 -45
  117. package/themes/original/src/components/FloatingButton/index.tsx +13 -11
  118. package/themes/original/src/components/FloatingButton/styles.tsx +1 -1
  119. package/themes/original/src/components/GPSButton/index.tsx +20 -19
  120. package/themes/original/src/components/GPSButton/styles.ts +3 -3
  121. package/themes/original/src/components/GoogleMap/index.tsx +20 -12
  122. package/themes/original/src/components/HelpAccountAndPayment/index.tsx +25 -10
  123. package/themes/original/src/components/HelpAccountAndPayment/styles.tsx +4 -0
  124. package/themes/original/src/components/HelpGuide/index.tsx +9 -8
  125. package/themes/original/src/components/HelpOrder/index.tsx +9 -8
  126. package/themes/original/src/components/LanguageSelector/index.tsx +19 -14
  127. package/themes/original/src/components/LoginForm/Otp/index.tsx +89 -73
  128. package/themes/original/src/components/LoginForm/Otp/styles.tsx +0 -1
  129. package/themes/original/src/components/LoginForm/index.tsx +98 -41
  130. package/themes/original/src/components/LottieAnimation/index.tsx +69 -0
  131. package/themes/original/src/components/Messages/index.tsx +35 -20
  132. package/themes/original/src/components/MomentOption/index.tsx +8 -6
  133. package/themes/original/src/components/MultiCart/index.tsx +63 -0
  134. package/themes/original/src/components/MultiCartsPaymethodsAndWallets/index.tsx +92 -93
  135. package/themes/original/src/components/MultiCheckout/index.tsx +10 -2
  136. package/themes/original/src/components/MultiOrdersDetails/index.tsx +34 -16
  137. package/themes/original/src/components/MyOrders/index.tsx +88 -22
  138. package/themes/original/src/components/NavBar/index.tsx +11 -5
  139. package/themes/original/src/components/NetworkError/index.tsx +5 -3
  140. package/themes/original/src/components/NotFoundSource/index.tsx +2 -1
  141. package/themes/original/src/components/Notifications/index.tsx +148 -0
  142. package/themes/original/src/components/Notifications/styles.tsx +17 -0
  143. package/themes/original/src/components/OrderDetails/OrderHistory.tsx +167 -0
  144. package/themes/original/src/components/OrderDetails/index.tsx +200 -39
  145. package/themes/original/src/components/OrderDetails/styles.tsx +15 -2
  146. package/themes/original/src/components/OrderItAgain/index.tsx +75 -0
  147. package/themes/original/src/components/OrderItAgain/styles.tsx +10 -0
  148. package/themes/original/src/components/OrderProgress/index.tsx +77 -66
  149. package/themes/original/src/components/OrderProgress/styles.tsx +5 -0
  150. package/themes/original/src/components/OrderSummary/index.tsx +2 -35
  151. package/themes/original/src/components/OrderTypeSelector/index.tsx +85 -36
  152. package/themes/original/src/components/OrderTypeSelector/styles.tsx +19 -1
  153. package/themes/original/src/components/OrdersOption/PreviousBusinessOrdered/index.tsx +94 -98
  154. package/themes/original/src/components/OrdersOption/PreviousProductsOrdered/index.tsx +3 -0
  155. package/themes/original/src/components/OrdersOption/index.tsx +101 -56
  156. package/themes/original/src/components/PaymentOptionWallet/index.tsx +56 -56
  157. package/themes/original/src/components/PaymentOptions/index.tsx +1 -2
  158. package/themes/original/src/components/PhoneInputNumber/index.tsx +1 -1
  159. package/themes/original/src/components/PlaceSpot/index.tsx +249 -47
  160. package/themes/original/src/components/PlaceSpot/styles.tsx +0 -2
  161. package/themes/original/src/components/PreviousOrders/index.tsx +3 -2
  162. package/themes/original/src/components/ProductForm/index.tsx +639 -664
  163. package/themes/original/src/components/ProductForm/styles.tsx +10 -11
  164. package/themes/original/src/components/ProductItemAccordion/index.tsx +199 -128
  165. package/themes/original/src/components/ProductOption/index.tsx +1 -1
  166. package/themes/original/src/components/ProductOptionSubOption/index.tsx +16 -8
  167. package/themes/original/src/components/ProductOptionSubOption/styles.tsx +0 -1
  168. package/themes/original/src/components/ProfessionalFilter/index.tsx +2 -1
  169. package/themes/original/src/components/ProfessionalProfile/index.tsx +19 -8
  170. package/themes/original/src/components/Promotions/index.tsx +232 -219
  171. package/themes/original/src/components/Promotions/styles.tsx +7 -2
  172. package/themes/original/src/components/ReviewDriver/index.tsx +3 -3
  173. package/themes/original/src/components/ReviewOrder/index.tsx +120 -108
  174. package/themes/original/src/components/ReviewOrder/styles.tsx +5 -7
  175. package/themes/original/src/components/ReviewProducts/index.tsx +8 -5
  176. package/themes/original/src/components/ReviewTrigger/index.tsx +136 -0
  177. package/themes/original/src/components/ReviewTrigger/styles.tsx +41 -0
  178. package/themes/original/src/components/ScheduleAccordion/index.tsx +68 -0
  179. package/themes/original/src/components/ScheduleAccordion/styles.tsx +14 -0
  180. package/themes/original/src/components/ServiceForm/index.tsx +341 -267
  181. package/themes/original/src/components/SignupForm/index.tsx +160 -113
  182. package/themes/original/src/components/SingleOrderCard/index.tsx +266 -183
  183. package/themes/original/src/components/SingleOrderCard/styles.tsx +10 -8
  184. package/themes/original/src/components/SingleProductCard/index.tsx +198 -112
  185. package/themes/original/src/components/SingleProductCard/styles.tsx +3 -10
  186. package/themes/original/src/components/SingleProductReview/index.tsx +38 -5
  187. package/themes/original/src/components/SingleProductReview/styles.tsx +12 -0
  188. package/themes/original/src/components/StripeElementsForm/index.tsx +13 -2
  189. package/themes/original/src/components/UpsellingProducts/index.tsx +15 -5
  190. package/themes/original/src/components/UserDetails/index.tsx +5 -3
  191. package/themes/original/src/components/UserFormDetails/index.tsx +6 -48
  192. package/themes/original/src/components/UserProfile/index.tsx +56 -31
  193. package/themes/original/src/components/UserProfile/styles.ts +17 -0
  194. package/themes/original/src/components/WalletTransactions/index.tsx +76 -0
  195. package/themes/original/src/components/WalletTransactions/styles.tsx +13 -0
  196. package/themes/original/src/components/Wallets/index.tsx +176 -164
  197. package/themes/original/src/components/Wallets/styles.tsx +12 -8
  198. package/themes/original/src/components/shared/CardAnimation.tsx +47 -0
  199. package/themes/original/src/components/shared/HeaderTitle.tsx +8 -3
  200. package/themes/original/src/components/shared/OBottomPopup.tsx +48 -15
  201. package/themes/original/src/components/shared/OButton.tsx +10 -3
  202. package/themes/original/src/components/shared/OIcon.tsx +8 -1
  203. package/themes/original/src/components/shared/OInput.tsx +10 -1
  204. package/themes/original/src/layouts/Container.tsx +13 -9
  205. package/themes/original/src/layouts/FloatingBottomContainer.tsx +5 -1
  206. package/themes/original/src/types/index.tsx +86 -28
  207. package/themes/original/src/utils/index.tsx +103 -58
  208. package/themes/uber-eats/src/components/BusinessesListing/index.tsx +1 -1
@@ -11,6 +11,8 @@ import { StyleSheet } from 'react-native';
11
11
  import { useTheme } from 'styled-components/native';
12
12
  import { shape } from '../../utils'
13
13
  import { CategoryDescriptionMemoized } from './CategoryDescription';
14
+ import { OrderItAgain } from '../OrderItAgain'
15
+ import { SubcategoriesComponentMemoized } from './SubcategoriesComponent';
14
16
 
15
17
  const BusinessProductsListUI = (props: BusinessProductsListParams) => {
16
18
  const {
@@ -35,7 +37,9 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
35
37
  onClickCategory,
36
38
  lazyLoadProductsRecommended,
37
39
  handleUpdateProducts,
38
- isFiltMode
40
+ previouslyProducts,
41
+ isFiltMode,
42
+ navigation
39
43
  } = props;
40
44
 
41
45
  const [, t] = useLanguage();
@@ -67,51 +71,29 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
67
71
  }
68
72
  }
69
73
 
70
- const SubcategoriesComponent = ({ category }: any) => {
71
- const allsubcategorySelected = !subcategoriesSelected?.some((subcategory: any) => category?.id === subcategory?.parent_category_id)
72
-
73
- return (
74
- <SubCategoriesContainer>
75
- <ContainerButton
76
- isSelected={allsubcategorySelected}
77
- >
78
- <OButton
79
- onClick={() => onClickSubcategory(null, category)}
80
- bgColor={allsubcategorySelected ? theme.colors.primary : theme.colors.backgroundGray}
81
- text={`${t('ALL', 'All')} ${allsubcategorySelected ? 'X' : ''}`}
82
- style={bpStyles.categoryButtonStyle}
83
- textStyle={{ color: allsubcategorySelected ? theme.colors.white : theme.colors.textNormal, fontSize: 12 }}
84
- />
85
- </ContainerButton>
86
- {category?.subcategories?.map((subcategory: any) => {
87
- const isSubcategorySelected = subcategoriesSelected?.find((_subcategory: any) => _subcategory?.id === subcategory?.id)
88
- return (
89
- <ContainerButton
90
- key={subcategory?.id}
91
- isSelected={isSubcategorySelected}
92
- >
93
- <OButton
94
- onClick={() => onClickSubcategory(subcategory, category)}
95
- bgColor={isSubcategorySelected ? theme.colors.primary : theme.colors.backgroundGray}
96
- text={`${subcategory?.name} ${isSubcategorySelected ? 'X' : ''}`}
97
- style={bpStyles.categoryButtonStyle}
98
- textStyle={{ color: isSubcategorySelected ? theme.colors.white : theme.colors.textNormal, fontSize: 12 }}
99
- />
100
- </ContainerButton>
101
- )
102
- }
103
- )}
104
- </SubCategoriesContainer>
105
- )
106
- }
107
-
108
74
  return (
109
75
  <ProductsContainer renderToHardwareTextureAndroid={categoryState.loading || isBusinessLoading}>
110
76
  <HeaderWrapper>
111
77
  {category?.subcategories?.length > 0 && (
112
- <SubcategoriesComponent category={category} />
78
+ <SubcategoriesComponentMemoized
79
+ category={category}
80
+ subcategoriesSelected={subcategoriesSelected}
81
+ onClickSubcategory={onClickSubcategory}
82
+ />
113
83
  )}
114
84
  </HeaderWrapper>
85
+ {previouslyProducts?.length > 0 && (
86
+ <OrderItAgain
87
+ onProductClick={onProductClick}
88
+ productList={previouslyProducts}
89
+ businessId={businessId}
90
+ categoryState={categoryState}
91
+ navigation={navigation}
92
+ handleUpdateProducts={handleUpdateProducts}
93
+ currentCart={currentCart}
94
+ searchValue={searchValue}
95
+ />
96
+ )}
115
97
  {category.id &&
116
98
  categoryState.products
117
99
  ?.filter((product: any) =>
@@ -122,12 +104,14 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
122
104
  <SingleProductCard
123
105
  key={'prod_' + product.id + `_${i}`}
124
106
  isSoldOut={product.inventoried && !product.quantity}
107
+ enableIntersection={!isFiltMode && categoryState.products?.length < 80}
125
108
  product={product}
126
109
  businessId={businessId}
127
110
  categoryState={categoryState}
128
111
  onProductClick={() => onProductClick(product)}
129
112
  productAddedToCartLength={currentCart?.products?.reduce((productsLength: number, Cproduct: any) => { return productsLength + (Cproduct?.id === product?.id ? Cproduct?.quantity : 0) }, 0)}
130
113
  handleUpdateProducts={handleUpdateProducts}
114
+ navigation={navigation}
131
115
  />
132
116
  ))
133
117
  }
@@ -148,11 +132,13 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
148
132
  key={'feat_' + product.id + `_${i}`}
149
133
  isSoldOut={product.inventoried && !product.quantity}
150
134
  product={product}
135
+ enableIntersection={!isFiltMode && categoryState.products?.length < 80}
151
136
  businessId={businessId}
152
137
  categoryState={categoryState}
153
138
  onProductClick={onProductClick}
154
139
  handleUpdateProducts={handleUpdateProducts}
155
140
  productAddedToCartLength={currentCart?.products?.reduce((productsLength: number, Cproduct: any) => { return productsLength + (Cproduct?.id === product?.id ? Cproduct?.quantity : 0) }, 0)}
141
+ navigation={navigation}
156
142
  />
157
143
  ),
158
144
  )}
@@ -180,14 +166,16 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
180
166
  style={bpStyles.catWrap}
181
167
  onLayout={(event: any) => handleOnLayout(event, category.id)}
182
168
  >
183
- <View style={bpStyles.catIcon}>
184
- <OIcon
185
- url={optimizeImage(category.image, 'h_250,c_limit')}
186
- width={41}
187
- height={41}
188
- style={{ borderRadius: 7.6 }}
189
- />
190
- </View>
169
+ {!!category.image && (
170
+ <View style={bpStyles.catIcon}>
171
+ <OIcon
172
+ url={optimizeImage(category.image, 'h_250,c_limit')}
173
+ width={41}
174
+ height={41}
175
+ style={{ borderRadius: 7.6 }}
176
+ />
177
+ </View>
178
+ )}
191
179
  <OText size={16} weight="600">
192
180
  {category.name}
193
181
  </OText>
@@ -233,18 +221,24 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
233
221
  </View>
234
222
  )}
235
223
  {category?.subcategories?.length > 0 && !isFiltMode && (
236
- <SubcategoriesComponent category={category} />
224
+ <SubcategoriesComponentMemoized
225
+ category={category}
226
+ subcategoriesSelected={subcategoriesSelected}
227
+ onClickSubcategory={onClickSubcategory}
228
+ />
237
229
  )}
238
230
  <>
239
231
  {products.sort((a: any, b: any) => a.rank - b.rank).map((product: any, i: any) => (
240
232
  <SingleProductCard
241
233
  key={`${product?.id}_${i}`}
234
+ enableIntersection={!isFiltMode && categoryState.products?.length < 80}
242
235
  isSoldOut={product.inventoried && !product.quantity}
243
236
  businessId={businessId}
244
237
  product={product}
245
238
  categoryState={categoryState}
246
239
  onProductClick={onProductClick}
247
240
  handleUpdateProducts={handleUpdateProducts}
241
+ navigation={navigation}
248
242
  productAddedToCartLength={currentCart?.products?.reduce((productsLength: number, Cproduct: any) => { return productsLength + (Cproduct?.id === product?.id ? Cproduct?.quantity : 0) }, 0)}
249
243
  />
250
244
  ))}
@@ -259,19 +253,24 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
259
253
  <>
260
254
  {[...Array(categoryState?.pagination?.nextPageItems).keys()].map(
261
255
  (item, i) => (
262
- <Placeholder key={i} style={{ padding: 5 }} Animation={Fade}>
263
- <View style={{ flexDirection: 'row' }}>
256
+ <View style={{ minHeight: 165, marginBottom: 28, padding: 12 }} key={i}>
257
+ <Placeholder style={{ padding: 5 }} Animation={Fade}>
258
+ <View style={{ flexDirection: 'row' }}>
259
+ <Placeholder style={{ paddingVertical: 10, flex: 1 }}>
260
+ <PlaceholderLine width={60} style={{ marginBottom: 15 }} />
261
+ <PlaceholderLine width={20} />
262
+ </Placeholder>
263
+ <PlaceholderLine
264
+ width={24}
265
+ height={70}
266
+ style={{ marginLeft: 10, marginBottom: 10 }}
267
+ />
268
+ </View>
264
269
  <PlaceholderLine
265
- width={24}
266
- height={70}
267
- style={{ marginRight: 10, marginBottom: 10 }}
270
+ height={52}
268
271
  />
269
- <Placeholder style={{ paddingVertical: 10 }}>
270
- <PlaceholderLine width={60} style={{ marginBottom: 25 }} />
271
- <PlaceholderLine width={20} />
272
- </Placeholder>
273
- </View>
274
- </Placeholder>
272
+ </Placeholder>
273
+ </View>
275
274
  ),
276
275
  )}
277
276
  </>
@@ -18,15 +18,12 @@ export const RibbonBox = styled.View`
18
18
  background-color: ${(props: any) => props.theme.colors.primary};
19
19
  padding: 2px 8px;
20
20
  max-width: 180px;
21
-
22
21
  ${(props: any) => props.bgColor && css`
23
22
  background-color: ${props.bgColor};
24
23
  `}
25
-
26
24
  ${(props: any) => props.isRoundRect && css`
27
25
  border-radius: 7.6px;
28
26
  `}
29
-
30
27
  ${(props: any) => props.isCapsule && css`
31
28
  border-radius: 50px;
32
29
  `}
@@ -1,5 +1,7 @@
1
1
  import React, { useCallback, useEffect, useRef, useState } from 'react'
2
2
  import { View, TouchableOpacity, StyleSheet, SafeAreaView, Dimensions, Platform, KeyboardAvoidingViewBase, KeyboardAvoidingView } from 'react-native'
3
+ import { IOScrollView } from 'react-native-intersection-observer'
4
+ import { useSafeAreaInsets } from 'react-native-safe-area-context'
3
5
  import { useTheme } from 'styled-components/native';
4
6
  import {
5
7
  BusinessAndProductList,
@@ -11,6 +13,7 @@ import {
11
13
  useToast,
12
14
  useConfig
13
15
  } from 'ordering-components/native'
16
+ import { Fade, Placeholder, PlaceholderLine } from 'rn-placeholder';
14
17
  import { OButton, OIcon, OModal, OText } from '../shared'
15
18
  import Alert from '../../providers/AlertProvider'
16
19
  import { BusinessBasicInformation } from '../BusinessBasicInformation'
@@ -19,21 +22,26 @@ import { BusinessProductsCategories } from '../BusinessProductsCategories'
19
22
  import { BusinessProductsList } from '../BusinessProductsList'
20
23
  import { BusinessProductsListingParams } from '../../types'
21
24
  import { _retrieveStoreData, _removeStoreData } from '../../providers/StoreUtil';
25
+ import IconAntDesign from 'react-native-vector-icons/AntDesign';
26
+ import { useIsFocused } from '@react-navigation/native';
27
+
22
28
  import {
23
29
  TopHeader,
24
30
  WrapSearchBar,
25
31
  WrapContent,
26
- BusinessProductsListingContainer,
27
32
  FiltProductsContainer,
28
33
  ContainerSafeAreaView,
29
34
  BackgroundGray,
30
- ProfessionalFilterWrapper
35
+ ProfessionalFilterWrapper,
36
+ NearBusiness,
37
+ TopActions
31
38
  } from './styles'
32
39
  import { FloatingButton } from '../FloatingButton'
33
40
  import { UpsellingRedirect } from './UpsellingRedirect'
34
41
  import Animated from 'react-native-reanimated'
35
42
  import { ProfessionalFilter } from '../ProfessionalFilter';
36
43
  import { ServiceForm } from '../ServiceForm';
44
+ import { BusinessesListing } from '../BusinessesListing/Layout/Original'
37
45
 
38
46
  const PIXELS_TO_SCROLL = 2000
39
47
 
@@ -58,20 +66,29 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
58
66
  getNextProducts,
59
67
  handleUpdateProducts,
60
68
  professionalSelected,
61
- handleChangeProfessionalSelected
69
+ handleUpdateProfessionals,
70
+ handleChangeProfessionalSelected,
71
+ onBusinessClick
62
72
  } = props
63
73
 
74
+ const insets = useSafeAreaInsets()
64
75
  const theme = useTheme();
65
76
  const [, t] = useLanguage()
66
77
  const [{ auth }] = useSession()
67
- const [orderState, { clearCart }] = useOrder()
78
+ const [orderState, { addProduct, updateProduct }] = useOrder()
68
79
  const [{ parsePrice }] = useUtils()
69
80
  const [, { showToast }] = useToast()
70
81
  const [{ configs }] = useConfig()
82
+ const isFocused = useIsFocused();
71
83
  const isPreOrder = configs?.preorder_status_enabled?.value === '1'
84
+
85
+ const isChewLayout = theme?.business_view?.components?.header?.components?.layout?.type === 'chew'
86
+ const showLogo = !theme?.business_view?.components?.header?.components?.business?.components?.logo?.hidden
87
+ const hideBusinessNearCity = theme?.business_view?.components?.near_business?.hidden ?? true
88
+
72
89
  const styles = StyleSheet.create({
73
90
  mainContainer: {
74
- flex: 1,
91
+ flex: 1
75
92
  },
76
93
  BackIcon: {
77
94
  paddingRight: 20,
@@ -93,7 +110,13 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
93
110
  padding: 15,
94
111
  justifyContent: 'center',
95
112
  shadowColor: theme.colors.clear,
96
- }
113
+ },
114
+ businessSkeleton: {
115
+ borderRadius: 8,
116
+ marginRight: 20,
117
+ width: 56,
118
+ height: 56
119
+ },
97
120
  })
98
121
 
99
122
  const { business, loading, error } = businessState
@@ -108,26 +131,51 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
108
131
  const [subcategoriesSelected, setSubcategoriesSelected] = useState([])
109
132
  const [openService, setOpenService] = useState(false)
110
133
  const [currentProduct, setCurrentProduct] = useState(null)
134
+ const [searchBarHeight, setSearchBarHeight] = useState(60)
111
135
 
112
136
  const isCheckoutMultiBusinessEnabled: Boolean = configs?.checkout_multi_business_enabled?.value === '1'
137
+ const isQuickAddProduct = configs?.add_product_with_one_click?.value === '1'
138
+ const openCarts = (Object.values(orderState?.carts)?.filter((cart: any) => cart?.products && cart?.products?.length && cart?.status !== 2 && cart?.valid_schedule && cart?.valid_products && cart?.valid_address && cart?.valid_maximum && cart?.valid_minimum && !cart?.wallets) || null) || []
139
+
113
140
  const currentCart: any = Object.values(orderState.carts).find((cart: any) => cart?.business?.slug === business?.slug) ?? {}
114
141
  const isOpenFiltProducts = isOpenSearchBar && !!searchValue
115
- const filtProductsHeight = Platform.OS === 'ios' ? 0 : 35
142
+ const filtProductsHeight = Platform.OS === 'ios' ? 0 : 100
116
143
  const onRedirect = (route: string, params?: any) => {
117
144
  navigation.navigate(route, params)
118
145
  }
119
-
120
- const onProductClick = (product: any) => {
121
- if (product?.type === 'service' && professionalSelected) {
122
- setCurrentProduct(product)
123
- setOpenService(true)
124
- return
146
+ const onProductClick = async (product: any) => {
147
+ if (product.extras.length === 0 && !product.inventoried && auth && isQuickAddProduct) {
148
+ const isProductAddedToCart = currentCart?.products?.find((Cproduct: any) => Cproduct.id === product.id)
149
+ const productQuantity = isProductAddedToCart?.quantity
150
+ const addCurrentProduct = {
151
+ ...product,
152
+ quantity: 1
153
+ }
154
+ const updateCurrentProduct = {
155
+ id: product.id,
156
+ code: isProductAddedToCart?.code,
157
+ quantity: productQuantity + 1
158
+ }
159
+ const cartData = currentCart?.business_id ? currentCart : { business_id: business.id }
160
+ if (isProductAddedToCart) {
161
+ await updateProduct(updateCurrentProduct, cartData, isQuickAddProduct)
162
+ } else {
163
+ await addProduct(addCurrentProduct, cartData, isQuickAddProduct)
164
+ }
165
+ } else {
166
+ const productAddedToCartLength = currentCart?.products?.reduce((productsLength: number, Cproduct: any) => { return productsLength + (Cproduct?.id === product?.id ? Cproduct?.quantity : 0) }, 0) || 0
167
+ if (product?.type === 'service' && business?.professionals?.length > 0) {
168
+ setCurrentProduct(product)
169
+ setOpenService(true)
170
+ return
171
+ }
172
+ onRedirect('ProductDetails', {
173
+ product: product,
174
+ businessSlug: business.slug,
175
+ businessId: business.id,
176
+ productAddedToCartLength
177
+ })
125
178
  }
126
- onRedirect('ProductDetails', {
127
- product: product,
128
- businessSlug: business.slug,
129
- businessId: business.id,
130
- })
131
179
  }
132
180
 
133
181
  const handleCancel = () => {
@@ -136,7 +184,7 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
136
184
  }
137
185
 
138
186
  const handleUpsellingPage = () => {
139
- if (isCheckoutMultiBusinessEnabled) {
187
+ if (isCheckoutMultiBusinessEnabled && openCarts.length > 1) {
140
188
  onRedirect('CheckoutNavigator', {
141
189
  screen: 'MultiCheckout'
142
190
  })
@@ -221,32 +269,41 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
221
269
  removeCartByReOrder()
222
270
  }, [currentCart])
223
271
 
272
+ useEffect(() => {
273
+ if (!isFocused) {
274
+ handleChangeSearch('')
275
+ setIsOpenSearchBar(false)
276
+ }
277
+ }, [isFocused])
278
+
279
+ const subtotalWithTaxes = currentCart?.taxes?.reduce((acc: any, item: any) => {
280
+ if (item?.type === 1)
281
+ return acc = acc + item?.summary?.tax
282
+ return acc = acc
283
+ }, currentCart?.subtotal)
284
+
224
285
  return (
225
286
  <>
226
- <ContainerSafeAreaView
227
- style={{ flex: 1 }}
228
- isOpenFiltProducts={isOpenFiltProducts}
229
- >
287
+ <View style={{ flex: 1 }}>
230
288
  <Animated.View style={{ position: 'relative' }}>
231
- <TopHeader isIos={Platform.OS === 'ios'}>
289
+ <TopHeader
290
+ style={{
291
+ marginTop: Platform.OS === 'ios' ? insets.top : 0
292
+ }}
293
+ onLayout={(event: any) => setSearchBarHeight(event.nativeEvent.layout.height)}
294
+ >
232
295
  {!isOpenSearchBar && (
233
296
  <>
234
- <View style={{ ...styles.headerItem, flex: 1 }}>
235
- <OButton
236
- imgLeftSrc={theme.images.general.arrow_left}
237
- imgRightSrc={null}
238
- style={styles.btnBackArrow}
239
- onClick={() => handleBackNavigation()}
240
- imgLeftStyle={{ tintColor: theme.colors.textNormal, width: 30 }}
241
- />
242
- </View>
297
+ <TopActions onPress={() => handleBackNavigation()}>
298
+ <OIcon src={theme.images.general.arrow_left} color={theme.colors.textNormal} />
299
+ </TopActions>
243
300
  {!errorQuantityProducts && (
244
301
  <View style={{ ...styles.headerItem }}>
245
302
  <TouchableOpacity
246
303
  onPress={() => setIsOpenSearchBar(true)}
247
304
  style={styles.searchIcon}
248
305
  >
249
- <OIcon src={theme.images.general.search} color={theme.colors.textNormal} width={16} />
306
+ <OIcon src={theme.images.general.search} color={theme.colors.textNormal} width={20} />
250
307
  </TouchableOpacity>
251
308
  </View>
252
309
  )}
@@ -266,14 +323,39 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
266
323
  </WrapSearchBar>
267
324
  )}
268
325
  </TopHeader>
326
+ {!hideBusinessNearCity && loading && (
327
+ <NearBusiness style={{ paddingBottom: 10 }}>
328
+ <Placeholder Animation={Fade}>
329
+ <View style={{ flexDirection: 'row' }}>
330
+ {[...Array(10).keys()].map(i => (
331
+ <View style={styles.businessSkeleton} key={i}>
332
+ <PlaceholderLine style={{ width: '100%', height: '100%' }} />
333
+ </View>
334
+ ))}
335
+ </View>
336
+ </Placeholder>
337
+ </NearBusiness>
338
+ )}
339
+ {!loading && !hideBusinessNearCity && businessState?.business?.city_id && (
340
+ <NearBusiness>
341
+ <BusinessesListing
342
+ logosLayout
343
+ propsToFetch={['id', 'logo', 'location', 'timezone', 'schedule', 'open', 'slug']}
344
+ cityId={businessState?.business?.city_id}
345
+ onBusinessClick={onBusinessClick}
346
+ actualSlug={businessState?.business?.slug}
347
+ />
348
+ </NearBusiness>
349
+ )}
269
350
  </Animated.View>
270
351
 
271
352
  {business?.categories?.length > 0 && isOpenFiltProducts && (
272
353
  <FiltProductsContainer
273
- isIos={Platform.OS === 'ios'}
274
354
  style={{
275
- height: Dimensions.get('window').height - filtProductsHeight
355
+ height: Dimensions.get('window').height - filtProductsHeight,
356
+ top: Platform.OS === 'ios' ? searchBarHeight + insets.top : searchBarHeight
276
357
  }}
358
+ contentContainerStyle={{ flexGrow: 1 }}
277
359
  >
278
360
  <View style={{ padding: 20, backgroundColor: theme.colors.white }}>
279
361
  <BusinessProductsList
@@ -301,22 +383,28 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
301
383
  setSubcategoriesSelected={setSubcategoriesSelected}
302
384
  onClickCategory={handleChangeCategory}
303
385
  handleUpdateProducts={handleUpdateProducts}
386
+ previouslyProducts={business?.previously_products}
387
+ navigation={navigation}
304
388
  isFiltMode
305
389
  />
306
390
  </View>
307
391
  </FiltProductsContainer>
308
392
  )}
309
393
  {isOpenFiltProducts && (
310
- <BackgroundGray />
394
+ <BackgroundGray isIos={Platform.OS === 'ios'} />
311
395
  )}
312
- <BusinessProductsListingContainer
313
- stickyHeaderIndices={[2]}
314
- style={styles.mainContainer}
396
+ <IOScrollView
397
+ stickyHeaderIndices={[business?.professionals?.length > 0 ? 3 : 2]}
398
+ style={{
399
+ ...styles.mainContainer,
400
+ marginBottom: currentCart?.products?.length > 0 && categoryState.products.length !== 0 ?
401
+ 50 : 0
402
+ }}
315
403
  ref={scrollViewRef}
316
- isActiveFloatingButtom={currentCart?.products?.length > 0 && categoryState.products.length !== 0}
317
404
  onScroll={handlePageScroll}
318
405
  onScrollBeginDrag={handleTouchDrag}
319
406
  scrollEventThrottle={16}
407
+ bounces={false}
320
408
  >
321
409
  <BusinessBasicInformation
322
410
  navigation={navigation}
@@ -342,27 +430,28 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
342
430
  />
343
431
  </ProfessionalFilterWrapper>
344
432
  )}
345
- <View style={{ height: 8, backgroundColor: theme.colors.backgroundGray100 }} />
346
- {!loading && business?.id && (
347
- <>
348
- {!(business?.categories?.length === 0) && (
349
- <BusinessProductsCategories
350
- categories={[{ id: null, name: t('ALL', 'All') }, { id: 'featured', name: t('FEATURED', 'Featured') }, ...business?.categories.sort((a: any, b: any) => a.rank - b.rank)]}
351
- categorySelected={categorySelected}
352
- onClickCategory={handleChangeCategory}
353
- featured={featuredProducts}
354
- openBusinessInformation={openBusinessInformation}
355
- scrollViewRef={scrollViewRef}
356
- productListLayout={productListLayout}
357
- categoriesLayout={categoriesLayout}
358
- selectedCategoryId={selectedCategoryId}
359
- lazyLoadProductsRecommended={business?.lazy_load_products_recommended}
360
- setSelectedCategoryId={setSelectedCategoryId}
361
- setCategoryClicked={setCategoryClicked}
362
-
363
- />
364
- )}
365
- </>
433
+ <View
434
+ style={{
435
+ height: 8,
436
+ backgroundColor: theme.colors.backgroundGray100,
437
+ marginTop: isChewLayout && showLogo ? 10 : 0
438
+ }}
439
+ />
440
+ {!loading && business?.id && !(business?.categories?.length === 0) && (
441
+ <BusinessProductsCategories
442
+ categories={[{ id: null, name: t('ALL', 'All') }, { id: 'featured', name: t('FEATURED', 'Featured') }, ...business?.categories.sort((a: any, b: any) => a.rank - b.rank)]}
443
+ categorySelected={categorySelected}
444
+ onClickCategory={handleChangeCategory}
445
+ featured={featuredProducts}
446
+ openBusinessInformation={openBusinessInformation}
447
+ scrollViewRef={scrollViewRef}
448
+ productListLayout={productListLayout}
449
+ categoriesLayout={categoriesLayout}
450
+ selectedCategoryId={selectedCategoryId}
451
+ lazyLoadProductsRecommended={business?.lazy_load_products_recommended}
452
+ setSelectedCategoryId={setSelectedCategoryId}
453
+ setCategoryClicked={setCategoryClicked}
454
+ />
366
455
  )}
367
456
  {!loading && business?.id && (
368
457
  <>
@@ -394,6 +483,8 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
394
483
  setSubcategoriesSelected={setSubcategoriesSelected}
395
484
  onClickCategory={handleChangeCategory}
396
485
  handleUpdateProducts={handleUpdateProducts}
486
+ navigation={navigation}
487
+ previouslyProducts={business?.previously_products}
397
488
  />
398
489
  </WrapContent>
399
490
  </>
@@ -416,28 +507,32 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
416
507
  isBusinessLoading={loading}
417
508
  errorQuantityProducts={errorQuantityProducts}
418
509
  handleUpdateProducts={handleUpdateProducts}
510
+ navigation={navigation}
419
511
  />
420
512
  </WrapContent>
421
513
  </>
422
514
  )}
423
- </BusinessProductsListingContainer>
515
+ </IOScrollView>
424
516
  {!loading && auth && currentCart?.products?.length > 0 && categoryState.products.length !== 0 && (
425
- <FloatingButton
426
- btnText={
427
- openUpselling
428
- ? t('LOADING', 'Loading')
429
- : currentCart?.subtotal >= currentCart?.minimum
430
- ? t('VIEW_ORDER', 'View Order')
431
- : `${t('MINIMUN_SUBTOTAL_ORDER', 'Minimum subtotal order:')} ${parsePrice(currentCart?.minimum)}`
432
- }
433
- isSecondaryBtn={currentCart?.subtotal < currentCart?.minimum || openUpselling}
434
- btnLeftValueShow={currentCart?.subtotal >= currentCart?.minimum && currentCart?.products?.length > 0}
435
- btnRightValueShow={currentCart?.subtotal >= currentCart?.minimum && currentCart?.products?.length > 0}
436
- btnLeftValue={currentCart?.products.reduce((prev: number, product: any) => prev + product.quantity, 0)}
437
- btnRightValue={parsePrice(currentCart?.total)}
438
- disabled={currentCart?.subtotal < currentCart?.minimum || openUpselling}
439
- handleClick={() => setOpenUpselling(true)}
440
- />
517
+ <View style={{ marginBottom: Platform.OS === 'ios' ? 20 : 0 }}>
518
+ <FloatingButton
519
+ btnText={
520
+ openUpselling
521
+ ? t('LOADING', 'Loading')
522
+ : subtotalWithTaxes >= currentCart?.minimum
523
+ ? t('VIEW_ORDER', 'View Order')
524
+ : `${t('MINIMUN_SUBTOTAL_ORDER', 'Minimum subtotal order:')} ${parsePrice(currentCart?.minimum)}`
525
+ }
526
+ isSecondaryBtn={subtotalWithTaxes < currentCart?.minimum || openUpselling}
527
+ btnLeftValueShow={subtotalWithTaxes >= currentCart?.minimum && currentCart?.products?.length > 0}
528
+ btnRightValueShow={subtotalWithTaxes >= currentCart?.minimum && currentCart?.products?.length > 0}
529
+ btnLeftValue={currentCart?.products.reduce((prev: number, product: any) => prev + product.quantity, 0)}
530
+ btnRightValue={parsePrice(currentCart?.total)}
531
+ disabled={subtotalWithTaxes < currentCart?.minimum || openUpselling}
532
+ hideButton={isCheckoutMultiBusinessEnabled}
533
+ handleClick={() => setOpenUpselling(true)}
534
+ />
535
+ </View>
441
536
  )}
442
537
  {openUpselling && (
443
538
  <UpsellingRedirect
@@ -461,7 +556,7 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
461
556
  onAccept={() => setAlertState({ open: false, content: [] })}
462
557
  onClose={() => setAlertState({ open: false, content: [] })}
463
558
  />
464
- </ContainerSafeAreaView>
559
+ </View>
465
560
  <OModal
466
561
  open={openService}
467
562
  onClose={() => setOpenService(false)}
@@ -475,6 +570,7 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
475
570
  professionalList={business?.professionals}
476
571
  professionalSelected={professionalSelected}
477
572
  handleChangeProfessional={handleChangeProfessionalSelected}
573
+ handleUpdateProfessionals={handleUpdateProfessionals}
478
574
  onSave={() => setOpenService(false)}
479
575
  onClose={() => setOpenService(false)}
480
576
  />
@@ -486,6 +582,7 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
486
582
  export const BusinessProductsListing = (props: BusinessProductsListingParams) => {
487
583
  const businessProductslistingProps = {
488
584
  ...props,
585
+ isForceSearch: Platform.OS === 'ios',
489
586
  UIComponent: BusinessProductsListingUI
490
587
  }
491
588
  return (