ソースを参照

Introduce SafeArea for Settings and Header

master
zbettenbuk 7年前
コミット
9a9890f86c
24個のファイルの変更398行の追加384行の削除
  1. 0
    1
      android/app/src/main/res/values/styles.xml
  2. 4
    2
      lang/main.json
  3. 2
    2
      react/features/app-settings/actionTypes.js
  4. 2
    2
      react/features/app-settings/actions.js
  5. 1
    7
      react/features/app-settings/components/AbstractAppSettings.js
  6. 83
    103
      react/features/app-settings/components/AppSettings.native.js
  7. 0
    117
      react/features/app-settings/components/FormSectionHeader.native.js
  8. 1
    0
      react/features/app-settings/components/_.native.js
  9. 0
    0
      react/features/app-settings/components/_.web.js
  10. 4
    5
      react/features/app-settings/components/native/BackButton.js
  11. 8
    39
      react/features/app-settings/components/native/FormRow.js
  12. 60
    0
      react/features/app-settings/components/native/FormSectionHeader.js
  13. 3
    0
      react/features/app-settings/components/native/index.js
  14. 83
    0
      react/features/app-settings/components/native/styles.js
  15. 4
    104
      react/features/app-settings/components/styles.js
  16. 56
    0
      react/features/base/react/components/native/Header.js
  17. 2
    0
      react/features/base/react/components/native/index.js
  18. 39
    0
      react/features/base/react/components/native/styles.js
  19. 0
    1
      react/features/base/react/index.js
  20. 1
    0
      react/features/base/styles/components/styles/ColorPalette.js
  21. 42
    0
      react/features/base/styles/components/styles/PlatformElements.native.js
  22. 0
    0
      react/features/base/styles/components/styles/PlatformElements.web.js
  23. 1
    0
      react/features/base/styles/components/styles/index.js
  24. 2
    1
      react/features/conference/components/Conference.native.js

+ 0
- 1
android/app/src/main/res/values/styles.xml ファイルの表示

@@ -2,6 +2,5 @@
2 2
     <!-- Base application theme. -->
3 3
     <style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
4 4
         <!-- Customize your theme here. -->
5
-        <item name="android:windowTranslucentStatus">true</item>
6 5
     </style>
7 6
 </resources>

+ 4
- 2
lang/main.json ファイルの表示

@@ -47,13 +47,15 @@
47 47
     },
48 48
     "welcomepage":{
49 49
         "appDescription": "Go ahead, video chat with the whole team. In fact, invite everyone you know. __app__ is a fully encrypted, 100% open source video conferencing solution that you can use all day, every day, for free — with no account needed.",
50
+        "audioOnlyLabel": "Voice",
50 51
         "go": "GO",
51 52
         "join": "JOIN",
52 53
         "privacy": "Privacy",
53 54
         "roomname": "Enter room name",
54 55
         "sendFeedback": "Send feedback",
55 56
         "terms": "Terms",
56
-        "title": "More secure, more flexible, and completely free video conferencing"
57
+        "title": "More secure, more flexible, and completely free video conferencing",
58
+        "videoEnabledLabel": "Video"
57 59
     },
58 60
     "startupoverlay": {
59 61
         "policyText": " ",
@@ -500,7 +502,7 @@
500 502
         "title": "Call info",
501 503
         "tooltip": "Get access info about the meeting"
502 504
     },
503
-    "profileModal": {
505
+    "settingsScreen": {
504 506
         "alertOk": "OK",
505 507
         "alertTitle": "Warning",
506 508
         "alertURLText": "The entered server URL is invalid",

+ 2
- 2
react/features/app-settings/actionTypes.js ファイルの表示

@@ -1,6 +1,6 @@
1 1
 /**
2 2
  * The type of (redux) action which signals the request
3
- * to hide the app settings modal.
3
+ * to hide the app settings screen.
4 4
  *
5 5
  * {
6 6
  *     type: HIDE_APP_SETTINGS
@@ -10,7 +10,7 @@ export const HIDE_APP_SETTINGS = Symbol('HIDE_APP_SETTINGS');
10 10
 
11 11
 /**
12 12
  * The type of (redux) action which signals the request
13
- * to show the app settings modal where available.
13
+ * to show the app settings screen where available.
14 14
  *
15 15
  * {
16 16
  *     type: SHOW_APP_SETTINGS

+ 2
- 2
react/features/app-settings/actions.js ファイルの表示

@@ -3,7 +3,7 @@
3 3
 import { HIDE_APP_SETTINGS, SHOW_APP_SETTINGS } from './actionTypes';
4 4
 
5 5
 /**
6
- * Redux-signals the request to hide the app settings modal.
6
+ * Redux-signals the request to hide the app settings screen.
7 7
  *
8 8
  * @returns {{
9 9
  *     type: HIDE_APP_SETTINGS
@@ -16,7 +16,7 @@ export function hideAppSettings() {
16 16
 }
17 17
 
18 18
 /**
19
- * Redux-signals the request to open the app settings modal.
19
+ * Redux-signals the request to open the app settings screen.
20 20
  *
21 21
  * @returns {{
22 22
  *     type: SHOW_APP_SETTINGS

+ 1
- 7
react/features/app-settings/components/AbstractAppSettings.js ファイルの表示

@@ -9,11 +9,6 @@ import { getProfile, updateProfile } from '../../base/profile';
9 9
  */
10 10
 type Props = {
11 11
 
12
-    /**
13
-     * The current aspect ratio of the screen.
14
-     */
15
-    _aspectRatio: Symbol,
16
-
17 12
     /**
18 13
      * The current profile object.
19 14
      */
@@ -25,7 +20,7 @@ type Props = {
25 20
     _serverURL: string,
26 21
 
27 22
     /**
28
-     * The visibility prop of the settings modal.
23
+     * The visibility prop of the settings screen.
29 24
      */
30 25
     _visible: boolean,
31 26
 
@@ -173,7 +168,6 @@ export function _mapStateToProps(state: Object) {
173 168
     const _profile = getProfile(state);
174 169
 
175 170
     return {
176
-        _aspectRatio: state['features/base/responsive-ui'].aspectRatio,
177 171
         _profile,
178 172
         _serverURL,
179 173
         _visible: state['features/app-settings'].visible

+ 83
- 103
react/features/app-settings/components/AppSettings.native.js ファイルの表示

@@ -4,6 +4,7 @@ import React from 'react';
4 4
 import {
5 5
     Alert,
6 6
     Modal,
7
+    SafeAreaView,
7 8
     ScrollView,
8 9
     Switch,
9 10
     Text,
@@ -13,16 +14,15 @@ import {
13 14
 import { connect } from 'react-redux';
14 15
 
15 16
 import { translate } from '../../base/i18n';
16
-import { getSafetyOffset, isIPad } from '../../base/react';
17
-import { ASPECT_RATIO_NARROW } from '../../base/responsive-ui';
17
+import { Header } from '../../base/react';
18
+import { PlatformElements } from '../../base/styles';
18 19
 
19
-import { _mapStateToProps, AbstractAppSettings } from './AbstractAppSettings';
20 20
 import { hideAppSettings } from '../actions';
21
-import BackButton from './BackButton.native';
22
-import FormRow from './FormRow.native';
23
-import FormSectionHeader from './FormSectionHeader.native';
24 21
 import { normalizeUserInputURL } from '../functions';
25
-import styles, { HEADER_PADDING } from './styles';
22
+
23
+import { BackButton, FormRow, FormSectionHeader } from './_';
24
+import { _mapStateToProps, AbstractAppSettings } from './AbstractAppSettings';
25
+import styles from './styles';
26 26
 
27 27
 /**
28 28
  * The native container rendering the app settings page.
@@ -40,7 +40,6 @@ class AppSettings extends AbstractAppSettings {
40 40
     constructor(props) {
41 41
         super(props);
42 42
 
43
-        this._getSafetyPadding = this._getSafetyPadding.bind(this);
44 43
         this._onBlurServerURL = this._onBlurServerURL.bind(this);
45 44
         this._onRequestClose = this._onRequestClose.bind(this);
46 45
         this._setURLFieldReference = this._setURLFieldReference.bind(this);
@@ -56,110 +55,91 @@ class AppSettings extends AbstractAppSettings {
56 55
     render() {
57 56
         const { _profile, t } = this.props;
58 57
 
59
-        // FIXME: presentationStyle is added to workaround orientation issue on
60
-        // iOS
61
-
62 58
         return (
63 59
             <Modal
64 60
                 animationType = 'slide'
65 61
                 onRequestClose = { this._onRequestClose }
66
-                presentationStyle = 'overFullScreen'
62
+                presentationStyle = 'fullScreen'
67 63
                 supportedOrientations = { [
68 64
                     'landscape',
69 65
                     'portrait'
70 66
                 ] }
71 67
                 visible = { this.props._visible }>
72
-                <View
73
-                    style = { [
74
-                        styles.headerContainer,
75
-                        this._getSafetyPadding()
76
-                    ] } >
77
-                    <BackButton
78
-                        onPress = { this._onRequestClose }
79
-                        style = { styles.settingsBackButton } />
80
-                    <Text style = { [ styles.text, styles.headerTitle ] } >
81
-                        { t('profileModal.header') }
82
-                    </Text>
68
+                <View style = { PlatformElements.page }>
69
+                    <Header>
70
+                        <BackButton
71
+                            onPress = { this._onRequestClose } />
72
+                        <Text
73
+                            style = { [
74
+                                styles.text,
75
+                                PlatformElements.headerText
76
+                            ] } >
77
+                            { t('settingsScreen.header') }
78
+                        </Text>
79
+                    </Header>
80
+                    <SafeAreaView style = { styles.settingsForm }>
81
+                        <ScrollView>
82
+                            <FormSectionHeader
83
+                                i18nLabel = 'settingsScreen.profileSection' />
84
+                            <FormRow
85
+                                fieldSeparator = { true }
86
+                                i18nLabel = 'settingsScreen.displayName' >
87
+                                <TextInput
88
+                                    onChangeText = { this._onChangeDisplayName }
89
+                                    placeholder = 'John Doe'
90
+                                    value = { _profile.displayName } />
91
+                            </FormRow>
92
+                            <FormRow
93
+                                i18nLabel = 'settingsScreen.email' >
94
+                                <TextInput
95
+                                    keyboardType = { 'email-address' }
96
+                                    onChangeText = { this._onChangeEmail }
97
+                                    placeholder = 'email@example.com'
98
+                                    value = { _profile.email } />
99
+                            </FormRow>
100
+                            <FormSectionHeader
101
+                                i18nLabel
102
+                                    = 'settingsScreen.conferenceSection' />
103
+                            <FormRow
104
+                                fieldSeparator = { true }
105
+                                i18nLabel = 'settingsScreen.serverURL' >
106
+                                <TextInput
107
+                                    autoCapitalize = 'none'
108
+                                    onBlur = { this._onBlurServerURL }
109
+                                    onChangeText = { this._onChangeServerURL }
110
+                                    placeholder = { this.props._serverURL }
111
+                                    value = { _profile.serverURL } />
112
+                            </FormRow>
113
+                            <FormRow
114
+                                fieldSeparator = { true }
115
+                                i18nLabel
116
+                                    = 'settingsScreen.startWithAudioMuted' >
117
+                                <Switch
118
+                                    onValueChange = {
119
+                                        this._onStartAudioMutedChange
120
+                                    }
121
+                                    value = {
122
+                                        _profile.startWithAudioMuted
123
+                                    } />
124
+                            </FormRow>
125
+                            <FormRow
126
+                                i18nLabel
127
+                                    = 'settingsScreen.startWithVideoMuted' >
128
+                                <Switch
129
+                                    onValueChange = {
130
+                                        this._onStartVideoMutedChange
131
+                                    }
132
+                                    value = {
133
+                                        _profile.startWithVideoMuted
134
+                                    } />
135
+                            </FormRow>
136
+                        </ScrollView>
137
+                    </SafeAreaView>
83 138
                 </View>
84
-                <ScrollView style = { styles.settingsContainer } >
85
-                    <FormSectionHeader
86
-                        i18nLabel = 'profileModal.profileSection' />
87
-                    <FormRow
88
-                        fieldSeparator = { true }
89
-                        i18nLabel = 'profileModal.displayName' >
90
-                        <TextInput
91
-                            onChangeText = { this._onChangeDisplayName }
92
-                            placeholder = 'John Doe'
93
-                            value = { _profile.displayName } />
94
-                    </FormRow>
95
-                    <FormRow
96
-                        i18nLabel = 'profileModal.email' >
97
-                        <TextInput
98
-                            keyboardType = { 'email-address' }
99
-                            onChangeText = { this._onChangeEmail }
100
-                            placeholder = 'email@example.com'
101
-                            value = { _profile.email } />
102
-                    </FormRow>
103
-                    <FormSectionHeader
104
-                        i18nLabel = 'profileModal.conferenceSection' />
105
-                    <FormRow
106
-                        fieldSeparator = { true }
107
-                        i18nLabel = 'profileModal.serverURL' >
108
-                        <TextInput
109
-                            autoCapitalize = 'none'
110
-                            onBlur = { this._onBlurServerURL }
111
-                            onChangeText = { this._onChangeServerURL }
112
-                            placeholder = { this.props._serverURL }
113
-                            ref = { this._setURLFieldReference }
114
-                            value = { _profile.serverURL } />
115
-                    </FormRow>
116
-                    <FormRow
117
-                        fieldSeparator = { true }
118
-                        i18nLabel = 'profileModal.startWithAudioMuted' >
119
-                        <Switch
120
-                            onValueChange = {
121
-                                this._onStartAudioMutedChange
122
-                            }
123
-                            value = {
124
-                                _profile.startWithAudioMuted
125
-                            } />
126
-                    </FormRow>
127
-                    <FormRow
128
-                        i18nLabel = 'profileModal.startWithVideoMuted' >
129
-                        <Switch
130
-                            onValueChange = {
131
-                                this._onStartVideoMutedChange
132
-                            }
133
-                            value = {
134
-                                _profile.startWithVideoMuted
135
-                            } />
136
-                    </FormRow>
137
-                </ScrollView>
138 139
             </Modal>
139 140
         );
140 141
     }
141 142
 
142
-    _getSafetyPadding: () => Object;
143
-
144
-    /**
145
-     * Calculates header safety padding for mobile devices. See comment in
146
-     * functions.js.
147
-     *
148
-     * @private
149
-     * @returns {Object}
150
-     */
151
-    _getSafetyPadding() {
152
-        if (isIPad() || this.props._aspectRatio === ASPECT_RATIO_NARROW) {
153
-            const safeOffset = Math.max(getSafetyOffset(), HEADER_PADDING);
154
-
155
-            return {
156
-                paddingTop: safeOffset
157
-            };
158
-        }
159
-
160
-        return undefined;
161
-    }
162
-
163 143
     _onBlurServerURL: () => void;
164 144
 
165 145
     /**
@@ -183,8 +163,6 @@ class AppSettings extends AbstractAppSettings {
183 163
 
184 164
     _onStartVideoMutedChange: (boolean) => void;
185 165
 
186
-    _onRequestClose: () => void;
187
-
188 166
     /**
189 167
      * Processes the server URL. It normalizes it and an error alert is
190 168
      * displayed in case it's incorrect.
@@ -208,6 +186,8 @@ class AppSettings extends AbstractAppSettings {
208 186
         }
209 187
     }
210 188
 
189
+    _onRequestClose: () => void;
190
+
211 191
     /**
212 192
      * Handles the back button.
213 193
      * Also invokes normalizeUserInputURL to validate the URL entered
@@ -243,12 +223,12 @@ class AppSettings extends AbstractAppSettings {
243 223
         const { t } = this.props;
244 224
 
245 225
         Alert.alert(
246
-            t('profileModal.alertTitle'),
247
-            t('profileModal.alertURLText'),
226
+            t('settingsScreen.alertTitle'),
227
+            t('settingsScreen.alertURLText'),
248 228
             [
249 229
                 {
250 230
                     onPress: () => this._urlField.focus(),
251
-                    text: t('profileModal.alertOk')
231
+                    text: t('settingsScreen.alertOk')
252 232
                 }
253 233
             ]
254 234
         );

+ 0
- 117
react/features/app-settings/components/FormSectionHeader.native.js ファイルの表示

@@ -1,117 +0,0 @@
1
-// @flow
2
-
3
-import React, { Component } from 'react';
4
-import { Text, View } from 'react-native';
5
-import { connect } from 'react-redux';
6
-
7
-import { translate } from '../../base/i18n';
8
-import { getSafetyOffset } from '../../base/react';
9
-import { ASPECT_RATIO_WIDE } from '../../base/responsive-ui';
10
-
11
-import styles, { CONTAINER_PADDING } from './styles';
12
-
13
-/**
14
- * The type of the React {@code Component} props of {@link FormSectionHeader}
15
- */
16
-type Props = {
17
-
18
-    /**
19
-     * The current aspect ratio of the screen.
20
-     */
21
-    _aspectRatio: Symbol,
22
-
23
-    /**
24
-     * The i18n key of the text label of the section.
25
-     */
26
-    i18nLabel: string,
27
-
28
-    /**
29
-     * An external style object passed to the component.
30
-     */
31
-    style: Object,
32
-
33
-    /**
34
-     * Invoked to obtain translated strings.
35
-     */
36
-    t: Function
37
-}
38
-
39
-/**
40
- * Implements a React {@code Component} which renders a section header on a
41
- * form. This calculates the available safe view as well.
42
- */
43
-class FormSectionHeader extends Component<Props> {
44
-    /**
45
-     * Initializes a new {@code FormSectionHeader} instance.
46
-     *
47
-     * @param {Object} props - Component properties.
48
-     */
49
-    constructor(props) {
50
-        super(props);
51
-
52
-        this._getSafetyMargin = this._getSafetyMargin.bind(this);
53
-    }
54
-
55
-    /**
56
-     * Implements React's {@link Component#render()}.
57
-     *
58
-     * @inheritdoc
59
-     * @override
60
-     * @returns {ReactElement}
61
-     */
62
-    render() {
63
-        const { t } = this.props;
64
-
65
-        return (
66
-            <View
67
-                style = { [
68
-                    styles.formSectionTitle,
69
-                    this.props.style,
70
-                    this._getSafetyMargin()
71
-                ] } >
72
-                <Text>
73
-                    { t(this.props.i18nLabel) }
74
-                </Text>
75
-            </View>
76
-        );
77
-    }
78
-
79
-    _getSafetyMargin: () => Object;
80
-
81
-    /**
82
-     * Calculates the safety margin for this header. See comment in
83
-     * functions.js.
84
-     *
85
-     * @private
86
-     * @returns {Object}
87
-     */
88
-    _getSafetyMargin() {
89
-        if (this.props._aspectRatio === ASPECT_RATIO_WIDE) {
90
-            const safeOffset
91
-                = Math.max(getSafetyOffset() - CONTAINER_PADDING, 0);
92
-
93
-            return {
94
-                marginLeft: safeOffset,
95
-                marginRight: safeOffset
96
-            };
97
-        }
98
-
99
-        return undefined;
100
-    }
101
-}
102
-
103
-/**
104
- * Maps (parts of) the redux state to the React {@code Component} props of
105
- * {@code FormSectionHeader}.
106
- *
107
- * @param {Object} state - The redux state.
108
- * @protected
109
- * @returns {Object}
110
- */
111
-export function _mapStateToProps(state: Object) {
112
-    return {
113
-        _aspectRatio: state['features/base/responsive-ui'].aspectRatio
114
-    };
115
-}
116
-
117
-export default translate(connect(_mapStateToProps)(FormSectionHeader));

+ 1
- 0
react/features/app-settings/components/_.native.js ファイルの表示

@@ -0,0 +1 @@
1
+export * from './native';

react/features/base/react/functions.web.js → react/features/app-settings/components/_.web.js ファイルの表示


react/features/app-settings/components/BackButton.native.js → react/features/app-settings/components/native/BackButton.js ファイルの表示

@@ -3,9 +3,8 @@
3 3
 import React, { Component } from 'react';
4 4
 import { TouchableOpacity } from 'react-native';
5 5
 
6
-import { Icon } from '../../base/font-icons';
7
-
8
-import styles from './styles';
6
+import { Icon } from '../../../base/font-icons';
7
+import { PlatformElements } from '../../../base/styles';
9 8
 
10 9
 /**
11 10
  * The type of the React {@code Component} props of {@link BackButton}
@@ -20,7 +19,7 @@ type Props = {
20 19
     /**
21 20
      * An external style object passed to the component.
22 21
      */
23
-    style: Object
22
+    style?: Object
24 23
 };
25 24
 
26 25
 /**
@@ -41,7 +40,7 @@ export default class BackButton extends Component<Props> {
41 40
                 <Icon
42 41
                     name = { 'arrow_back' }
43 42
                     style = { [
44
-                        styles.backIcon,
43
+                        PlatformElements.headerButton,
45 44
                         this.props.style
46 45
                     ] } />
47 46
             </TouchableOpacity>

react/features/app-settings/components/FormRow.native.js → react/features/app-settings/components/native/FormRow.js ファイルの表示

@@ -2,24 +2,16 @@
2 2
 
3 3
 import React, { Component } from 'react';
4 4
 import { Text, View } from 'react-native';
5
-import { connect } from 'react-redux';
6 5
 
7
-import { translate } from '../../base/i18n';
8
-import { getSafetyOffset } from '../../base/react';
9
-import { ASPECT_RATIO_WIDE } from '../../base/responsive-ui';
6
+import { translate } from '../../../base/i18n';
10 7
 
11
-import styles, { ANDROID_UNDERLINE_COLOR, CONTAINER_PADDING } from './styles';
8
+import styles, { ANDROID_UNDERLINE_COLOR } from './styles';
12 9
 
13 10
 /**
14 11
  * The type of the React {@code Component} props of {@link FormRow}
15 12
  */
16 13
 type Props = {
17 14
 
18
-    /**
19
-     * The current aspect ratio of the screen.
20
-     */
21
-    _aspectRatio: Symbol,
22
-
23 15
     /**
24 16
      *
25 17
      */
@@ -80,7 +72,10 @@ class FormRow extends Component<Props> {
80 72
             <View
81 73
                 style = { this._getRowStyle() } >
82 74
                 <View style = { styles.fieldLabelContainer } >
83
-                    <Text style = { styles.text } >
75
+                    <Text
76
+                        style = { [
77
+                            styles.text, styles.fieldLabelText
78
+                        ] } >
84 79
                         { t(this.props.i18nLabel) }
85 80
                     </Text>
86 81
                 </View>
@@ -122,8 +117,7 @@ class FormRow extends Component<Props> {
122 117
     _getRowStyle: () => Array<Object>;
123 118
 
124 119
     /**
125
-     * Assembles the row style array based on the row's props. For padding, see
126
-     * comment in functions.js.
120
+     * Assembles the row style array based on the row's props.
127 121
      *
128 122
      * @private
129 123
      * @returns {Array<Object>}
@@ -137,33 +131,8 @@ class FormRow extends Component<Props> {
137 131
             rowStyle.push(styles.fieldSeparator);
138 132
         }
139 133
 
140
-        if (this.props._aspectRatio === ASPECT_RATIO_WIDE) {
141
-            const safeOffset = Math.max(
142
-                getSafetyOffset() - CONTAINER_PADDING, 0
143
-            );
144
-
145
-            rowStyle.push({
146
-                marginLeft: safeOffset,
147
-                marginRight: safeOffset
148
-            });
149
-        }
150
-
151 134
         return rowStyle;
152 135
     }
153 136
 }
154 137
 
155
-/**
156
- * Maps (parts of) the redux state to the React {@code Component} props of
157
- * {@code FormRow}.
158
- *
159
- * @param {Object} state - The redux state.
160
- * @protected
161
- * @returns {Object}
162
- */
163
-export function _mapStateToProps(state: Object) {
164
-    return {
165
-        _aspectRatio: state['features/base/responsive-ui'].aspectRatio
166
-    };
167
-}
168
-
169
-export default translate(connect(_mapStateToProps)(FormRow));
138
+export default translate(FormRow);

+ 60
- 0
react/features/app-settings/components/native/FormSectionHeader.js ファイルの表示

@@ -0,0 +1,60 @@
1
+// @flow
2
+
3
+import React, { Component } from 'react';
4
+import { Text, View } from 'react-native';
5
+
6
+import { translate } from '../../../base/i18n';
7
+
8
+import styles from './styles';
9
+
10
+/**
11
+ * The type of the React {@code Component} props of {@link FormSectionHeader}
12
+ */
13
+type Props = {
14
+
15
+    /**
16
+     * The i18n key of the text label of the section.
17
+     */
18
+    i18nLabel: string,
19
+
20
+    /**
21
+     * An external style object passed to the component.
22
+     */
23
+    style: Object,
24
+
25
+    /**
26
+     * Invoked to obtain translated strings.
27
+     */
28
+    t: Function
29
+}
30
+
31
+/**
32
+ * Implements a React {@code Component} which renders a section header on a
33
+ * form.
34
+ */
35
+class FormSectionHeader extends Component<Props> {
36
+    /**
37
+     * Implements React's {@link Component#render()}.
38
+     *
39
+     * @inheritdoc
40
+     * @override
41
+     * @returns {ReactElement}
42
+     */
43
+    render() {
44
+        const { i18nLabel, style, t } = this.props;
45
+
46
+        return (
47
+            <View
48
+                style = { [
49
+                    styles.formSectionTitle,
50
+                    style
51
+                ] } >
52
+                <Text>
53
+                    { t(i18nLabel) }
54
+                </Text>
55
+            </View>
56
+        );
57
+    }
58
+}
59
+
60
+export default translate(FormSectionHeader);

+ 3
- 0
react/features/app-settings/components/native/index.js ファイルの表示

@@ -0,0 +1,3 @@
1
+export { default as BackButton } from './BackButton';
2
+export { default as FormRow } from './FormRow';
3
+export { default as FormSectionHeader } from './FormSectionHeader';

+ 83
- 0
react/features/app-settings/components/native/styles.js ファイルの表示

@@ -0,0 +1,83 @@
1
+import {
2
+    ColorPalette,
3
+    createStyleSheet
4
+} from '../../../base/styles';
5
+
6
+export const ANDROID_UNDERLINE_COLOR = 'transparent';
7
+const TEXT_SIZE = 17;
8
+
9
+/**
10
+ * The styles of the native components of the feature
11
+ * {@code app-settings}.
12
+ */
13
+export default createStyleSheet({
14
+    /**
15
+     * Standardized style for a field container {@code View}.
16
+     */
17
+    fieldContainer: {
18
+        alignItems: 'center',
19
+        flexDirection: 'row',
20
+        minHeight: 65,
21
+        paddingHorizontal: 8
22
+    },
23
+
24
+    /**
25
+     * Standard container for a {@code View} containing a field label.
26
+     */
27
+    fieldLabelContainer: {
28
+        alignItems: 'center',
29
+        flexDirection: 'row',
30
+        marginRight: 5
31
+    },
32
+
33
+    /**
34
+     * Text of the field labels on the form.
35
+     */
36
+    fieldLabelText: {
37
+        fontSize: TEXT_SIZE
38
+    },
39
+
40
+    /**
41
+     * Field container style for all but last row {@code View}.
42
+     */
43
+    fieldSeparator: {
44
+        borderBottomWidth: 1,
45
+        borderColor: 'rgba(0, 0, 0, 0.1)'
46
+    },
47
+
48
+    /**
49
+     * Style for the {@code View} containing each
50
+     * field values (the actual field).
51
+     */
52
+    fieldValueContainer: {
53
+        alignItems: 'center',
54
+        flex: 1,
55
+        flexDirection: 'row',
56
+        justifyContent: 'flex-end'
57
+    },
58
+
59
+    /**
60
+     * Style fo the form section separator titles.
61
+     */
62
+    formSectionTitle: {
63
+        backgroundColor: 'rgba(0, 0, 0, 0.1)',
64
+        marginTop: 5,
65
+        padding: 5
66
+    },
67
+
68
+    /**
69
+     * Global {@code Text} color for the components.
70
+     */
71
+    text: {
72
+        color: ColorPalette.black
73
+    },
74
+
75
+    /**
76
+     * Standard text input field style.
77
+     */
78
+    textInputField: {
79
+        flex: 1,
80
+        fontSize: TEXT_SIZE,
81
+        textAlign: 'right'
82
+    }
83
+});

+ 4
- 104
react/features/app-settings/components/styles.js ファイルの表示

@@ -4,90 +4,11 @@ import {
4 4
     createStyleSheet
5 5
 } from '../../base/styles';
6 6
 
7
-export const ANDROID_UNDERLINE_COLOR = 'transparent';
8
-export const CONTAINER_PADDING = 2 * BoxModel.padding;
9
-export const HEADER_COLOR = ColorPalette.blue;
10
-export const HEADER_PADDING = BoxModel.padding;
11
-const TEXT_SIZE = 17;
12
-
13 7
 /**
14 8
  * The styles of the React {@code Components} of the feature
15 9
  * {@code app-settings}.
16 10
  */
17 11
 export default createStyleSheet({
18
-
19
-    /**
20
-     * The back button style.
21
-     */
22
-    backIcon: {
23
-        alignSelf: 'center',
24
-        fontSize: 26,
25
-        padding: 8,
26
-        paddingRight: 22
27
-    },
28
-
29
-    /**
30
-     * Standardized style for a field container {@code View}.
31
-     */
32
-    fieldContainer: {
33
-        alignItems: 'center',
34
-        flexDirection: 'row',
35
-        minHeight: 65
36
-    },
37
-
38
-    /**
39
-     * Standard container for a {@code View} containing a field label.
40
-     */
41
-    fieldLabelContainer: {
42
-        alignItems: 'center',
43
-        flexDirection: 'row',
44
-        marginRight: 5
45
-    },
46
-
47
-    /**
48
-     * Field container style for all but last row {@code View}.
49
-     */
50
-    fieldSeparator: {
51
-        borderBottomWidth: 1,
52
-        borderColor: 'rgba(0, 0, 0, 0.1)'
53
-    },
54
-
55
-    /**
56
-     * Style for the {@code View} containing each
57
-     * field values (the actual field).
58
-     */
59
-    fieldValueContainer: {
60
-        alignItems: 'center',
61
-        flex: 1,
62
-        flexDirection: 'row',
63
-        justifyContent: 'flex-end'
64
-    },
65
-
66
-    formSectionTitle: {
67
-        backgroundColor: 'rgba(0, 0, 0, 0.1)',
68
-        marginTop: 5,
69
-        padding: 5
70
-    },
71
-
72
-    /**
73
-     * Page header {@code View}.
74
-     */
75
-    headerContainer: {
76
-        alignItems: 'center',
77
-        backgroundColor: HEADER_COLOR,
78
-        flexDirection: 'row',
79
-        justifyContent: 'flex-start',
80
-        padding: HEADER_PADDING
81
-    },
82
-
83
-    /**
84
-     * The title {@code Text} of the header.
85
-     */
86
-    headerTitle: {
87
-        color: ColorPalette.white,
88
-        fontSize: 22
89
-    },
90
-
91 12
     /**
92 13
      * Style of the ScrollView to be able to scroll the content.
93 14
      */
@@ -96,38 +17,17 @@ export default createStyleSheet({
96 17
     },
97 18
 
98 19
     /**
99
-     * The back button style on the settings screen.
100
-     */
101
-    settingsBackButton: {
102
-        color: ColorPalette.white
103
-    },
104
-
105
-    /**
106
-     * The top level container {@code View}.
20
+     * Style of the settings screen content (form).
107 21
      */
108
-    settingsContainer: {
109
-        backgroundColor: ColorPalette.white,
22
+    settingsForm: {
110 23
         flex: 1,
111
-        flexDirection: 'column',
112
-        margin: 0,
113
-        padding: CONTAINER_PADDING,
114
-        paddingTop: 0
24
+        margin: BoxModel.margin
115 25
     },
116 26
 
117 27
     /**
118 28
      * Global {@code Text} color for the page.
119 29
      */
120 30
     text: {
121
-        color: ColorPalette.black,
122
-        fontSize: TEXT_SIZE
123
-    },
124
-
125
-    /**
126
-     * Standard text input field style.
127
-     */
128
-    textInputField: {
129
-        flex: 1,
130
-        fontSize: TEXT_SIZE,
131
-        textAlign: 'right'
31
+        color: ColorPalette.black
132 32
     }
133 33
 });

+ 56
- 0
react/features/base/react/components/native/Header.js ファイルの表示

@@ -0,0 +1,56 @@
1
+// @flow
2
+
3
+import React, { Component } from 'react';
4
+import { SafeAreaView, StatusBar, View } from 'react-native';
5
+
6
+import styles, { STATUSBAR_COLOR } from './styles';
7
+
8
+/**
9
+ * The type of the React {@code Component} props of {@link ScreenHeader}
10
+ */
11
+type Props = {
12
+
13
+    /**
14
+     * Children component(s).
15
+     */
16
+    children: React$Node,
17
+
18
+    /**
19
+     * The component's external style
20
+     */
21
+    style: Object
22
+}
23
+
24
+/**
25
+ * A generic screen header component.
26
+ */
27
+export default class Header extends Component<Props> {
28
+    /**
29
+     * Implements React's {@link Component#render()}.
30
+     *
31
+     * @inheritdoc
32
+     */
33
+    render() {
34
+        return (
35
+            <View
36
+                style = { styles.headerOverlay } >
37
+                <StatusBar
38
+                    backgroundColor = { STATUSBAR_COLOR }
39
+                    barStyle = 'light-content'
40
+                    translucent = { false } />
41
+                <SafeAreaView>
42
+                    <View
43
+                        style = { [
44
+                            styles.screenHeader,
45
+                            this.props.style
46
+                        ] }>
47
+                        {
48
+                            this.props.children
49
+                        }
50
+                    </View>
51
+                </SafeAreaView>
52
+            </View>
53
+        );
54
+    }
55
+
56
+}

+ 2
- 0
react/features/base/react/components/native/index.js ファイルの表示

@@ -1,5 +1,7 @@
1 1
 export { default as Container } from './Container';
2 2
 export { default as Link } from './Link';
3 3
 export { default as LoadingIndicator } from './LoadingIndicator';
4
+export { default as Header } from './Header';
5
+export * from './styles';
4 6
 export { default as TintedView } from './TintedView';
5 7
 export { default as Text } from './Text';

+ 39
- 0
react/features/base/react/components/native/styles.js ファイルの表示

@@ -0,0 +1,39 @@
1
+import {
2
+    BoxModel,
3
+    ColorPalette,
4
+    createStyleSheet
5
+} from '../../../styles';
6
+
7
+const HEADER_COLOR = ColorPalette.blue;
8
+
9
+// Header height is from iOS guidelines. Also, this looks good.
10
+const HEADER_HEIGHT = 44;
11
+const HEADER_PADDING = BoxModel.padding;
12
+
13
+export const STATUSBAR_COLOR = ColorPalette.blueHighlight;
14
+
15
+/**
16
+ * The styles of the React {@code Components} of the generic components
17
+ * in the app.
18
+ */
19
+export default createStyleSheet({
20
+
21
+    /**
22
+     * Style of the header overlay to cover the unsafe areas.
23
+     */
24
+    headerOverlay: {
25
+        backgroundColor: HEADER_COLOR
26
+    },
27
+
28
+    /**
29
+     * Base style of Header
30
+     */
31
+    screenHeader: {
32
+        alignItems: 'center',
33
+        backgroundColor: HEADER_COLOR,
34
+        flexDirection: 'row',
35
+        height: HEADER_HEIGHT,
36
+        justifyContent: 'flex-start',
37
+        padding: HEADER_PADDING
38
+    }
39
+});

+ 0
- 1
react/features/base/react/index.js ファイルの表示

@@ -1,4 +1,3 @@
1 1
 export * from './components';
2
-export * from './functions';
3 2
 export { default as Platform } from './Platform';
4 3
 export { default as RouteRegistry } from './RouteRegistry';

+ 1
- 0
react/features/base/styles/components/styles/ColorPalette.js ファイルの表示

@@ -19,6 +19,7 @@ export const ColorPalette = {
19 19
      */
20 20
     black: BLACK,
21 21
     blue: '#17A0DB',
22
+    blueHighlight: '#1081b2',
22 23
     buttonUnderlay: '#495258',
23 24
     darkGrey: '#555555',
24 25
     red: '#D00000',

+ 42
- 0
react/features/base/styles/components/styles/PlatformElements.native.js ファイルの表示

@@ -0,0 +1,42 @@
1
+import { ColorPalette } from './ColorPalette';
2
+
3
+import {
4
+    createStyleSheet
5
+} from '../../functions';
6
+
7
+export const PlatformElements = createStyleSheet({
8
+
9
+    /**
10
+     * Platform specific header button (e.g. back, menu...etc).
11
+     */
12
+    headerButton: {
13
+        alignSelf: 'center',
14
+        color: ColorPalette.white,
15
+        fontSize: 26,
16
+        paddingRight: 22,
17
+        zIndex: 9999
18
+    },
19
+
20
+    /**
21
+     * Generic style for a label placed in the header.
22
+     */
23
+    headerText: {
24
+        color: ColorPalette.white,
25
+        fontSize: 20
26
+    },
27
+
28
+    /**
29
+     * The topmost level element of a page.
30
+     */
31
+    page: {
32
+        alignItems: 'stretch',
33
+        bottom: 0,
34
+        flex: 1,
35
+        flexDirection: 'column',
36
+        left: 0,
37
+        overflow: 'hidden',
38
+        position: 'absolute',
39
+        right: 0,
40
+        top: 0
41
+    }
42
+});

+ 0
- 0
react/features/base/styles/components/styles/PlatformElements.web.js ファイルの表示


+ 1
- 0
react/features/base/styles/components/styles/index.js ファイルの表示

@@ -1,2 +1,3 @@
1 1
 export * from './BoxModel';
2 2
 export * from './ColorPalette';
3
+export * from './PlatformElements';

+ 2
- 1
react/features/conference/components/Conference.native.js ファイルの表示

@@ -3,7 +3,7 @@
3 3
 import React, { Component } from 'react';
4 4
 
5 5
 // eslint-disable-next-line react-native/split-platform-components
6
-import { BackAndroid, BackHandler, View } from 'react-native';
6
+import { BackAndroid, BackHandler, StatusBar, View } from 'react-native';
7 7
 import { connect as reactReduxConnect } from 'react-redux';
8 8
 
9 9
 import { appNavigate } from '../../app';
@@ -192,6 +192,7 @@ class Conference extends Component<Props> {
192 192
                 onClick = { this._onClick }
193 193
                 style = { styles.conference }
194 194
                 touchFeedback = { false }>
195
+                <StatusBar translucent = { true } />
195 196
 
196 197
                 {/*
197 198
                   * The LargeVideo is the lowermost stacking layer.

読み込み中…
キャンセル
保存