ordering-ui-react-native 0.21.99 → 0.22.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ordering-ui-react-native",
3
- "version": "0.21.99",
3
+ "version": "0.22.01",
4
4
  "description": "Reusable components made in react native",
5
5
  "main": "src/index.tsx",
6
6
  "author": "ordering.inc",
@@ -4,8 +4,10 @@ import {
4
4
  View,
5
5
  TouchableOpacity,
6
6
  ActivityIndicator,
7
+ Alert,
7
8
  } from 'react-native';
8
9
  import Clipboard from '@react-native-clipboard/clipboard';
10
+ import { StarPRNT } from 'react-native-star-prnt';
9
11
  import { Placeholder, PlaceholderLine, Fade } from 'rn-placeholder';
10
12
  import { useTheme } from 'styled-components/native';
11
13
  import {
@@ -35,6 +37,8 @@ import CountryPicker from 'react-native-country-picker-modal';
35
37
  import { NotFoundSource } from '../NotFoundSource';
36
38
  import { OrderHeaderComponent } from './OrderHeaderComponent';
37
39
  import { OrderContentComponent } from './OrderContentComponent';
40
+ import { _retrieveStoreData } from '../../providers/StoreUtil'
41
+ import { usePrinterCommands } from './usePrinterCommands'
38
42
 
39
43
  export const OrderDetailsUI = (props: OrderDetailsParams) => {
40
44
  const {
@@ -57,6 +61,7 @@ export const OrderDetailsUI = (props: OrderDetailsParams) => {
57
61
  const [{ parsePrice, parseNumber, parseDate }] = useUtils();
58
62
  const [{ user, token }] = useSession();
59
63
  const [{ configs }] = useConfig();
64
+ const { generateCommands } = usePrinterCommands()
60
65
  const [, { showToast }] = useToast();
61
66
  const [unreadAlert, setUnreadAlert] = useState({
62
67
  business: false,
@@ -70,6 +75,7 @@ export const OrderDetailsUI = (props: OrderDetailsParams) => {
70
75
  const [openModalForAccept, setOpenModalForAccept] = useState(false);
71
76
  const [openModalForMapView, setOpenModalForMapView] = useState(false);
72
77
  const [isDriverModalVisible, setIsDriverModalVisible] = useState(false);
78
+ const [printerSettings, setPrinterSettings] = useState('')
73
79
 
74
80
  if (order?.status === 7 || order?.status === 4) {
75
81
  if (drivers?.length > 0 && drivers) {
@@ -291,7 +297,40 @@ export const OrderDetailsUI = (props: OrderDetailsParams) => {
291
297
  setOpenModalForAccept(true);
292
298
  };
293
299
 
300
+ const printAction = async (printerSettings: any, commands: any) => {
301
+ try {
302
+ var printResult = await StarPRNT.print(printerSettings?.emulation, commands, printerSettings?.portName);
303
+ Alert.alert(
304
+ t('PRINT_SUCCESS_TITLE', 'Print Success'),
305
+ t('PRINT_SUCCESS_SUBTITLE', `Go check your _printer_ printer!`).replace('_printer_', printerSettings?.model),
306
+ [
307
+ {text: 'OK', onPress: () => null},
308
+ ],
309
+ { cancelable: false }
310
+ )
311
+ } catch (e) {
312
+ Alert.alert(
313
+ t('PRINT_FAIL_TITLE', 'Connection Failed'),
314
+ t('PRINT_FAIL_SUBTITLE', 'Make sure your Star Printer is turned on and have thermal paper in it.'),
315
+ [
316
+ {text: 'OK', onPress: () => null},
317
+ ],
318
+ { cancelable: false }
319
+ )
320
+ }
321
+ }
322
+
294
323
  const handleViewSummaryOrder = () => {
324
+ if (printerSettings) {
325
+ const commands: any = generateCommands({
326
+ ...order,
327
+ orderStatus: getOrderStatus(order?.status, t)?.value
328
+ })
329
+ commands.push({ appendCutPaper: StarPRNT.CutPaperAction.PartialCutWithFeed })
330
+
331
+ printAction(printerSettings, commands)
332
+ return
333
+ }
295
334
  navigation?.navigate &&
296
335
  navigation.navigate('OrderSummary', {
297
336
  order,
@@ -372,6 +411,15 @@ export const OrderDetailsUI = (props: OrderDetailsParams) => {
372
411
  }
373
412
  }, [driverLocation]);
374
413
 
414
+ useEffect(() => {
415
+ const getPrinterDefault = async () => {
416
+ const printer = await _retrieveStoreData('printer')
417
+ setPrinterSettings(printer)
418
+ }
419
+
420
+ getPrinterDefault()
421
+ }, [])
422
+
375
423
  const styles = StyleSheet.create({
376
424
  driverOff: {
377
425
  backgroundColor: theme.colors.notAvailable,
@@ -0,0 +1,140 @@
1
+ import { useConfig, useUtils, useLanguage} from 'ordering-components/native'
2
+
3
+ import { verifyDecimals, getProductPrice } from '../../utils';
4
+
5
+ /**
6
+ * Hook to create commands for star micronics printer using PassPRNT library
7
+ * @returns array of strings
8
+ */
9
+
10
+ export const usePrinterCommands = () => {
11
+ const [, t] = useLanguage()
12
+ const [{ configs }] = useConfig();
13
+ const [{ parsePrice, parseNumber, parseDate }] = useUtils();
14
+
15
+ const deliveryStatus: any = {
16
+ 1: t('DELIVERY', 'Delivery'),
17
+ 2: t('PICK_UP', 'Pick up'),
18
+ 3: t('EAT_IN', 'Eat In'),
19
+ 4: t('CURBSIDE', 'Curbside'),
20
+ 5: t('DRIVER_THRU', 'Driver thru'),
21
+ };
22
+
23
+ const walletName: any = {
24
+ cash: {
25
+ name: t('CASH_WALLET', 'Cash Wallet')
26
+ },
27
+ credit_point: {
28
+ name: t('POINTS_WALLET', 'Points Wallet')
29
+ }
30
+ }
31
+
32
+ const percentTip = (order: any) =>
33
+ parseInt(configs?.driver_tip_type?.value, 10) === 2 &&
34
+ !parseInt(configs?.driver_tip_use_custom?.value, 10) &&
35
+ verifyDecimals(order?.summary?.driver_tip, parseNumber);
36
+
37
+ const handlePaymethodsListString = (order: any) => {
38
+ const paymethodsList = order?.payment_events?.filter((item: any) => item.event === 'payment').map((paymethod: any) => {
39
+ return paymethod?.wallet_event
40
+ ? walletName[paymethod?.wallet_event?.wallet?.type]?.name
41
+ : t(paymethod?.paymethod?.gateway?.toUpperCase(), paymethod?.paymethod?.name)
42
+ })
43
+ return paymethodsList.join(', ')
44
+ }
45
+
46
+ const paymethodsLength = (order: any) => order?.payment_events?.filter((item: any) => item.event === 'payment')?.length
47
+
48
+ const customerName = (order: any) => `${order?.customer?.name ?? ''} ${order?.customer?.middle_name ?? ''} ${order?.customer?.lastname ?? ''} ${order?.customer?.second_lastname ?? ''}`?.replace(' ', ' ')?.trim() ?? ''
49
+
50
+ const generateCommands = (order: any) => {
51
+ let commands: any = [];
52
+
53
+ const textProps = {
54
+ fontSize: 12,
55
+ absolutePosition: 40
56
+ }
57
+
58
+ const generateProductsText = () => {
59
+ const list: any = []
60
+
61
+ if (order?.products.length) {
62
+ order?.products.map((product: any) => {
63
+ list.push(`${product?.quantity} ${product?.name} \t\t\t ${parsePrice(product.total ?? getProductPrice(product))}`)
64
+
65
+ product.options?.map((option: any) => {
66
+ list.push(`\t ${option.name}`)
67
+
68
+ option.suboptions?.map((suboption: any) => {
69
+ const { quantity, name, position, price } = suboption
70
+ const pos = position && position !== 'whole' ? `(${t(position.toUpperCase(), position)})` : ''
71
+ const string = name !== 'No'
72
+ ? pos
73
+ ? `${quantity} x ${name} ${pos} +${parsePrice(price)}`
74
+ : `${quantity} x ${name} +${parsePrice(price)}`
75
+ : 'No'
76
+
77
+ list.push(`\t\t ${string}`)
78
+ })
79
+ })
80
+
81
+ if (product.comment) {
82
+ list.push(`\t ${t('COMMENT', 'Comment')}`)
83
+ list.push(`\t\t ${product.comment}`)
84
+ }
85
+
86
+ list.push('------------------------------------------------',)
87
+ })
88
+ }
89
+
90
+ return list
91
+ }
92
+
93
+ const appends: any = [
94
+ `${t('ORDER_NO', 'Order No.')} ${order.id}`,
95
+ '\n', // need to replace with other break line command
96
+ order.orderStatus,
97
+ `${t('DELIVERY_TYPE', 'Delivery Type')}: ${deliveryStatus[order?.delivery_type]}`,
98
+ `${t('DELIVERY_DATE', 'Delivery Date')}: ${order?.delivery_datetime_utc ? parseDate(order?.delivery_datetime_utc) : parseDate(order?.delivery_datetime, { utc: false })}`,
99
+ `${t(`PAYMENT_METHOD${paymethodsLength(order) > 1 ? 'S' : ''}`, `Payment method${paymethodsLength(order) > 1 ? 's' : ''}`)}: ${handlePaymethodsListString(order)}`,
100
+ '\n', // need to replace with other break line command
101
+ `${t('CUSTOMER_DETAILS', 'Customer details')}`,
102
+ `${t('FULL_NAME', 'Full Name')}: ${customerName(order)}`,
103
+ `${t('EMAIL', 'Email')}: ${order?.customer?.email}`,
104
+ `${t('MOBILE_PHONE', 'Mobile Phone')}: ${order?.customer?.cellphone}`,
105
+ `${!!order?.customer?.phone ? `${t('MOBILE_PHONE', 'Mobile Phone')}: ${order?.customer?.phone}` : '\n'}`,
106
+ `${t('FULL_ADDRESS', 'Full Addres')}: ${order?.customer?.address}`,
107
+ `${!!order?.customer?.internal_number ? `${t('INTERNAL_NUMBER', 'Internal Number')}: ${order?.customer?.internal_number}` : '\n'}`,
108
+ `${!!order?.customer?.zipcode ? `${t('ZIPCODE', 'Zipcode')}: ${order?.customer?.zipcode}` : '\n'}`,
109
+ '\n', // need to replace with other break line command
110
+ `${t('BUSINESS_DETAILS', 'Business details')}`,
111
+ order?.business?.name,
112
+ order?.business?.email,
113
+ `${t('BUSINESS_PHONE', 'Business Phone')}: ${order?.business?.cellphone}`,
114
+ `${!!order?.business?.phone ? `${t('BUSINESS_PHONE', 'Business Phone')}: ${order?.business?.phone}` : '\n'}`,
115
+ `${t('ADDRESS', 'Address')}: ${order?.business?.address}`,
116
+ `${!!order?.business?.address_notes ? `${t('SPECIAL_ADDRESS', 'Special Address')}: ${order?.business?.address_notes}` : '\n'}`,
117
+ '\n', // need to replace with other break line command
118
+ `${t('ORDER_DETAILS', 'Order Details')}`,
119
+ ...generateProductsText(),
120
+ '\n', // need to replace with other break line command
121
+ `${t('SUBTOTAL', 'Subtotal')} \t\t\t ${parsePrice(order.tax_type === 1 ? (order?.summary?.subtotal + order?.summary?.tax) ?? 0 : order?.summary?.subtotal ?? 0)}`,
122
+ `${order?.summary?.discount > 0 ? `${order?.offer_type === 1 ? `${t('DISCOUNT', 'Discount')} (${verifyDecimals(order?.offer_rate, parsePrice)}%)` : t('DISCOUNT', 'Discount')} \t\t\t ${parsePrice(order?.summary?.discount)}` : '\n'}`,
123
+ `${order?.tax_type !== 1 ? `${t('TAX', 'Tax')} (${verifyDecimals(order?.summary?.tax_rate, parseNumber)}%) \t\t\t ${parsePrice(order?.summary?.tax ?? 0)}` : '\n'}`,
124
+ `${order?.summary?.delivery_price > 0 ? `${t('DELIVERY_FEE', 'Delivery Fee')} \t\t\t ${parsePrice(order?.summary?.delivery_price ?? 0)}` : '\n'}`,
125
+ `${t('DRIVER_TIP', 'Driver tip')} ${percentTip(order) ? `(${percentTip(order)}%)` : ''} \t\t\t ${parsePrice(order?.summary?.driver_tip ?? 0)}`,
126
+ `${t('SERVICE_FEE', 'Service Fee')} (${verifyDecimals(order?.summary?.service_fee, parseNumber)}%) \t\t\t ${parsePrice(order?.summary?.service_fee ?? 0)}`,
127
+ '------------------------------------------------',
128
+ `${t('TOTAL', 'Total')} \t\t\t ${parsePrice(order?.summary?.total ?? 0)}`
129
+ ]
130
+
131
+ commands = [
132
+ ...commands,
133
+ ...appends.map((append: any) => ({ appendBitmapText: append, ...textProps }))
134
+ ]
135
+
136
+ return commands
137
+ }
138
+
139
+ return { generateCommands }
140
+ }
@@ -0,0 +1,117 @@
1
+ import React, { useEffect, useState } from 'react'
2
+ import { ScrollView, StyleSheet, TouchableOpacity, View } from 'react-native'
3
+ import SimpleLineIcons from 'react-native-vector-icons/SimpleLineIcons'
4
+ import FeatherIcon from 'react-native-vector-icons/Feather'
5
+ import { useTheme } from 'styled-components/native'
6
+ import { useLanguage } from 'ordering-components/native'
7
+
8
+ import { _setStoreData, _retrieveStoreData } from '../../providers/StoreUtil'
9
+ import { Container } from './styles'
10
+ import { OText } from '../shared'
11
+
12
+ export const PrinterSettings = (props: any) => {
13
+ const { onClose } = props
14
+
15
+ const [currentPrinter, setCurrentPrinter] = useState<any>(null)
16
+
17
+ const [, t] = useLanguage()
18
+ const theme = useTheme()
19
+
20
+ const styles = StyleSheet.create({
21
+ icons: {
22
+ maxWidth: 40,
23
+ height: 40,
24
+ padding: 10,
25
+ alignItems: 'flex-end'
26
+ },
27
+ })
28
+
29
+ const printerList = [
30
+ { model: 'mPOP', emulation: 'StarPRNT', portName: 'BT:TSP100' },
31
+ { model: 'FVP10', emulation: 'StarLine', portName: 'BT:TSP100' },
32
+ { model: 'TSP100', emulation: 'StarGraphic', portName: 'BT:TSP100' },
33
+ { model: 'TSP65011', emulation: 'StarLine', portName: 'BT:TSP100' },
34
+ { model: 'TSP7001', emulation: 'StarLine', portName: 'BT:TSP100' },
35
+ { model: 'TSP80011', emulation: 'StarLine', portName: 'BT:TSP100' },
36
+ { model: 'SP700', emulation: 'StarDotimpact', portName: 'BT:TSP100' },
37
+ { model: 'SM-S210i', emulation: 'EscPosMobile', portName: 'BT:TSP100' },
38
+ { model: 'SM-S220i', emulation: 'EscPosMobile', portName: 'BT:TSP100' },
39
+ { model: 'SM-S230i', emulation: 'EscosMobile', portName: 'BT:TSP100' },
40
+ { model: 'SM-T300i/T300', emulation: 'EscPosMobile', portName: 'BT:TSP100' },
41
+ { model: 'SM-T400i', emulation: 'EscosMobile', portName: 'BT:TSP100' },
42
+ { model: 'SM-L200', emulation: 'StarPRNT', portName: 'BT:TSP100' },
43
+ { model: 'SM-L300', emulation: 'StarPRNT', portName: 'BT:TSP100' },
44
+ { model: 'BSC10', emulation: 'EscPos', portName: 'BT:TSP100' },
45
+ { model: 'SM-S210i StarPRNT', emulation: 'StarPRNT', portName: 'BT:TSP100' },
46
+ { model: 'SM-S220i StarPRNT', emulation: 'StarPRNT', portName: 'BT:TSP100' },
47
+ { model: 'SM-S230i StarPRNT', emulation: 'StarPRNT', portName: 'BT:TSP100' },
48
+ { model: 'SM-T300i/T300 StarPRNT', emulation: 'StarPRNT', portName: 'BT:TSP100' },
49
+ { model: 'SM-T400i StarPRNT', emulation: 'StarPRNT', portName: 'BT:TSP100' },
50
+ ]
51
+
52
+ const handleClick = async (item: any) => {
53
+ setCurrentPrinter(item)
54
+ await _setStoreData('printer', item)
55
+ onClose && onClose()
56
+ }
57
+
58
+ useEffect(() => {
59
+ const getPrinterDefault = async () => {
60
+ const printer = await _retrieveStoreData('printer')
61
+ setCurrentPrinter(printer)
62
+ }
63
+
64
+ getPrinterDefault()
65
+ }, [])
66
+
67
+ return (
68
+ <ScrollView
69
+ showsVerticalScrollIndicator={false}
70
+ >
71
+ <OText size={24} style={{ paddingLeft: 30 }}>
72
+ {t('PRINTER_SETTINGS', 'Printer Settings')}
73
+ </OText>
74
+ <View style={{ padding: 30 }}>
75
+ {printerList.map((item: any, i: number) => (
76
+ <Container
77
+ key={i}
78
+ activeOpacity={1}
79
+ onPress={() => handleClick(item)}
80
+ >
81
+ <TouchableOpacity
82
+ activeOpacity={1}
83
+ style={{ flexDirection: 'row', alignItems: 'center' }}
84
+ onPress={() => handleClick(item)}
85
+ >
86
+ <SimpleLineIcons
87
+ name='printer'
88
+ color={theme.colors.textGray}
89
+ size={18}
90
+ style={{ ...styles.icons, color: currentPrinter?.model === item.model ? theme.colors.primary : theme.colors.textGray }}
91
+ />
92
+ <OText
93
+ size={18}
94
+ color={currentPrinter?.model === item.model ? theme.colors.primary : theme.colors.textGray}
95
+ >
96
+ {item.model}
97
+ </OText>
98
+ </TouchableOpacity>
99
+ {currentPrinter?.model === item.model && (
100
+ <TouchableOpacity
101
+ activeOpacity={1}
102
+ onPress={() => handleClick(null)}
103
+ >
104
+ <FeatherIcon
105
+ name='x-circle'
106
+ color={theme.colors.danger500}
107
+ size={20}
108
+ style={styles.icons}
109
+ />
110
+ </TouchableOpacity>
111
+ )}
112
+ </Container>
113
+ ))}
114
+ </View>
115
+ </ScrollView>
116
+ )
117
+ }
@@ -0,0 +1,10 @@
1
+ import styled from "styled-components/native";
2
+
3
+ export const Container = styled.View`
4
+ flex-direction: row;
5
+ justify-content: space-between;
6
+ width: 100%;
7
+ padding: 5px 5px 5px 0;
8
+ border-bottom-width: 1px;
9
+ border-bottom-color: ${(props: any) => props.theme.colors.lightGray};
10
+ `
@@ -36,7 +36,8 @@ export const UserFormDetailsUI = (props: any) => {
36
36
  handleCancelEdit,
37
37
  toggleIsEdit,
38
38
  isCheckout,
39
- isAlsea
39
+ isAlsea,
40
+ allowDriverUpdateData
40
41
  } = props;
41
42
 
42
43
  const theme = useTheme();
@@ -66,9 +67,9 @@ export const UserFormDetailsUI = (props: any) => {
66
67
  const rules: any = {
67
68
  required: isRequiredField(field.code)
68
69
  ? t(
69
- `VALIDATION_ERROR_${field.code.toUpperCase()}_REQUIRED`,
70
- `${field.name} is required`,
71
- ).replace('_attribute_', t(field.name, field.code))
70
+ `VALIDATION_ERROR_${field.code.toUpperCase()}_REQUIRED`,
71
+ `${field.name} is required`,
72
+ ).replace('_attribute_', t(field.name, field.code))
72
73
  : null,
73
74
  };
74
75
  if (field.code && field.code === 'email') {
@@ -261,90 +262,93 @@ export const UserFormDetailsUI = (props: any) => {
261
262
  sortInputFields({ values: validationFields?.fields?.checkout })
262
263
  .length > 0 && (
263
264
  <UDWrapper>
264
- {sortInputFields({
265
- values: validationFields.fields?.checkout,
266
- }).map(
267
- (field: any) =>
268
- showField &&
269
- showField(field.code) &&
270
- !isAlsea
271
- && (
272
- <React.Fragment key={field.id}>
273
- <OText style={styles.label}>
274
- {t(field?.code.toUpperCase(), field?.name)}
275
- </OText>
265
+ {allowDriverUpdateData && (
266
+ <>
267
+ {sortInputFields({
268
+ values: validationFields.fields?.checkout,
269
+ }).map(
270
+ (field: any) =>
271
+ showField &&
272
+ showField(field.code) &&
273
+ !isAlsea
274
+ && (
275
+ <React.Fragment key={field.id}>
276
+ <OText style={styles.label}>
277
+ {t(field?.code.toUpperCase(), field?.name)}
278
+ </OText>
276
279
 
277
- <Controller
278
- key={field.id}
279
- control={control}
280
- render={() => (
281
- <OInput
282
- name={field.code}
283
- placeholder={t(
284
- field.code.toUpperCase(),
285
- field?.name,
286
- )}
287
- placeholderTextColor={theme.colors.arrowColor}
288
- style={styles.inputStyle}
289
- icon={
290
- field.code === 'email'
291
- ? theme.images.general.email
292
- : theme.images.general.user
293
- }
294
- autoCapitalize={
295
- field.code === 'email' ? 'none' : 'sentences'
296
- }
297
- isDisabled={!isEdit}
298
- value={
299
- formState?.changes[field.code] ??
300
- (user && user[field.code]) ??
301
- ''
302
- }
303
- onChange={(val: any) => {
304
- field.code !== 'email'
305
- ? setValue(field.code, val.target.value)
306
- : setValue(
307
- field.code,
308
- val.target.value
309
- .toLowerCase()
310
- .replace(/[&,()%";:ç?<>{}\\[\]\s]/g, ''),
311
- );
312
- field.code !== 'email'
313
- ? handleChangeInput(val)
314
- : handleChangeInput({
315
- target: {
316
- name: 'email',
317
- value: val.target.value
280
+ <Controller
281
+ key={field.id}
282
+ control={control}
283
+ render={() => (
284
+ <OInput
285
+ name={field.code}
286
+ placeholder={t(
287
+ field.code.toUpperCase(),
288
+ field?.name,
289
+ )}
290
+ placeholderTextColor={theme.colors.arrowColor}
291
+ style={styles.inputStyle}
292
+ icon={
293
+ field.code === 'email'
294
+ ? theme.images.general.email
295
+ : theme.images.general.user
296
+ }
297
+ autoCapitalize={
298
+ field.code === 'email' ? 'none' : 'sentences'
299
+ }
300
+ isDisabled={!isEdit}
301
+ value={
302
+ formState?.changes[field.code] ??
303
+ (user && user[field.code]) ??
304
+ ''
305
+ }
306
+ onChange={(val: any) => {
307
+ field.code !== 'email'
308
+ ? setValue(field.code, val.target.value)
309
+ : setValue(
310
+ field.code,
311
+ val.target.value
318
312
  .toLowerCase()
319
- .replace(
320
- /[&,()%";:ç?<>{}\\[\]\s]/g,
321
- '',
322
- ),
323
- },
324
- });
325
- }}
326
- autoCorrect={field.code === 'email' && false}
327
- type={
328
- field.code === 'email'
329
- ? 'email-address'
330
- : 'default'
331
- }
332
- returnKeyType="done"
333
- autoCompleteType={
334
- field.code === 'email' ? 'email' : 'off'
335
- }
336
- selectionColor={theme.colors.primary}
337
- color={theme.colors.textGray}
313
+ .replace(/[&,()%";:ç?<>{}\\[\]\s]/g, ''),
314
+ );
315
+ field.code !== 'email'
316
+ ? handleChangeInput(val)
317
+ : handleChangeInput({
318
+ target: {
319
+ name: 'email',
320
+ value: val.target.value
321
+ .toLowerCase()
322
+ .replace(
323
+ /[&,()%";:ç?<>{}\\[\]\s]/g,
324
+ '',
325
+ ),
326
+ },
327
+ });
328
+ }}
329
+ autoCorrect={field.code === 'email' && false}
330
+ type={
331
+ field.code === 'email'
332
+ ? 'email-address'
333
+ : 'default'
334
+ }
335
+ returnKeyType="done"
336
+ autoCompleteType={
337
+ field.code === 'email' ? 'email' : 'off'
338
+ }
339
+ selectionColor={theme.colors.primary}
340
+ color={theme.colors.textGray}
341
+ />
342
+ )}
343
+ name={field.code}
344
+ rules={getInputRules(field)}
345
+ defaultValue={user && user[field.code]}
338
346
  />
339
- )}
340
- name={field.code}
341
- rules={getInputRules(field)}
342
- defaultValue={user && user[field.code]}
343
- />
344
- </React.Fragment>
345
- ),
347
+ </React.Fragment>
348
+ ),
349
+ )}
350
+ </>
346
351
  )}
347
-
348
352
  <OText style={styles.label}>{t('PASSWORD', 'Password')}</OText>
349
353
 
350
354
  <Controller
@@ -445,7 +449,7 @@ export const UserFormDetailsUI = (props: any) => {
445
449
  </OText>
446
450
  )}
447
451
 
448
- {!!showInputPhoneNumber && !isAlsea && (
452
+ {!!showInputPhoneNumber && !isAlsea && allowDriverUpdateData && (
449
453
  <WrapperPhone>
450
454
  <PhoneInputNumber
451
455
  data={phoneInputData}
@@ -487,28 +491,28 @@ export const UserFormDetailsUI = (props: any) => {
487
491
  isEdit) ||
488
492
  (watchPassword?.length > 0 && watchConfirmPassword?.length > 0) ||
489
493
  formState?.loading) && (
490
- <View style={{ flex: 1, marginLeft: 5 }}>
491
- <OButton
492
- text={
493
- formState.loading
494
- ? t('UPDATING', 'Updating')
495
- : t('UPDATE', 'Update')
496
- }
497
- bgColor={theme.colors.primary}
498
- textStyle={{
499
- ...styles.btnText,
500
- color: formState.loading
501
- ? theme.colors.textGray
502
- : theme.colors.white,
503
- }}
504
- borderColor={theme.colors.primary}
505
- isDisabled={formState.loading}
506
- imgRightSrc={null}
507
- style={styles.editButton}
508
- onClick={handleSubmit(onSubmit)}
509
- />
510
- </View>
511
- )}
494
+ <View style={{ flex: 1, marginLeft: 5 }}>
495
+ <OButton
496
+ text={
497
+ formState.loading
498
+ ? t('UPDATING', 'Updating')
499
+ : t('UPDATE', 'Update')
500
+ }
501
+ bgColor={theme.colors.primary}
502
+ textStyle={{
503
+ ...styles.btnText,
504
+ color: formState.loading
505
+ ? theme.colors.textGray
506
+ : theme.colors.white,
507
+ }}
508
+ borderColor={theme.colors.primary}
509
+ isDisabled={formState.loading}
510
+ imgRightSrc={null}
511
+ style={styles.editButton}
512
+ onClick={handleSubmit(onSubmit)}
513
+ />
514
+ </View>
515
+ )}
512
516
  </EditButton>
513
517
  )}
514
518
  </>
@@ -24,6 +24,7 @@ import { LogoutButton } from '../LogoutButton';
24
24
  import { LanguageSelector } from '../LanguageSelector';
25
25
  import { UserFormDetailsUI } from '../UserFormDetails';
26
26
  import { DriverSchedule } from '../DriverSchedule'
27
+ import { PrinterSettings } from '../PrinterSettings'
27
28
  import ToggleSwitch from 'toggle-switch-react-native';
28
29
  import { UDWrapper } from '../UserFormDetails/styles';
29
30
  import {
@@ -502,17 +503,31 @@ const ProfileUI = (props: ProfileParams) => {
502
503
  />
503
504
  </EditButton>
504
505
  )}
505
- <Pressable style={{ marginBottom: 10 }} onPress={() => setOpenModal(true)}>
506
- <View style={{ flexDirection: 'row', justifyContent: 'space-between' }}>
507
- <OText size={16}>{t('SCHEDULE', 'Schedule')}</OText>
508
- <AntDesignIcon size={18} name='right' />
509
- </View>
510
- <View style={{
511
- borderBottomColor: theme.colors.tabBar,
512
- borderBottomWidth: 1,
513
- marginTop: 10
514
- }} />
515
- </Pressable>
506
+ {!props.isBusinessApp ? (
507
+ <Pressable style={{ marginBottom: 10 }} onPress={() => setOpenModal(true)}>
508
+ <View style={{ flexDirection: 'row', justifyContent: 'space-between' }}>
509
+ <OText size={16}>{t('SCHEDULE', 'Schedule')}</OText>
510
+ <AntDesignIcon size={18} name='right' />
511
+ </View>
512
+ <View style={{
513
+ borderBottomColor: theme.colors.tabBar,
514
+ borderBottomWidth: 1,
515
+ marginTop: 10
516
+ }} />
517
+ </Pressable>
518
+ ) : (
519
+ <Pressable style={{ marginBottom: 10 }} onPress={() => setOpenModal(true)}>
520
+ <View style={{ flexDirection: 'row', justifyContent: 'space-between' }}>
521
+ <OText size={16}>{t('PRINTER_SETTINGS', 'Printer Settings')}</OText>
522
+ <AntDesignIcon size={18} name='right' />
523
+ </View>
524
+ <View style={{
525
+ borderBottomColor: theme.colors.tabBar,
526
+ borderBottomWidth: 1,
527
+ marginTop: 10
528
+ }} />
529
+ </Pressable>
530
+ )}
516
531
  <Pressable style={{ marginBottom: 10 }} onPress={() => navigation.navigate('Sessions')}>
517
532
  <View style={{ flexDirection: 'row', justifyContent: 'space-between' }}>
518
533
  <OText size={16}>{t('SESSIONS', 'Sessions')}</OText>
@@ -535,7 +550,11 @@ const ProfileUI = (props: ProfileParams) => {
535
550
  entireModal
536
551
  hideIcons
537
552
  >
538
- <DriverSchedule schedule={user?.schedule} />
553
+ {props.isBusinessApp ? (
554
+ <PrinterSettings onClose={() => setOpenModal(false)} />
555
+ ) : (
556
+ <DriverSchedule schedule={user?.schedule} />
557
+ )}
539
558
  </OModal>
540
559
  </ScrollView>
541
560
  )}
@@ -48,8 +48,8 @@ export const useLocation = () => {
48
48
  GeoLocation.getCurrentPosition(
49
49
  ({ coords }) => {
50
50
  resolve({
51
- latitude: typeof coords.latitude !== 'number' && !Number.isNaN(coords.latitude) ? coords.latitude : 0,
52
- longitude: typeof coords.longitude !== 'number' && !Number.isNaN(coords.longitude) ? coords.longitude : 0,
51
+ latitude: typeof coords.latitude === 'number' && !Number.isNaN(coords.latitude) ? coords.latitude : 0,
52
+ longitude: typeof coords.longitude === 'number' && !Number.isNaN(coords.longitude) ? coords.longitude : 0,
53
53
  speed: coords.speed,
54
54
  });
55
55
  },
@@ -59,6 +59,7 @@ export interface ProfileParams {
59
59
  isAlsea?: boolean;
60
60
  isShowDriverStatus?: boolean;
61
61
  isFocused?: boolean;
62
+ isBusinessApp?: boolean;
62
63
  }
63
64
 
64
65
  export interface AddressListParams {
@@ -771,7 +771,7 @@ const CheckoutUI = (props: any) => {
771
771
  cart?.status !== 2 &&
772
772
  validationFields?.fields?.checkout?.driver_tip?.enabled &&
773
773
  driverTipsOptions && driverTipsOptions?.length > 0 &&
774
- !isGiftCardCart &&
774
+ cart?.business_id &&
775
775
  (
776
776
  <ChSection>
777
777
  <ChDriverTips>