Skip to content

Commit

Permalink
Sample app overhaul.
Browse files Browse the repository at this point in the history
Only two screens now: home and permissions.
Home screen handles showing settings screen, showing mock reader, startPayment, and taking you to the permissions screen.
Permission screens handles bluetooth, location, microphone permissions and authorization.
Moved certain things to their own components.
Should look 95% like the sample app for iOS/Android.
  • Loading branch information
plinio-square committed Jan 21, 2025
1 parent a9d8c2a commit 321c941
Show file tree
Hide file tree
Showing 13 changed files with 498 additions and 368 deletions.
1 change: 1 addition & 0 deletions example/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
"@react-navigation/native-stack": "^6.11.0",
"react": "18.3.1",
"react-native": "0.75.3",
"react-native-bouncy-checkbox": "^4.1.2",
"react-native-permissions": "^3.6.1",
"react-native-safe-area-context": "^4.11.0",
"react-native-screens": "^3.34.0",
Expand Down
16 changes: 8 additions & 8 deletions example/src/App.tsx
Original file line number Diff line number Diff line change
@@ -1,22 +1,22 @@
import { createNativeStackNavigator } from '@react-navigation/native-stack';
import { NavigationContainer } from '@react-navigation/native';
import SplashScreen from './Screens/SplashScreen';
import { HomeScreen } from './Screens/HomeScreen';
import HomeView from './Screens/HomeScreen';
import PermissionsScreen from './Screens/PermissionsScreen';

const Stack = createNativeStackNavigator();

export default function App() {
return (
<NavigationContainer>
<Stack.Navigator>
<Stack.Screen
name="Splash"
component={SplashScreen}
<Stack.Screen
name="Home"
component={HomeView}
options={{ headerShown: false }}
/>
<Stack.Screen
name="Home"
component={HomeScreen}
<Stack.Screen
name="Permissions"
component={PermissionsScreen}
options={{ headerShown: false }}
/>
</Stack.Navigator>
Expand Down
188 changes: 113 additions & 75 deletions example/src/Screens/HomeScreen.tsx
Original file line number Diff line number Diff line change
@@ -1,91 +1,129 @@
import {
View,
Text,
StyleSheet,
SafeAreaView,
TouchableOpacity,
} from 'react-native';
import Feather from 'react-native-vector-icons/Feather';
import { defaultStyles } from '../styles/common';
import {
showSettings,
type PaymentParameters,
CurrencyCode,
type PromptParameters,
AdditionalPaymentMethodType,
PromptMode,
startPayment,
} from 'mobile-payments-sdk-react-native';
import { useEffect } from 'react';
import CustomButton from '../components/CustomButton';
import { useNavigation } from '@react-navigation/native';
import { AdditionalPaymentMethodType, CurrencyCode, hideMockReaderUI, PromptMode, showMockReaderUI, showSettings, startPayment, type PaymentParameters, type PromptParameters } from 'mobile-payments-sdk-react-native';
import React, { useState } from 'react';
import { View, Text, Image, StyleSheet, SafeAreaView, TouchableOpacity } from 'react-native';
import uuid from 'react-native-uuid';
import LoadingButton from '../components/LoadingButton';
import HeaderButton from '../components/HeaderButton';

const handleStartPayment = async () => {
const paymentParameters: PaymentParameters = {
amountMoney: { amount: 100, currencyCode: CurrencyCode.USD },
appFeeMoney: { amount: 0, currencyCode: CurrencyCode.USD },
idempotencyKey: uuid.v4(),
note: 'Payment for services',
// Other parameters you could add:
// autocomplete: true,
// delayAction: DelayAction.CANCEL,
// tipMoney: { amount: 0, currencyCode: CurrencyCode.USD },
// etc
// For more information, visit
// iOS: https://developer.squareup.com/docs/mobile-payments-sdk/ios/take-payments#create-payment-parameters
// Android: https://developer.squareup.com/docs/mobile-payments-sdk/android/take-payments#create-payment-parameters
const HomeView = () => {
const navigation = useNavigation();

const [isMockReaderPresented, setMockReaderPresented] = useState(false);

const dismissMockReader = () => {
hideMockReaderUI();
setMockReaderPresented(false);
};

const promptParameters: PromptParameters = {
additionalMethods: [AdditionalPaymentMethodType.ALL],
mode: PromptMode.DEFAULT,
const presentMockReader = () => {
showMockReaderUI();
setMockReaderPresented(true);
};

try {
const payment = await startPayment(paymentParameters, promptParameters);
console.log('Payment successful:', payment);
} catch (error) {
console.log('Payment error:', JSON.stringify(error['userInfo']));
}
};
const handleStartPayment = async () => {
const paymentParameters: PaymentParameters = {
amountMoney: { amount: 100, currencyCode: CurrencyCode.USD },
appFeeMoney: { amount: 0, currencyCode: CurrencyCode.USD },
idempotencyKey: uuid.v4(),
note: 'Payment for services',
// Other parameters you could add:
// autocomplete: true,
// delayAction: DelayAction.CANCEL,
// tipMoney: { amount: 0, currencyCode: CurrencyCode.USD },
// etc
// For more information, visit
// iOS: https://developer.squareup.com/docs/mobile-payments-sdk/ios/take-payments#create-payment-parameters
// Android: https://developer.squareup.com/docs/mobile-payments-sdk/android/take-payments#create-payment-parameters
};

const promptParameters: PromptParameters = {
additionalMethods: [AdditionalPaymentMethodType.ALL],
mode: PromptMode.DEFAULT,
};

export function HomeScreen() {
useEffect(() => {
// If you wish to display mock reader UI, make sure you're initializing the SDK
// with a sandbox Application ID.
// https://developer.squareup.com/docs/mobile-payments-sdk/ios#3-initialize-the-mobile-payments-sdk
// showMockReaderUI();
});
try {
const payment = await startPayment(paymentParameters, promptParameters);
console.log('Payment successful:', payment);
} catch (error) {
console.log('Payment error:', JSON.stringify(error['userInfo']));
}
};

return (
<SafeAreaView style={defaultStyles.pageContainer}>
<View style={defaultStyles.pageContainer}>
<View style={styles.iconContainer}>
<TouchableOpacity onPress={showSettings}>
<Feather name="settings" size={30} color="black" />
</TouchableOpacity>
</View>
<View style={defaultStyles.descriptionContainer}>
<Text style={defaultStyles.title}>Authorize Reader SDK.</Text>
<Text style={defaultStyles.subtitle}>
Generate an authorization code
{'\n'}
in the Reader SDK tab
{'\n'}
of the Developer Portal.
</Text>
</View>
<CustomButton title="Start Payment" onPress={handleStartPayment} />
<SafeAreaView style={styles.container}>
<View style={styles.header}>
<HeaderButton title="Settings" onPress={showSettings} />
<View style={styles.headerSpacer} />
<HeaderButton title="Permissions" onPress={() => navigation.navigate('Permissions')} />
</View>
<View style={styles.content}>
<Image source={require('../assets/donut.png')} style={styles.donutImage} />
<Text style={styles.title}>Donut Counter</Text>
<LoadingButton
isLoading={false}
isButtonStateActive={true}
handleActiveState={null}
handleInactiveState={() => handleStartPayment}
activeButtonLabel='Buy for $1'
inactiveButtonLabel=''
/>
</View>
<TouchableOpacity style={styles.mockButton}
onPress={() => {
if (isMockReaderPresented) {
dismissMockReader();
} else {
presentMockReader();
}
}}
><Text style={styles.mockReaderText}>{isMockReaderPresented ? 'Hide Mock Reader' : 'Show Mock Reader'}</Text>
</TouchableOpacity>
</SafeAreaView>
);
}
};

const styles = StyleSheet.create({
iconContainer: {
position: 'absolute',
top: 0,
right: 10,
zIndex: 1,
container: {
flex: 1,
padding: 16,
backgroundColor: 'white',
},
header: {
flexDirection: 'row',
marginBottom: 50,
paddingLeft: 16,
paddingRight: 16
},
headerSpacer: {
flex: 4,
},
content: {
alignItems: 'center',
flex: 9,
paddingLeft: 16,
paddingRight: 16,
},
donutImage: {
width: 248,
height: 248,
marginBottom: 50,
},
title: {
fontSize: 24,
fontWeight: 'bold',
color: 'black',
marginBottom: 32,
},
mockButton: {
flex: 1,
alignItems: 'center',
},
mockReaderText: {
color: '#007BFF',
fontSize: 16,
fontWeight: 'bold',
},
});

export default HomeView;
Loading

0 comments on commit 321c941

Please sign in to comment.