Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[5.3] [IMPROVEMENT] Update SelectQRAccounts UI #4070

Merged
merged 29 commits into from
May 26, 2022
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
6dd2ea6
Convert class to functional component
Apr 8, 2022
edfab6d
Refactor withQRHardwareAwareness
Apr 11, 2022
6f68f14
Add new component AccountDetails
Apr 11, 2022
cade3a6
Update QR connect flow style
Apr 11, 2022
c074078
Merge branch 'main' into improv/keystone
Apr 11, 2022
58d6f28
Fix reference
Apr 12, 2022
521ffc8
Merge branch 'main' into improv/keystone
Apr 13, 2022
9ba07d7
Merge branch 'main' into improv/keystone
Apr 18, 2022
6f6509b
Solve conflicts
Apr 18, 2022
cf51fd5
Merge branch 'improv/keystone' of https://github.com/MetaMask/metamas…
Apr 18, 2022
7db9006
Fix ticker
Apr 19, 2022
52e8dd0
Merge branch 'main' into improv/keystone
Apr 19, 2022
1e8595a
Merge branch 'main' into improv/keystone
Apr 22, 2022
e07a7cc
Merge branch 'main' into improv/keystone
Apr 23, 2022
03e6849
Fix type error
Apr 23, 2022
a5a3465
Merge branch 'improv/keystone' of https://github.com/MetaMask/metamas…
Apr 23, 2022
a7c87c6
Merge branch 'main' into improv/keystone
Apr 25, 2022
d4e80ed
Merge branch 'main' into improv/keystone
Apr 26, 2022
afcdbcb
Update styles
Apr 27, 2022
fdd7b98
Update styles
Apr 27, 2022
5b61b2d
Merge branch 'main' into improv/keystone
Apr 27, 2022
78d7609
Solve conflicts
May 5, 2022
2ace7a9
Add default ticker
May 5, 2022
5f541fe
Optimize rendering with React.memo
May 6, 2022
0cd7c45
Move method to parent component
May 7, 2022
0bd3c4c
Remove unused props
May 7, 2022
885f59f
Solve conflicts
May 23, 2022
d17016e
Merge branch 'main' into improv/keystone
May 25, 2022
b0d4794
Merge branch 'main' into improv/keystone
May 26, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
65 changes: 28 additions & 37 deletions app/components/UI/QRHardware/withQRHardwareAwareness.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React, { Component, ComponentClass } from 'react';
import React, { useState, useEffect, useRef, ComponentClass } from 'react';
import Engine from '../../../core/Engine';
import { IQRState } from './types';

Expand All @@ -9,51 +9,42 @@ const withQRHardwareAwareness = (
isSyncingQRHardware?: boolean;
}>
) => {
class QRHardwareAwareness extends Component<any, any> {
state: {
QRState: IQRState;
} = {
QRState: {
sync: {
reading: false,
},
sign: {},
const QRHardwareAwareness = (props: any) => {
const keyringState: any = useRef();
const [QRState, SetQRState] = useState<IQRState>({
sync: {
reading: false,
},
};

keyringState: any;
sign: {},
});

subscribeKeyringState = (value: any) => {
this.setState({
QRState: value,
});
const subscribeKeyringState = (value: any) => {
SetQRState(value);
};

componentDidMount() {
useEffect(() => {
const { KeyringController } = Engine.context as any;
KeyringController.getQRKeyringState().then((store: any) => {
this.keyringState = store;
this.keyringState.subscribe(this.subscribeKeyringState);
keyringState.current = store;
keyringState.current.subscribe(subscribeKeyringState);
});
}
return () => {
if (keyringState) {
gantunesr marked this conversation as resolved.
Show resolved Hide resolved
keyringState.unsubscribe(subscribeKeyringState);
}
};
}, []);

componentWillUnmount() {
if (this.keyringState) {
this.keyringState.unsubscribe(this.subscribeKeyringState);
}
}
return (
<Children
{...props}
isSigningQRObject={!!QRState.sign?.request}
isSyncingQRHardware={QRState.sync.reading}
QRState={QRState}
/>
);
};

render() {
return (
<Children
{...this.props}
isSigningQRObject={!!this.state.QRState.sign?.request}
isSyncingQRHardware={this.state.QRState.sync.reading}
QRState={this.state.QRState}
/>
);
}
}
return QRHardwareAwareness;
};

Expand Down
77 changes: 77 additions & 0 deletions app/components/Views/ConnectQRHardware/AccountDetails/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
import React from 'react';
import { View, Text, StyleSheet } from 'react-native';
import { useNavigation } from '@react-navigation/native';
import Icon from 'react-native-vector-icons/EvilIcons';
import Device from '../../../../util/device';
import { getEtherscanAddressUrl } from '../../../../util/etherscan';
import { renderFromWei } from '../../../../util/number';
import { mockTheme, useAppThemeFromContext } from '../../../../util/theme';
import EthereumAddress from '../../../UI/EthereumAddress';

interface IAccountDetailsProps {
item: any;
network: string;
}

const createStyle = (colors: any) =>
StyleSheet.create({
rowContainer: {
flex: 1,
height: 65,
flexDirection: 'row',
justifyContent: 'space-between',
paddingLeft: Device.isIphoneX() ? 20 : 10,
},
accountDetails: {
justifyContent: 'flex-start',
},
linkIcon: {
height: '100%',
fontSize: 36,
textAlignVertical: 'center',
},
index: {
fontSize: 22,
color: colors.text.default,
},
information: {
color: colors.text.muted,
},
});

const AccountDetails = (props: IAccountDetailsProps) => {
const { colors } = useAppThemeFromContext() || mockTheme;
const styles = createStyle(colors);
const navigation = useNavigation();
const { item } = props;

const toEtherscan = (address: string) => {
const { network } = props;
const accountLink = getEtherscanAddressUrl(network, address);
navigation.navigate('Webview', {
screen: 'SimpleWebview',
params: {
url: accountLink,
},
});
};

return (
<View style={styles.rowContainer}>
<View style={styles.accountDetails}>
<Text style={styles.index}>{item.index}</Text>
<EthereumAddress style={styles.information} address={item.address} type={'short'} />
<Text style={styles.information}>{renderFromWei(item.balance)} ETH</Text>
</View>
<Icon
size={18}
name={'external-link'}
onPress={() => toEtherscan(item.address)}
style={styles.linkIcon}
color={colors.text.default}
/>
</View>
);
};

export default AccountDetails;
gantunesr marked this conversation as resolved.
Show resolved Hide resolved
59 changes: 16 additions & 43 deletions app/components/Views/ConnectQRHardware/SelectQRAccounts/index.tsx
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
import React from 'react';
import { View, Text, FlatList, StyleSheet, TouchableOpacity } from 'react-native';
import { strings } from '../../../../../locales/i18n';
import Icon from 'react-native-vector-icons/FontAwesome';
import { fontStyles } from '../../../../styles/common';
import CheckBox from '@react-native-community/checkbox';
import { IAccount } from '../types';
import { renderFromWei } from '../../../../util/number';
import { useSelector } from 'react-redux';
import { useNavigation } from '@react-navigation/native';
import { getEtherscanAddressUrl } from '../../../../util/etherscan';
import { fontStyles } from '../../../../styles/common';
import { strings } from '../../../../../locales/i18n';
import { IAccount } from '../types';
import Device from '../../../../util/device';
import { mockTheme, useAppThemeFromContext } from '../../../../util/theme';
import EthereumAddress from '../../../UI/EthereumAddress';
import AccountDetails from '../AccountDetails';
import StyledButton from '../../../UI/StyledButton';

interface ISelectQRAccountsProps {
Expand All @@ -26,6 +24,7 @@ interface ISelectQRAccountsProps {
const createStyle = (colors: any) =>
StyleSheet.create({
container: {
flex: 1,
width: '100%',
paddingHorizontal: 32,
},
Expand All @@ -38,19 +37,11 @@ const createStyle = (colors: any) =>
},
account: {
flexDirection: 'row',
alignItems: 'center',
height: 36,
width: '100%',
paddingVertical: 4,
paddingHorizontal: 12,
paddingVertical: 5,
},
checkBox: {
marginRight: 8,
},
accountUnchecked: {
backgroundColor: colors.primary.muted,
},
accountChecked: {
backgroundColor: colors.primary.disabled,
backgroundColor: colors.background.default,
},
number: {
...fontStyles.normal,
Expand All @@ -64,7 +55,6 @@ const createStyle = (colors: any) =>
color: colors.text.default,
},
pagination: {
marginTop: 16,
alignSelf: 'flex-end',
flexDirection: 'row',
alignItems: 'center',
Expand All @@ -81,33 +71,22 @@ const createStyle = (colors: any) =>
},
bottom: {
alignItems: 'center',
marginTop: 150,
height: 100,
justifyContent: 'space-between',
paddingTop: 75,
paddingBottom: Device.isIphoneX() ? 20 : 10,
},
button: {
width: '100%',
padding: 12,
justifyContent: 'flex-end',
},
});

const SelectQRAccounts = (props: ISelectQRAccountsProps) => {
const { accounts, prevPage, nextPage, toggleAccount, onForget, onUnlock, canUnlock } = props;
const { colors } = useAppThemeFromContext() || mockTheme;
const styles = createStyle(colors);
const navigation = useNavigation();
const provider = useSelector((state: any) => state.engine.backgroundState.NetworkController.provider);

const toEtherscan = (address: string) => {
const accountLink = getEtherscanAddressUrl(provider.type, address);
navigation.navigate('Webview', {
screen: 'SimpleWebview',
params: {
url: accountLink,
},
});
};

return (
<View style={styles.container}>
<Text style={styles.title}>{strings('connect_qr_hardware.select_accounts')}</Text>
Expand All @@ -123,17 +102,12 @@ const SelectQRAccounts = (props: ISelectQRAccountsProps) => {
onValueChange={() => toggleAccount(item.index)}
boxType={'square'}
tintColors={{ true: colors.primary.default, false: colors.border.default }}
onCheckColor={colors.background.default}
onFillColor={colors.primary.default}
onTintColor={colors.primary.default}
testID={'skip-backup-check'}
/>
<Text style={styles.number}>{item.index}</Text>
<EthereumAddress address={item.address} style={styles.address} type={'short'} />
<Text style={styles.address}>{renderFromWei(item.balance)} ETH</Text>
<Icon
size={18}
name={'external-link'}
onPress={() => toEtherscan(item.address)}
color={colors.text.default}
/>
<AccountDetails item={item} network={provider.type} />
</View>
)}
/>
Expand All @@ -147,7 +121,6 @@ const SelectQRAccounts = (props: ISelectQRAccountsProps) => {
<Icon name={'chevron-right'} color={colors.primary.default} />
</TouchableOpacity>
</View>

<View style={styles.bottom}>
<StyledButton
type={'confirm'}
Expand Down
33 changes: 15 additions & 18 deletions app/components/Views/ConnectQRHardware/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -28,31 +28,28 @@ const createStyles = (colors: any) =>
flexDirection: 'column',
alignItems: 'center',
},
navbarRightButton: {
alignSelf: 'flex-end',
paddingTop: 20,
paddingBottom: 10,
marginTop: Device.isIphoneX() ? 40 : 20,
},
closeIcon: {
fontSize: 28,
color: colors.text.default,
},
header: {
marginTop: Device.isIphoneX() ? 50 : 20,
flexDirection: 'row',
width: '100%',
paddingHorizontal: 32,
flexDirection: 'column',
alignItems: 'center',
},
close: {
alignSelf: 'flex-end',
width: 48,
navbarRightButton: {
flexDirection: 'row',
justifyContent: 'flex-end',
height: 48,
alignItems: 'center',
justifyContent: 'center',
width: 48,
flex: 1,
},
closeIcon: {
fontSize: 28,
color: colors.text.default,
},
qrcode: {
alignSelf: 'flex-start',
flex: 1,
flexDirection: 'row',
justifyContent: 'flex-start',
},
error: {
...fontStyles.normal,
Expand Down Expand Up @@ -255,10 +252,10 @@ const ConnectQRHardware = ({ navigation }: IConnectQRHardwareProps) => {
<Fragment>
<View style={styles.container}>
<View style={styles.header}>
<Icon name="qrcode" size={42} style={styles.qrcode} color={colors.text.default} />
<TouchableOpacity onPress={navigation.goBack} style={styles.navbarRightButton}>
<MaterialIcon name="close" size={15} style={styles.closeIcon} />
</TouchableOpacity>
<Icon name="qrcode" size={42} style={styles.qrcode} color={colors.text.default} />
</View>
{accounts.length <= 0 ? (
<ConnectQRInstruction
Expand Down