mirror of https://git.lenooby09.tech/LeNooby09/social-app.git
1import React, {useState} from 'react'
2import {Platform, StyleSheet, TouchableOpacity, View} from 'react-native'
3import {
4 FontAwesomeIcon,
5 FontAwesomeIconStyle,
6} from '@fortawesome/react-native-fontawesome'
7import {ScrollView, TextInput} from './util'
8import {Text} from '../util/text/Text'
9import {s, colors} from 'lib/styles'
10import {usePalette} from 'lib/hooks/usePalette'
11import {useTheme} from 'lib/ThemeContext'
12import {LOCAL_DEV_SERVICE, STAGING_SERVICE, PROD_SERVICE} from 'lib/constants'
13import {LOGIN_INCLUDE_DEV_SERVERS} from 'lib/build-flags'
14import {Trans, msg} from '@lingui/macro'
15import {useLingui} from '@lingui/react'
16import {useModalControls} from '#/state/modals'
17
18export const snapPoints = ['80%']
19
20export function Component({onSelect}: {onSelect: (url: string) => void}) {
21 const theme = useTheme()
22 const pal = usePalette('default')
23 const [customUrl, setCustomUrl] = useState<string>('')
24 const {_} = useLingui()
25 const {closeModal} = useModalControls()
26
27 const doSelect = (url: string) => {
28 if (!url.startsWith('http://') && !url.startsWith('https://')) {
29 url = `https://${url}`
30 }
31 closeModal()
32 onSelect(url)
33 }
34
35 return (
36 <View style={[pal.view, s.flex1]} testID="serverInputModal">
37 <Text type="2xl-bold" style={[pal.text, s.textCenter]}>
38 <Trans>Choose Service</Trans>
39 </Text>
40 <ScrollView style={styles.inner}>
41 <View style={styles.group}>
42 {LOGIN_INCLUDE_DEV_SERVERS ? (
43 <>
44 <TouchableOpacity
45 testID="localDevServerButton"
46 style={styles.btn}
47 onPress={() => doSelect(LOCAL_DEV_SERVICE)}
48 accessibilityRole="button">
49 <Text style={styles.btnText}>
50 <Trans>Local dev server</Trans>
51 </Text>
52 <FontAwesomeIcon
53 icon="arrow-right"
54 style={s.white as FontAwesomeIconStyle}
55 />
56 </TouchableOpacity>
57 <TouchableOpacity
58 style={styles.btn}
59 onPress={() => doSelect(STAGING_SERVICE)}
60 accessibilityRole="button">
61 <Text style={styles.btnText}>
62 <Trans>Staging</Trans>
63 </Text>
64 <FontAwesomeIcon
65 icon="arrow-right"
66 style={s.white as FontAwesomeIconStyle}
67 />
68 </TouchableOpacity>
69 </>
70 ) : undefined}
71 <TouchableOpacity
72 style={styles.btn}
73 onPress={() => doSelect(PROD_SERVICE)}
74 accessibilityRole="button"
75 accessibilityLabel={_(msg`Select Bluesky Social`)}
76 accessibilityHint="Sets Bluesky Social as your service provider">
77 <Text style={styles.btnText}>
78 <Trans>Bluesky.Social</Trans>
79 </Text>
80 <FontAwesomeIcon
81 icon="arrow-right"
82 style={s.white as FontAwesomeIconStyle}
83 />
84 </TouchableOpacity>
85 </View>
86 <View style={styles.group}>
87 <Text style={[pal.text, styles.label]}>
88 <Trans>Other service</Trans>
89 </Text>
90 <View style={s.flexRow}>
91 <TextInput
92 testID="customServerTextInput"
93 style={[pal.borderDark, pal.text, styles.textInput]}
94 placeholder="e.g. https://bsky.app"
95 placeholderTextColor={colors.gray4}
96 autoCapitalize="none"
97 autoComplete="off"
98 autoCorrect={false}
99 keyboardAppearance={theme.colorScheme}
100 value={customUrl}
101 onChangeText={setCustomUrl}
102 accessibilityLabel={_(msg`Custom domain`)}
103 // TODO: Simplify this wording further to be understandable by everyone
104 accessibilityHint="Use your domain as your Bluesky client service provider"
105 />
106 <TouchableOpacity
107 testID="customServerSelectBtn"
108 style={[pal.borderDark, pal.text, styles.textInputBtn]}
109 onPress={() => doSelect(customUrl)}
110 accessibilityRole="button"
111 accessibilityLabel={`Confirm service. ${
112 customUrl === ''
113 ? 'Button disabled. Input custom domain to proceed.'
114 : ''
115 }`}
116 accessibilityHint=""
117 // TODO - accessibility: Need to inform state change on failure
118 disabled={customUrl === ''}>
119 <FontAwesomeIcon
120 icon="check"
121 style={[pal.text as FontAwesomeIconStyle, styles.checkIcon]}
122 size={18}
123 />
124 </TouchableOpacity>
125 </View>
126 </View>
127 </ScrollView>
128 </View>
129 )
130}
131
132const styles = StyleSheet.create({
133 inner: {
134 padding: 14,
135 },
136 group: {
137 marginBottom: 20,
138 },
139 label: {
140 fontWeight: 'bold',
141 paddingHorizontal: 4,
142 paddingBottom: 4,
143 },
144 textInput: {
145 flex: 1,
146 borderWidth: 1,
147 borderTopLeftRadius: 6,
148 borderBottomLeftRadius: 6,
149 paddingHorizontal: 14,
150 paddingVertical: 12,
151 fontSize: 16,
152 },
153 textInputBtn: {
154 borderWidth: 1,
155 borderLeftWidth: 0,
156 borderTopRightRadius: 6,
157 borderBottomRightRadius: 6,
158 paddingHorizontal: 14,
159 paddingVertical: 10,
160 },
161 btn: {
162 flexDirection: 'row',
163 alignItems: 'center',
164 backgroundColor: colors.blue3,
165 borderRadius: 6,
166 paddingHorizontal: 14,
167 paddingVertical: 10,
168 marginBottom: 6,
169 },
170 btnText: {
171 flex: 1,
172 fontSize: 18,
173 fontWeight: '500',
174 color: colors.white,
175 },
176 checkIcon: {
177 position: 'relative',
178 ...Platform.select({
179 android: {
180 top: 8,
181 },
182 ios: {
183 top: 2,
184 },
185 }),
186 },
187})