ordering-ui-react-native 0.15.25 → 0.15.27-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 (165) hide show
  1. package/package.json +3 -2
  2. package/src/DeliveryApp.tsx +43 -1
  3. package/src/components/BusinessController/index.tsx +8 -2
  4. package/src/components/BusinessTypeFilter/index.tsx +4 -1
  5. package/src/components/BusinessesListing/index.tsx +1 -1
  6. package/src/components/Checkout/index.tsx +23 -3
  7. package/src/components/DriverTips/index.tsx +11 -6
  8. package/src/components/LanguageSelector/index.tsx +7 -2
  9. package/src/components/OrderDetails/index.tsx +2 -2
  10. package/src/components/PaymentOptions/index.tsx +9 -16
  11. package/src/components/PaymentOptionsWebView/index.tsx +123 -124
  12. package/src/components/SingleProductCard/index.tsx +16 -4
  13. package/src/components/StripeElementsForm/index.tsx +27 -48
  14. package/src/components/UpsellingProducts/index.tsx +1 -1
  15. package/src/components/UserProfileForm/index.tsx +63 -6
  16. package/src/components/UserProfileForm/styles.tsx +8 -0
  17. package/src/components/VerifyPhone/styles.tsx +1 -2
  18. package/src/components/shared/OModal.tsx +1 -1
  19. package/src/config.json +0 -2
  20. package/src/hooks/useCountdownTimer.tsx +26 -0
  21. package/src/navigators/HomeNavigator.tsx +6 -0
  22. package/src/pages/BusinessProductsList.tsx +1 -0
  23. package/src/pages/BusinessesListing.tsx +1 -1
  24. package/src/pages/Checkout.tsx +1 -1
  25. package/src/pages/Sessions.tsx +22 -0
  26. package/src/types/index.tsx +5 -11
  27. package/src/utils/index.tsx +68 -1
  28. package/themes/business/index.tsx +2 -0
  29. package/themes/business/src/components/AcceptOrRejectOrder/index.tsx +103 -15
  30. package/themes/business/src/components/AcceptOrRejectOrder/styles.tsx +6 -0
  31. package/themes/business/src/components/Chat/index.tsx +38 -86
  32. package/themes/business/src/components/Home/index.tsx +128 -55
  33. package/themes/business/src/components/Home/styles.tsx +8 -1
  34. package/themes/business/src/components/LoginForm/index.tsx +89 -2
  35. package/themes/business/src/components/LoginForm/styles.tsx +6 -0
  36. package/themes/business/src/components/LogoutButton/index.tsx +1 -1
  37. package/themes/business/src/components/NewOrderNotification/index.tsx +79 -105
  38. package/themes/business/src/components/OrderDetails/Business.tsx +2 -1
  39. package/themes/business/src/components/OrderDetails/Delivery.tsx +32 -15
  40. package/themes/business/src/components/OrderDetails/OrderContentComponent.tsx +151 -89
  41. package/themes/business/src/components/OrderDetails/OrderHeaderComponent.tsx +91 -17
  42. package/themes/business/src/components/OrderDetails/styles.tsx +7 -0
  43. package/themes/business/src/components/OrdersListManager/index.tsx +874 -0
  44. package/themes/business/src/components/OrdersListManager/styles.tsx +123 -0
  45. package/themes/business/src/components/OrdersListManager/utils.tsx +216 -0
  46. package/themes/business/src/components/OrdersOption/index.tsx +58 -51
  47. package/themes/business/src/components/PreviousOrders/index.tsx +75 -22
  48. package/themes/business/src/components/shared/OModal.tsx +1 -1
  49. package/themes/business/src/types/index.tsx +5 -1
  50. package/themes/doordash/src/components/BusinessesListing/index.tsx +1 -1
  51. package/themes/doordash/src/components/LoginForm/index.tsx +1 -2
  52. package/themes/instacart/src/components/BusinessesListing/index.tsx +1 -1
  53. package/themes/kiosk/src/components/Cart/index.tsx +98 -24
  54. package/themes/kiosk/src/components/Cart/styles.tsx +6 -0
  55. package/themes/kiosk/src/components/CartBottomSheet/index.tsx +1 -1
  56. package/themes/kiosk/src/components/CartBottomSheet/styles.tsx +1 -1
  57. package/themes/kiosk/src/components/CartContent/index.tsx +13 -3
  58. package/themes/kiosk/src/components/CartItem/index.tsx +20 -8
  59. package/themes/kiosk/src/components/CustomerName/index.tsx +89 -88
  60. package/themes/kiosk/src/components/Intro/index.tsx +13 -13
  61. package/themes/kiosk/src/components/NavBar/index.tsx +14 -14
  62. package/themes/kiosk/src/components/OptionCard/index.tsx +1 -1
  63. package/themes/kiosk/src/components/OrderDetails/index.tsx +136 -41
  64. package/themes/kiosk/src/components/OrderDetails/styles.tsx +5 -0
  65. package/themes/kiosk/src/components/OrderSummary/index.tsx +1 -1
  66. package/themes/kiosk/src/components/OrderTypeCardSelector/index.tsx +10 -12
  67. package/themes/kiosk/src/components/ProductForm/index.tsx +174 -125
  68. package/themes/kiosk/src/components/ProductForm/styles.tsx +1 -1
  69. package/themes/kiosk/src/components/ProductOption/index.tsx +1 -0
  70. package/themes/kiosk/src/components/ProductOption/styles.tsx +1 -0
  71. package/themes/kiosk/src/components/UpsellingProducts/index.tsx +48 -34
  72. package/themes/kiosk/src/components/shared/OButton.tsx +5 -18
  73. package/themes/kiosk/src/types/index.d.ts +2 -0
  74. package/themes/original/index.tsx +178 -1
  75. package/themes/original/src/components/AddressForm/index.tsx +15 -10
  76. package/themes/original/src/components/AddressList/index.tsx +56 -18
  77. package/themes/original/src/components/AppleLogin/index.tsx +117 -78
  78. package/themes/original/src/components/BusinessBasicInformation/index.tsx +96 -45
  79. package/themes/original/src/components/BusinessBasicInformation/styles.tsx +28 -1
  80. package/themes/original/src/components/BusinessController/index.tsx +52 -22
  81. package/themes/original/src/components/BusinessController/styles.tsx +22 -0
  82. package/themes/original/src/components/BusinessFeaturedController/index.tsx +20 -1
  83. package/themes/original/src/components/BusinessFeaturedController/styles.tsx +23 -0
  84. package/themes/original/src/components/BusinessListingSearch/index.tsx +121 -7
  85. package/themes/original/src/components/BusinessListingSearch/styles.tsx +14 -1
  86. package/themes/original/src/components/BusinessMenuList/index.tsx +11 -4
  87. package/themes/original/src/components/BusinessPreorder/index.tsx +142 -122
  88. package/themes/original/src/components/BusinessProductsCategories/index.tsx +9 -7
  89. package/themes/original/src/components/BusinessProductsList/index.tsx +127 -20
  90. package/themes/original/src/components/BusinessProductsList/styles.tsx +29 -2
  91. package/themes/original/src/components/BusinessProductsListing/index.tsx +118 -37
  92. package/themes/original/src/components/BusinessProductsListing/styles.tsx +22 -0
  93. package/themes/original/src/components/BusinessReviews/index.tsx +4 -25
  94. package/themes/original/src/components/BusinessTypeFilter/index.tsx +1 -2
  95. package/themes/original/src/components/BusinessesListing/index.tsx +53 -60
  96. package/themes/original/src/components/Cart/index.tsx +21 -17
  97. package/themes/original/src/components/CartContent/index.tsx +2 -2
  98. package/themes/original/src/components/Checkout/index.tsx +58 -45
  99. package/themes/original/src/components/DriverTips/index.tsx +17 -12
  100. package/themes/original/src/components/ForgotPasswordForm/index.tsx +84 -4
  101. package/themes/original/src/components/GoogleMap/index.tsx +1 -0
  102. package/themes/original/src/components/Help/index.tsx +21 -4
  103. package/themes/original/src/components/HighestRatedBusinesses/index.tsx +97 -89
  104. package/themes/original/src/components/Home/index.tsx +1 -1
  105. package/themes/original/src/components/LastOrders/index.tsx +12 -1
  106. package/themes/original/src/components/LoginForm/Otp/index.tsx +90 -0
  107. package/themes/original/src/components/LoginForm/Otp/styles.tsx +7 -0
  108. package/themes/original/src/components/LoginForm/index.tsx +389 -156
  109. package/themes/original/src/components/LoginForm/styles.tsx +7 -4
  110. package/themes/original/src/components/LogoutButton/index.tsx +7 -1
  111. package/themes/original/src/components/MessageListing/index.tsx +10 -1
  112. package/themes/original/src/components/Messages/index.tsx +34 -25
  113. package/themes/original/src/components/Messages/styles.tsx +1 -3
  114. package/themes/original/src/components/MomentOption/index.tsx +10 -1
  115. package/themes/original/src/components/MomentOption/styles.tsx +1 -1
  116. package/themes/original/src/components/OrderDetails/index.tsx +56 -33
  117. package/themes/original/src/components/OrderDetails/styles.tsx +1 -2
  118. package/themes/original/src/components/OrderProgress/index.tsx +4 -4
  119. package/themes/original/src/components/OrderProgress/styles.tsx +1 -0
  120. package/themes/original/src/components/OrderSummary/index.tsx +3 -3
  121. package/themes/original/src/components/OrderTypeSelector/index.tsx +4 -2
  122. package/themes/original/src/components/OrdersOption/index.tsx +55 -58
  123. package/themes/original/src/components/OrdersOption/styles.tsx +0 -6
  124. package/themes/original/src/components/PaymentOptionCash/index.tsx +2 -2
  125. package/themes/original/src/components/PaymentOptionWallet/index.tsx +22 -24
  126. package/themes/original/src/components/PaymentOptionWallet/styles.tsx +1 -1
  127. package/themes/original/src/components/PaymentOptions/index.tsx +9 -19
  128. package/themes/original/src/components/PhoneInputNumber/index.tsx +1 -1
  129. package/themes/original/src/components/PreviousOrders/index.tsx +20 -14
  130. package/themes/original/src/components/ProductForm/index.tsx +76 -61
  131. package/themes/original/src/components/ProductForm/styles.tsx +2 -2
  132. package/themes/original/src/components/ProductItemAccordion/index.tsx +2 -2
  133. package/themes/original/src/components/ProductOptionSubOption/index.tsx +18 -12
  134. package/themes/original/src/components/Promotions/index.tsx +250 -0
  135. package/themes/original/src/components/Promotions/styles.tsx +60 -0
  136. package/themes/original/src/components/ReviewOrder/index.tsx +10 -9
  137. package/themes/original/src/components/ReviewProducts/index.tsx +1 -1
  138. package/themes/original/src/components/SearchBar/index.tsx +4 -1
  139. package/themes/original/src/components/Sessions/index.tsx +160 -0
  140. package/themes/original/src/components/Sessions/styles.tsx +15 -0
  141. package/themes/original/src/components/SingleProductCard/index.tsx +47 -21
  142. package/themes/original/src/components/SingleProductCard/styles.tsx +28 -1
  143. package/themes/original/src/components/StripeElementsForm/index.tsx +55 -72
  144. package/themes/original/src/components/TaxInformation/index.tsx +10 -4
  145. package/themes/original/src/components/UpsellingProducts/index.tsx +87 -75
  146. package/themes/original/src/components/UserDetails/index.tsx +4 -95
  147. package/themes/original/src/components/UserFormDetails/index.tsx +34 -24
  148. package/themes/original/src/components/UserProfile/index.tsx +62 -14
  149. package/themes/original/src/components/UserProfileForm/index.tsx +20 -18
  150. package/themes/original/src/components/UserVerification/index.tsx +178 -192
  151. package/themes/original/src/components/VerifyPhone/index.tsx +10 -7
  152. package/themes/original/src/components/VerifyPhone/styles.tsx +2 -1
  153. package/themes/original/src/components/Wallets/index.tsx +76 -9
  154. package/themes/original/src/components/Wallets/styles.tsx +21 -0
  155. package/themes/original/src/components/shared/HeaderTitle.tsx +21 -0
  156. package/themes/original/src/components/shared/OModal.tsx +1 -1
  157. package/themes/original/src/components/shared/index.tsx +2 -0
  158. package/themes/original/src/config/constants.tsx +6 -6
  159. package/themes/original/src/types/index.tsx +68 -6
  160. package/themes/original/src/utils/index.tsx +28 -2
  161. package/themes/single-business/src/components/AddressList/index.tsx +1 -1
  162. package/themes/single-business/src/components/OrderTypeSelector/index.tsx +6 -6
  163. package/themes/single-business/src/components/UserProfile/index.tsx +1 -1
  164. package/themes/uber-eats/src/components/BusinessesListing/index.tsx +1 -1
  165. package/src/components/StripeMethodForm/index.tsx +0 -168
@@ -4,11 +4,12 @@ import { SingleProductCard } from '../SingleProductCard';
4
4
  import { NotFoundSource } from '../NotFoundSource';
5
5
  import { BusinessProductsListParams } from '../../types';
6
6
  import { OButton, OIcon, OModal, OText } from '../shared';
7
- import { ProductsContainer, ErrorMessage, WrapperNotFound } from './styles';
7
+ import { ProductsContainer, ErrorMessage, WrapperNotFound, RibbonBox, SubCategoriesContainer, ContainerButton, HeaderWrapper } from './styles';
8
8
  import { Fade, Placeholder, PlaceholderLine } from 'rn-placeholder';
9
9
  import { View, ScrollView } from 'react-native';
10
10
  import { StyleSheet } from 'react-native';
11
11
  import { useTheme } from 'styled-components/native';
12
+ import { shape } from '../../utils'
12
13
 
13
14
  const BusinessProductsListUI = (props: BusinessProductsListParams) => {
14
15
  const {
@@ -27,7 +28,12 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
27
28
  handleCancelSearch,
28
29
  categoriesLayout,
29
30
  setCategoriesLayout,
30
- currentCart
31
+ currentCart,
32
+ setSubcategoriesSelected,
33
+ subcategoriesSelected,
34
+ onClickCategory,
35
+ lazyLoadProductsRecommended,
36
+ isFiltMode
31
37
  } = props;
32
38
 
33
39
  const [, t] = useLanguage();
@@ -43,20 +49,85 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
43
49
  setCategoriesLayout(_categoriesLayout)
44
50
  }
45
51
 
46
- return (
47
- <ProductsContainer>
48
- {category.id &&
49
- categoryState.products?.sort((a: any, b: any) => a.rank - b.rank).map((product: any) => (
50
- <SingleProductCard
51
- key={'prod_' + product.id}
52
- isSoldOut={product.inventoried && !product.quantity}
53
- product={product}
54
- businessId={businessId}
55
- onProductClick={() => onProductClick(product)}
56
- productAddedToCartLength={currentCart?.products?.reduce((productsLength: number, Cproduct: any) => { return productsLength + (Cproduct?.id === product?.id ? Cproduct?.quantity : 0) }, 0)}
52
+ const onClickSubcategory = (subCategory: any, parentCategory: any) => {
53
+ if (parentCategory && lazyLoadProductsRecommended) {
54
+ onClickCategory(parentCategory)
55
+ }
56
+ if (!subCategory) {
57
+ setSubcategoriesSelected?.(subcategoriesSelected.filter((_subcategory: any) => _subcategory?.parent_category_id !== parentCategory?.id))
58
+ return
59
+ }
60
+ const categoryFounded = subcategoriesSelected.find((_subcategory: any) => subCategory?.id === _subcategory?.id)
61
+ if (categoryFounded) {
62
+ setSubcategoriesSelected?.(subcategoriesSelected.filter((_subcategory: any) => subCategory?.id !== _subcategory?.id))
63
+ } else {
64
+ setSubcategoriesSelected?.([...subcategoriesSelected, subCategory])
65
+ }
66
+ }
67
+
68
+ const SubcategoriesComponent = ({ category }: any) => {
69
+ const allsubcategorySelected = !subcategoriesSelected?.some((subcategory: any) => category?.id === subcategory?.parent_category_id)
70
+
71
+ return (
72
+ <SubCategoriesContainer>
73
+ <ContainerButton
74
+ isSelected={allsubcategorySelected}
75
+ >
76
+ <OButton
77
+ onClick={() => onClickSubcategory(null, category)}
78
+ bgColor={allsubcategorySelected ? theme.colors.primary : theme.colors.backgroundGray}
79
+ text={`${t('ALL', 'All')} ${allsubcategorySelected ? 'X' : ''}`}
80
+ style={bpStyles.categoryButtonStyle}
81
+ textStyle={{ color: allsubcategorySelected ? theme.colors.white : theme.colors.textNormal, fontSize: 12 }}
57
82
  />
58
- ))}
83
+ </ContainerButton>
84
+ {category?.subcategories?.map((subcategory: any) => {
85
+ const isSubcategorySelected = subcategoriesSelected?.find((_subcategory: any) => _subcategory?.id === subcategory?.id)
86
+ return (
87
+ <ContainerButton
88
+ key={subcategory?.id}
89
+ isSelected={isSubcategorySelected}
90
+ >
91
+ <OButton
92
+ onClick={() => onClickSubcategory(subcategory, category)}
93
+ bgColor={isSubcategorySelected ? theme.colors.primary : theme.colors.backgroundGray}
94
+ text={`${subcategory?.name} ${isSubcategorySelected ? 'X' : ''}`}
95
+ style={bpStyles.categoryButtonStyle}
96
+ textStyle={{ color: isSubcategorySelected ? theme.colors.white : theme.colors.textNormal, fontSize: 12 }}
97
+ />
98
+ </ContainerButton>
99
+ )
100
+ }
101
+ )}
102
+ </SubCategoriesContainer>
103
+ )
104
+ }
59
105
 
106
+
107
+ return (
108
+ <ProductsContainer renderToHardwareTextureAndroid={categoryState.loading || isBusinessLoading}>
109
+ <HeaderWrapper>
110
+ {category?.subcategories?.length > 0 && (
111
+ <SubcategoriesComponent category={category} />
112
+ )}
113
+ </HeaderWrapper>
114
+ {category.id &&
115
+ categoryState.products
116
+ ?.filter((product: any) =>
117
+ !subcategoriesSelected.find((subcategory: any) => subcategory?.parent_category_id === category?.id) ||
118
+ subcategoriesSelected?.some((subcategory: any) => subcategory.id === product?.category_id))
119
+ ?.sort((a: any, b: any) => a.rank - b.rank)
120
+ ?.map((product: any, i : number) => (
121
+ <SingleProductCard
122
+ key={'prod_' + product.id + `_${i}`}
123
+ isSoldOut={product.inventoried && !product.quantity}
124
+ product={product}
125
+ businessId={businessId}
126
+ onProductClick={() => onProductClick(product)}
127
+ productAddedToCartLength={currentCart?.products?.reduce((productsLength: number, Cproduct: any) => { return productsLength + (Cproduct?.id === product?.id ? Cproduct?.quantity : 0) }, 0)}
128
+ />
129
+ ))
130
+ }
60
131
  {!category.id &&
61
132
  featured &&
62
133
  categoryState?.products?.find((product: any) => product.featured) && (
@@ -71,7 +142,7 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
71
142
  (product: any, i: any) =>
72
143
  product.featured && (
73
144
  <SingleProductCard
74
- key={i}
145
+ key={'feat_' + product.id + `_${i}`}
75
146
  isSoldOut={product.inventoried && !product.quantity}
76
147
  product={product}
77
148
  businessId={businessId}
@@ -85,9 +156,14 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
85
156
  )}
86
157
 
87
158
  {!category?.id && categories.filter(category => category?.id !== null).map((category, i, _categories) => {
88
- const products = !isUseParentCategory
159
+ const _products = !isUseParentCategory
89
160
  ? categoryState?.products?.filter((product: any) => product?.category_id === category?.id) ?? []
90
161
  : categoryState?.products?.filter((product: any) => category?.children?.some((cat: any) => cat.category_id === product?.category_id)) ?? []
162
+ const products = subcategoriesSelected?.length > 0
163
+ ? _products?.filter((product: any) =>
164
+ !subcategoriesSelected.find((subcategory: any) => subcategory?.parent_category_id === category?.id) ||
165
+ subcategoriesSelected?.some((subcategory: any) => subcategory.id === product?.category_id))
166
+ : _products
91
167
 
92
168
  const shortCategoryDescription = category?.description?.length > 80 ? `${category?.description?.substring(0, 80)}...` : category?.description
93
169
 
@@ -110,10 +186,28 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
110
186
  <OText size={16} weight="600">
111
187
  {category.name}
112
188
  </OText>
189
+ {category?.ribbon?.enabled && (
190
+ <RibbonBox
191
+ bgColor={category?.ribbon?.color}
192
+ isRoundRect={category?.ribbon?.shape === shape?.rectangleRound}
193
+ isCapsule={category?.ribbon?.shape === shape?.capsuleShape}
194
+ >
195
+ <OText
196
+ size={10}
197
+ weight={'400'}
198
+ color={theme.colors.white}
199
+ numberOfLines={2}
200
+ ellipsizeMode='tail'
201
+ lineHeight={13}
202
+ >
203
+ {category?.ribbon?.text}
204
+ </OText>
205
+ </RibbonBox>
206
+ )}
113
207
  </View>
114
208
  {!!category?.description && (
115
209
  <View style={{ position: 'relative' }}>
116
- <OText size={12} weight={'500'} mBottom={5}>
210
+ <OText size={12} weight={'500'} mBottom={10} color='#909BA9'>
117
211
  {shortCategoryDescription}
118
212
  {category?.description?.length > 80 && (
119
213
  <OButton
@@ -133,6 +227,9 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
133
227
  </OText>
134
228
  </View>
135
229
  )}
230
+ {category?.subcategories?.length > 0 && !isFiltMode && (
231
+ <SubcategoriesComponent category={category} />
232
+ )}
136
233
  <>
137
234
  {products.sort((a: any, b: any) => a.rank - b.rank).map((product: any, i: any) => (
138
235
  <SingleProductCard
@@ -176,6 +273,7 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
176
273
  !isBusinessLoading &&
177
274
  categoryState.products.length === 0 &&
178
275
  !errors &&
276
+ !isFiltMode &&
179
277
  !(
180
278
  (searchValue && errorQuantityProducts) ||
181
279
  (!searchValue && !errorQuantityProducts)
@@ -217,9 +315,9 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
217
315
  ))}
218
316
  <OModal
219
317
  open={!!openDescription}
220
- title={openDescription?.name}
221
318
  onClose={() => setOpenDescription(null)}
222
319
  >
320
+ <OText size={20} style={{paddingLeft: 70, paddingRight: 20, bottom: 25}}>{openDescription?.name}</OText>
223
321
  <ScrollView style={{ padding: 20 }}>
224
322
  {!!openDescription?.image && (
225
323
  <OIcon
@@ -229,7 +327,7 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
229
327
  style={{ borderRadius: 7.6 }}
230
328
  />
231
329
  )}
232
- <OText>{openDescription?.description}</OText>
330
+ <OText mBottom={60}>{openDescription?.description}</OText>
233
331
  </ScrollView>
234
332
  </OModal>
235
333
  </ProductsContainer>
@@ -237,7 +335,7 @@ const BusinessProductsListUI = (props: BusinessProductsListParams) => {
237
335
  };
238
336
 
239
337
  const bpStyles = StyleSheet.create({
240
- catWrap: { flexDirection: 'row', alignItems: 'center', height: 41, marginBottom: 19 },
338
+ catWrap: { flexDirection: 'row', alignItems: 'center', marginBottom: 19 },
241
339
  catIcon: {
242
340
  borderRadius: 7.6,
243
341
  shadowColor: '#000000',
@@ -246,6 +344,15 @@ const bpStyles = StyleSheet.create({
246
344
  shadowRadius: 1,
247
345
  marginEnd: 13,
248
346
  },
347
+ categoryButtonStyle: {
348
+ borderWidth: 0,
349
+ marginLeft: 5,
350
+ marginRight: 5,
351
+ marginBottom: 10,
352
+ height: 35,
353
+ paddingLeft: 3,
354
+ paddingRight: 3,
355
+ }
249
356
  });
250
357
 
251
358
  export const BusinessProductsList = (props: BusinessProductsListParams) => {
@@ -1,4 +1,4 @@
1
- import styled from 'styled-components/native'
1
+ import styled, { css } from 'styled-components/native'
2
2
 
3
3
  export const ProductsContainer = styled.View`
4
4
  `
@@ -11,4 +11,31 @@ export const ErrorMessage = styled.View`
11
11
 
12
12
  export const WrapperNotFound = styled.View`
13
13
  height: 500px;
14
- `
14
+ `
15
+
16
+ export const RibbonBox = styled.View`
17
+ margin-left: 5px;
18
+ background-color: ${(props: any) => props.theme.colors.primary};
19
+ padding: 2px 8px;
20
+ max-width: 180px;
21
+ ${(props: any) => props.bgColor && css`
22
+ background-color: ${props.bgColor};
23
+ `}
24
+ ${(props: any) => props.isRoundRect && css`
25
+ border-radius: 7.6px;
26
+ `}
27
+ ${(props: any) => props.isCapsule && css`
28
+ border-radius: 50px;
29
+ `}
30
+ `
31
+
32
+ export const SubCategoriesContainer = styled.View`
33
+ flex-direction: row;
34
+ flex-wrap: wrap;
35
+ margin-bottom: 10px;
36
+ `
37
+
38
+ export const ContainerButton = styled.View`
39
+ `
40
+
41
+ export const HeaderWrapper = styled.View``
@@ -1,5 +1,5 @@
1
1
  import React, { useCallback, useEffect, useRef, useState } from 'react'
2
- import { View, TouchableOpacity, StyleSheet, SafeAreaView } from 'react-native'
2
+ import { View, TouchableOpacity, StyleSheet, SafeAreaView, Dimensions, Platform, KeyboardAvoidingViewBase, KeyboardAvoidingView } from 'react-native'
3
3
  import { useTheme } from 'styled-components/native';
4
4
  import {
5
5
  BusinessAndProductList,
@@ -12,22 +12,27 @@ import {
12
12
  useConfig
13
13
  } from 'ordering-components/native'
14
14
  import { OButton, OIcon, OModal, OText } from '../shared'
15
+ import Alert from '../../providers/AlertProvider'
15
16
  import { BusinessBasicInformation } from '../BusinessBasicInformation'
16
17
  import { SearchBar } from '../SearchBar'
17
18
  import { BusinessProductsCategories } from '../BusinessProductsCategories'
18
19
  import { BusinessProductsList } from '../BusinessProductsList'
19
20
  import { BusinessProductsListingParams } from '../../types'
21
+ import { _retrieveStoreData, _removeStoreData } from '../../providers/StoreUtil';
20
22
  import {
21
23
  TopHeader,
22
24
  WrapSearchBar,
23
25
  WrapContent,
24
- BusinessProductsListingContainer
26
+ BusinessProductsListingContainer,
27
+ FiltProductsContainer,
28
+ ContainerSafeAreaView,
29
+ BackgroundGray
25
30
  } from './styles'
26
31
  import { FloatingButton } from '../FloatingButton'
27
32
  import { UpsellingRedirect } from './UpsellingRedirect'
28
33
  import Animated from 'react-native-reanimated'
29
34
 
30
- const PIXELS_TO_SCROLL = 1000
35
+ const PIXELS_TO_SCROLL = 2000
31
36
 
32
37
  const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
33
38
  const {
@@ -44,13 +49,16 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
44
49
  errorQuantityProducts,
45
50
  header,
46
51
  logo,
52
+ alertState,
53
+ setAlertState,
54
+ multiRemoveProducts,
47
55
  getNextProducts,
48
56
  } = props
49
57
 
50
58
  const theme = useTheme();
51
59
  const [, t] = useLanguage()
52
60
  const [{ auth }] = useSession()
53
- const [orderState] = useOrder()
61
+ const [orderState, { clearCart }] = useOrder()
54
62
  const [{ parsePrice }] = useUtils()
55
63
  const [, { showToast }] = useToast()
56
64
  const [{ configs }] = useConfig()
@@ -72,6 +80,7 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
72
80
  borderWidth: 0,
73
81
  backgroundColor: theme.colors.clear,
74
82
  shadowColor: theme.colors.clear,
83
+ padding: 40,
75
84
  },
76
85
  searchIcon: {
77
86
  borderWidth: 0,
@@ -90,32 +99,21 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
90
99
  const [categoriesLayout, setCategoriesLayout] = useState<any>({})
91
100
  const [productListLayout, setProductListLayout] = useState<any>(null)
92
101
  const [isCategoryClicked, setCategoryClicked] = useState(false)
102
+ const [subcategoriesSelected, setSubcategoriesSelected] = useState([])
93
103
 
94
104
  const currentCart: any = Object.values(orderState.carts).find((cart: any) => cart?.business?.slug === business?.slug) ?? {}
95
-
105
+ const isOpenFiltProducts = isOpenSearchBar && !!searchValue
106
+ const filtProductsHeight = Platform.OS === 'ios' ? 0 : 35
96
107
  const onRedirect = (route: string, params?: any) => {
97
108
  navigation.navigate(route, params)
98
109
  }
99
110
 
100
111
  const onProductClick = (product: any) => {
101
- const cartProduct = currentCart?.products?.find((cproduct: any) => cproduct?.id === product?.id)
102
- if (cartProduct) {
103
- onRedirect('ProductDetails', {
104
- businessId: business.id,
105
- isCartProduct: true,
106
- productCart: cartProduct,
107
- businessSlug: business?.slug,
108
- categoryId: cartProduct?.category_id,
109
- productId: cartProduct?.id,
110
- })
111
- } else {
112
- onRedirect('ProductDetails', {
113
- product: product,
114
- businessSlug: business.slug,
115
- businessId: business.id,
116
- })
117
- }
118
-
112
+ onRedirect('ProductDetails', {
113
+ product: product,
114
+ businessSlug: business.slug,
115
+ businessId: business.id,
116
+ })
119
117
  }
120
118
 
121
119
  const handleCancel = () => {
@@ -169,18 +167,47 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
169
167
 
170
168
  const handleTouchDrag = useCallback(() => {
171
169
  setCategoryClicked(false);
172
- }, []);
173
-
170
+ }, []);
171
+
174
172
  const handleBackNavigation = () => {
175
173
  navigation?.canGoBack() ? navigation.goBack() : navigation.navigate('BottomTab')
176
174
  }
177
175
 
176
+ const adjustBusiness = async (adjustBusinessId: number) => {
177
+ const _carts = orderState?.carts?.[adjustBusinessId]
178
+ const products = _carts?.products
179
+ const unavailableProducts = products.filter((product: any) => product.valid !== true)
180
+ const alreadyRemoved = await _retrieveStoreData('already-removed')
181
+ _removeStoreData('already-removed')
182
+ if (unavailableProducts.length > 0) {
183
+ multiRemoveProducts && await multiRemoveProducts(unavailableProducts, _carts)
184
+ return
185
+ }
186
+
187
+ if (alreadyRemoved === 'removed') {
188
+ setAlertState({ open: true, content: [t('NOT_AVAILABLE_PRODUCT', 'This product is not available.')] })
189
+ }
190
+ }
191
+
192
+ const removeCartByReOrder = async () => {
193
+ const adjustBusinessId = await _retrieveStoreData('adjust-cart-products')
194
+ if (currentCart && adjustBusinessId) {
195
+ _removeStoreData('adjust-cart-products')
196
+ adjustBusiness(adjustBusinessId)
197
+ }
198
+ }
199
+
200
+ useEffect(() => {
201
+ removeCartByReOrder()
202
+ }, [currentCart])
203
+
178
204
  return (
179
- <SafeAreaView
205
+ <ContainerSafeAreaView
180
206
  style={{ flex: 1 }}
207
+ isOpenFiltProducts={isOpenFiltProducts}
181
208
  >
182
209
  <Animated.View style={{ position: 'relative' }}>
183
- <TopHeader>
210
+ <TopHeader isIos={Platform.OS === 'ios'}>
184
211
  {!isOpenSearchBar && (
185
212
  <>
186
213
  <View style={{ ...styles.headerItem, flex: 1 }}>
@@ -218,6 +245,46 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
218
245
  )}
219
246
  </TopHeader>
220
247
  </Animated.View>
248
+
249
+ {business?.categories?.length > 0 && isOpenFiltProducts && (
250
+ <FiltProductsContainer
251
+ style={{
252
+ height: Dimensions.get('window').height - filtProductsHeight
253
+ }}
254
+ >
255
+ <View style={{ padding: 20, backgroundColor: theme.colors.white }}>
256
+ <BusinessProductsList
257
+ categories={[
258
+ { id: null, name: t('ALL', 'All') },
259
+ { id: 'featured', name: t('FEATURED', 'Featured') },
260
+ ...business?.categories.sort((a: any, b: any) => a.rank - b.rank)
261
+ ]}
262
+ category={categorySelected}
263
+ categoryState={categoryState}
264
+ businessId={business.id}
265
+ errors={errors}
266
+ onProductClick={onProductClick}
267
+ handleSearchRedirect={handleSearchRedirect}
268
+ featured={featuredProducts}
269
+ searchValue={searchValue}
270
+ handleClearSearch={handleChangeSearch}
271
+ errorQuantityProducts={errorQuantityProducts}
272
+ handleCancelSearch={handleCancel}
273
+ categoriesLayout={categoriesLayout}
274
+ subcategoriesSelected={subcategoriesSelected}
275
+ lazyLoadProductsRecommended={business?.lazy_load_products_recommended}
276
+ setCategoriesLayout={setCategoriesLayout}
277
+ currentCart={currentCart}
278
+ setSubcategoriesSelected={setSubcategoriesSelected}
279
+ onClickCategory={handleChangeCategory}
280
+ isFiltMode
281
+ />
282
+ </View>
283
+ </FiltProductsContainer>
284
+ )}
285
+ {isOpenFiltProducts && (
286
+ <BackgroundGray />
287
+ )}
221
288
  <BusinessProductsListingContainer
222
289
  stickyHeaderIndices={[2]}
223
290
  style={styles.mainContainer}
@@ -251,7 +318,8 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
251
318
  selectedCategoryId={selectedCategoryId}
252
319
  lazyLoadProductsRecommended={business?.lazy_load_products_recommended}
253
320
  setSelectedCategoryId={setSelectedCategoryId}
254
- setCategoryClicked={setCategoryClicked}
321
+ setCategoryClicked={setCategoryClicked}
322
+
255
323
  />
256
324
  )}
257
325
  </>
@@ -279,8 +347,12 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
279
347
  errorQuantityProducts={errorQuantityProducts}
280
348
  handleCancelSearch={handleCancel}
281
349
  categoriesLayout={categoriesLayout}
350
+ subcategoriesSelected={subcategoriesSelected}
351
+ lazyLoadProductsRecommended={business?.lazy_load_products_recommended}
282
352
  setCategoriesLayout={setCategoriesLayout}
283
353
  currentCart={currentCart}
354
+ setSubcategoriesSelected={setSubcategoriesSelected}
355
+ onClickCategory={handleChangeCategory}
284
356
  />
285
357
  </WrapContent>
286
358
  </>
@@ -310,16 +382,18 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
310
382
  {!loading && auth && currentCart?.products?.length > 0 && categoryState.products.length !== 0 && (
311
383
  <FloatingButton
312
384
  btnText={
313
- currentCart?.subtotal >= currentCart?.minimum
314
- ? t('VIEW_ORDER', 'View Order')
315
- : `${t('MINIMUN_SUBTOTAL_ORDER', 'Minimum subtotal order:')} ${parsePrice(currentCart?.minimum)}`
385
+ openUpselling
386
+ ? t('LOADING', 'Loading')
387
+ : currentCart?.subtotal >= currentCart?.minimum
388
+ ? t('VIEW_ORDER', 'View Order')
389
+ : `${t('MINIMUN_SUBTOTAL_ORDER', 'Minimum subtotal order:')} ${parsePrice(currentCart?.minimum)}`
316
390
  }
317
- isSecondaryBtn={currentCart?.subtotal < currentCart?.minimum}
391
+ isSecondaryBtn={currentCart?.subtotal < currentCart?.minimum || openUpselling}
318
392
  btnLeftValueShow={currentCart?.subtotal >= currentCart?.minimum && currentCart?.products?.length > 0}
319
393
  btnRightValueShow={currentCart?.subtotal >= currentCart?.minimum && currentCart?.products?.length > 0}
320
- btnLeftValue={currentCart?.products?.length}
394
+ btnLeftValue={currentCart?.products.reduce((prev: number, product: any) => prev + product.quantity, 0)}
321
395
  btnRightValue={parsePrice(currentCart?.total)}
322
- disabled={currentCart?.subtotal < currentCart?.minimum}
396
+ disabled={currentCart?.subtotal < currentCart?.minimum || openUpselling}
323
397
  handleClick={() => setOpenUpselling(true)}
324
398
  />
325
399
  )}
@@ -329,16 +403,23 @@ const BusinessProductsListingUI = (props: BusinessProductsListingParams) => {
329
403
  business={currentCart?.business}
330
404
  cartProducts={currentCart?.products}
331
405
  cart={currentCart}
332
- setOpenUpselling={setOpenUpselling}
406
+ setOpenUpselling={setOpenUpselling}
333
407
  handleUpsellingPage={handleUpsellingPage}
334
408
  handleCloseUpsellingPage={handleCloseUpsellingPage}
335
409
  openUpselling={openUpselling}
336
410
  canOpenUpselling={canOpenUpselling}
337
411
  setCanOpenUpselling={setCanOpenUpselling}
338
- onRedirect={onRedirect}
412
+ onRedirect={onRedirect}
339
413
  />
340
414
  )}
341
- </SafeAreaView>
415
+ <Alert
416
+ open={alertState?.open || false}
417
+ title=''
418
+ content={[t('NOT_AVAILABLE_PRODUCTS', 'These products are not available.')]}
419
+ onAccept={() => setAlertState({ open: false, content: [] })}
420
+ onClose={() => setAlertState({ open: false, content: [] })}
421
+ />
422
+ </ContainerSafeAreaView>
342
423
  )
343
424
  }
344
425
 
@@ -1,5 +1,8 @@
1
1
  import styled, { css } from 'styled-components/native'
2
2
 
3
+ export const ContainerSafeAreaView = styled.SafeAreaView`
4
+ `
5
+
3
6
  export const WrapHeader = styled.View`
4
7
  position: relative;
5
8
  `
@@ -11,6 +14,7 @@ export const TopHeader = styled.View`
11
14
  z-index: 1;
12
15
  height: 60px;
13
16
  min-height: 60px;
17
+ margin-top: ${(props : any) => props.isIos ? '0' : '40px'};
14
18
  `
15
19
  export const AddressInput = styled.TouchableOpacity`
16
20
  flex: 1;
@@ -33,3 +37,21 @@ export const BusinessProductsListingContainer = styled.ScrollView`
33
37
  margin-bottom: 50px;
34
38
  `}
35
39
  `
40
+
41
+ export const FiltProductsContainer = styled.ScrollView`
42
+ position: absolute;
43
+ width: 100%;
44
+ z-index: 2000;
45
+ top: ${(props : any) => props.isIos ? '40px': '80px'};
46
+ margin-top: 20px;
47
+ `
48
+
49
+ export const BackgroundGray = styled.View`
50
+ flex: 1;
51
+ height: 100%;
52
+ background-color: rgba(0,0,0,0.5);
53
+ position: absolute;
54
+ margin-top: 100px;
55
+ z-index: 100;
56
+ width: 100%;
57
+ `
@@ -90,33 +90,12 @@ const BusinessReviewsUI = (props: BusinessReviewsParams) => {
90
90
  </View>
91
91
  );
92
92
 
93
- const ReviewItem = ({ comment, created_at, total, customer }: any) => (
93
+ const ReviewItem = ({ comment, created_at, total }: any) => (
94
94
  <View style={{ marginBottom: 30 }}>
95
- <View
96
- style={{ flexDirection: 'row', marginBottom: 19, alignItems: 'center' }}>
97
- <OIcon
98
- url={theme.images.dummies.customerPhoto}
99
- width={38}
100
- height={38}
101
- style={{
102
- borderRadius: 7.6,
103
- borderWidth: 1,
104
- borderColor: theme.colors.border,
105
- marginEnd: 9,
106
- }}
107
- />
108
- <View>
109
- <OText size={12} color={theme.colors.textNormal} weight={'500'}>
110
- {customer?.name || 'Jane Cooper'}
111
- </OText>
112
- <OText size={10} color={theme.colors.textSecondary}>
113
- {moment(created_at).format('MMMM d, yyyy • hh:mm')}
114
- </OText>
115
- </View>
116
- </View>
117
- <OText size={10} color={theme.colors.textNormal}>
118
- {comment}
95
+ <OText size={12} color={theme.colors.textSecondary}>
96
+ {moment(created_at).format('MMMM d, yyyy hh:mm')}
119
97
  </OText>
98
+ <OText size={12} color={theme.colors.textNormal}>{comment}</OText>
120
99
  </View>
121
100
  );
122
101
 
@@ -45,7 +45,6 @@ export const BusinessTypeFilterUI = (props: BusinessTypeFilterParams) => {
45
45
  const renderTypes = ({ item }: any) => {
46
46
  return (
47
47
  <TouchableOpacity
48
- key={item.id}
49
48
  onPress={() => handleChangeBusinessType(item.id)}
50
49
  style={{
51
50
  height: 34,
@@ -103,7 +102,7 @@ export const BusinessTypeFilterUI = (props: BusinessTypeFilterParams) => {
103
102
  showsHorizontalScrollIndicator={false}
104
103
  data={typesState?.types}
105
104
  renderItem={renderTypes}
106
- keyExtractor={(type) => type.name}
105
+ keyExtractor={(type, index) => `${type.name}_${index}`}
107
106
  />
108
107
  <TouchableOpacity
109
108
  style={{ marginLeft: 15 }}