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

Add Dark Mode support to the App template and NewAppScreen components #28711

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
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
1 change: 1 addition & 0 deletions Libraries/NewAppScreen/components/Colors.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,5 +16,6 @@ export default {
lighter: '#F3F3F3',
light: '#DAE1E7',
dark: '#444',
darker: '#222',
black: '#000',
};
38 changes: 26 additions & 12 deletions Libraries/NewAppScreen/components/Header.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,25 +11,40 @@
'use strict';
import Colors from './Colors';
import type {Node} from 'react';
import {Text, StyleSheet, ImageBackground} from 'react-native';
import {ImageBackground, StyleSheet, Text, useColorScheme} from 'react-native';
import React from 'react';

const Header = (): Node => (
<ImageBackground
accessibilityRole={'image'}
source={require('./logo.png')}
style={styles.background}
imageStyle={styles.logo}>
<Text style={styles.text}>Welcome to React</Text>
</ImageBackground>
);
const Header = (): Node => {
const isDarkMode = useColorScheme() === 'dark';
return (
<ImageBackground
accessibilityRole="image"
source={require('./logo.png')}
style={[
styles.background,
{
backgroundColor: isDarkMode ? Colors.darker : Colors.lighter,
},
]}
imageStyle={styles.logo}>
<Text
style={[
styles.text,
{
color: isDarkMode ? Colors.white : Colors.black,
},
]}>
Welcome to React
</Text>
</ImageBackground>
);
};

const styles = StyleSheet.create({
background: {
paddingBottom: 40,
paddingTop: 96,
paddingHorizontal: 32,
backgroundColor: Colors.lighter,
},
logo: {
opacity: 0.2,
Expand All @@ -48,7 +63,6 @@ const styles = StyleSheet.create({
fontSize: 40,
fontWeight: '600',
textAlign: 'center',
color: Colors.black,
},
});

Expand Down
56 changes: 38 additions & 18 deletions Libraries/NewAppScreen/components/LearnMoreLinks.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,14 @@
import Colors from './Colors';
import type {Node} from 'react';
import openURLInBrowser from 'react-native/Libraries/Core/Devtools/openURLInBrowser';
import {View, Text, StyleSheet, TouchableOpacity} from 'react-native';
import React from 'react';
import {
StyleSheet,
Text,
TouchableOpacity,
useColorScheme,
View,
} from 'react-native';
import React, {Fragment} from 'react';

const links = [
{
Expand Down Expand Up @@ -70,24 +76,40 @@ const links = [
},
];

const LinkList = (): Node => (
<View style={styles.container}>
{links.map(({id, title, link, description}) => {
return (
<React.Fragment key={id}>
<View style={styles.separator} />
const LinkList = (): Node => {
const isDarkMode = useColorScheme() === 'dark';
return (
<View style={styles.container}>
{links.map(({id, title, link, description}) => (
<Fragment key={id}>
<View
style={[
styles.separator,
{
backgroundColor: isDarkMode ? Colors.dark : Colors.light,
},
]}
/>
<TouchableOpacity
accessibilityRole={'button'}
accessibilityRole="button"
onPress={() => openURLInBrowser(link)}
style={styles.linkContainer}>
<Text style={styles.link}>{title}</Text>
<Text style={styles.description}>{description}</Text>
<Text
style={[
styles.description,
{
color: isDarkMode ? Colors.lighter : Colors.dark,
},
]}>
{description}
</Text>
</TouchableOpacity>
</React.Fragment>
);
})}
</View>
);
</Fragment>
))}
</View>
);
};

const styles = StyleSheet.create({
container: {
Expand All @@ -112,11 +134,9 @@ const styles = StyleSheet.create({
paddingVertical: 16,
fontWeight: '400',
fontSize: 18,
color: Colors.dark,
},
separator: {
backgroundColor: Colors.light,
height: 1,
height: StyleSheet.hairlineWidth,
},
});

Expand Down
140 changes: 82 additions & 58 deletions template/App.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,102 +7,126 @@
*/

import React from 'react';
import type {Node} from 'react';
import {
SafeAreaView,
StyleSheet,
ScrollView,
View,
Text,
StatusBar,
StyleSheet,
Text,
useColorScheme,
View,
} from 'react-native';

import {
Header,
LearnMoreLinks,
Colors,
DebugInstructions,
Header,
LearnMoreLinks,
ReloadInstructions,
} from 'react-native/Libraries/NewAppScreen';

const App: () => React$Node = () => {
const Section = ({children, title}): Node => {
const isDarkMode = useColorScheme() === 'dark';
return (
<>
<StatusBar barStyle="dark-content" />
<SafeAreaView>
<ScrollView
contentInsetAdjustmentBehavior="automatic"
style={styles.scrollView}>
<Header />
{global.HermesInternal == null ? null : (
<View style={styles.engine}>
<Text style={styles.footer}>Engine: Hermes</Text>
</View>
)}
<View style={styles.body}>
<View style={styles.sectionContainer}>
<Text style={styles.sectionTitle}>Step One</Text>
<Text style={styles.sectionDescription}>
Edit <Text style={styles.highlight}>App.js</Text> to change this
screen and then come back to see your edits.
</Text>
</View>
<View style={styles.sectionContainer}>
<Text style={styles.sectionTitle}>See Your Changes</Text>
<Text style={styles.sectionDescription}>
<ReloadInstructions />
</Text>
</View>
<View style={styles.sectionContainer}>
<Text style={styles.sectionTitle}>Debug</Text>
<Text style={styles.sectionDescription}>
<DebugInstructions />
</Text>
</View>
<View style={styles.sectionContainer}>
<Text style={styles.sectionTitle}>Learn More</Text>
<Text style={styles.sectionDescription}>
Read the docs to discover what to do next:
</Text>
</View>
<LearnMoreLinks />
</View>
</ScrollView>
</SafeAreaView>
</>
<View style={styles.sectionContainer}>
<Text
style={[
styles.sectionTitle,
{
color: isDarkMode ? Colors.white : Colors.black,
},
]}>
{title}
</Text>
<Text
style={[
styles.sectionDescription,
{
color: isDarkMode ? Colors.light : Colors.dark,
},
]}>
{children}
</Text>
</View>
);
};

const App: () => Node = () => {
const isDarkMode = useColorScheme() === 'dark';

const backgroundStyle = {
backgroundColor: isDarkMode ? Colors.darker : Colors.lighter,
};

const hermes = global.HermesInternal ? (
<View style={styles.engine}>
<Text
style={[
styles.footer,
{
color: isDarkMode ? Colors.light : Colors.dark,
},
]}>
Engine: Hermes
</Text>
</View>
) : null;

return (
<SafeAreaView style={backgroundStyle}>
<StatusBar barStyle={isDarkMode ? 'light-content' : 'dark-content'} />
<ScrollView
contentInsetAdjustmentBehavior="automatic"
style={backgroundStyle}>
<Header />
{hermes}
<View
style={{
backgroundColor: isDarkMode ? Colors.black : Colors.white,
}}>
<Section title="Step One">
Edit <Text style={styles.highlight}>App.js</Text> to change this
screen and then come back to see your edits.
</Section>
<Section title="See Your Changes">
<ReloadInstructions />
</Section>
<Section title="Debug">
<DebugInstructions />
</Section>
<Section title="Learn More">
Read the docs to discover what to do next:
</Section>
<LearnMoreLinks />
</View>
</ScrollView>
</SafeAreaView>
);
};

const styles = StyleSheet.create({
scrollView: {
backgroundColor: Colors.lighter,
},
engine: {
position: 'absolute',
right: 0,
},
body: {
backgroundColor: Colors.white,
},
sectionContainer: {
marginTop: 32,
paddingHorizontal: 24,
},
sectionTitle: {
fontSize: 24,
fontWeight: '600',
color: Colors.black,
},
sectionDescription: {
marginTop: 8,
fontSize: 18,
fontWeight: '400',
color: Colors.dark,
},
highlight: {
fontWeight: '700',
},
footer: {
color: Colors.dark,
fontSize: 12,
fontWeight: '600',
padding: 4,
Expand Down
2 changes: 1 addition & 1 deletion template/android/app/src/main/res/values/styles.xml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<resources>

<!-- Base application theme. -->
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<style name="AppTheme" parent="Theme.AppCompat.DayNight.NoActionBar">
<!-- Customize your theme here. -->
<item name="android:textColor">#000000</item>
</style>
Expand Down
6 changes: 5 additions & 1 deletion template/ios/HelloWorld/AppDelegate.m
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,11 @@ - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(
moduleName:@"HelloWorld"
initialProperties:nil];

rootView.backgroundColor = [[UIColor alloc] initWithRed:1.0f green:1.0f blue:1.0f alpha:1];
if (@available(iOS 13.0, *)) {
rootView.backgroundColor = [UIColor systemBackgroundColor];
} else {
rootView.backgroundColor = [UIColor whiteColor];
}

self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds];
UIViewController *rootViewController = [UIViewController new];
Expand Down
13 changes: 1 addition & 12 deletions template/ios/HelloWorld/LaunchScreen.storyboard
Original file line number Diff line number Diff line change
Expand Up @@ -16,32 +16,21 @@
<rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
<subviews>
<label opaque="NO" clipsSubviews="YES" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" minimumFontSize="9" translatesAutoresizingMaskIntoConstraints="NO" id="obG-Y5-kRd">
<rect key="frame" x="0.0" y="647" width="375" height="0.0"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<color key="textColor" red="0.0" green="0.0" blue="0.0" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<nil key="highlightedColor"/>
</label>
<label opaque="NO" clipsSubviews="YES" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="HelloWorld" textAlignment="center" lineBreakMode="middleTruncation" baselineAdjustment="alignBaselines" minimumFontSize="18" translatesAutoresizingMaskIntoConstraints="NO" id="GJd-Yh-RWb">
<rect key="frame" x="0.0" y="202" width="375" height="43"/>
<fontDescription key="fontDescription" type="boldSystem" pointSize="36"/>
<color key="textColor" red="0.0" green="0.0" blue="0.0" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<nil key="highlightedColor"/>
</label>
<label opaque="NO" clipsSubviews="YES" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Powered by React Native" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" minimumFontSize="9" translatesAutoresizingMaskIntoConstraints="NO" id="MN2-I3-ftu">
<rect key="frame" x="0.0" y="626" width="375" height="21"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<color key="textColor" cocoaTouchSystemColor="darkTextColor"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<color key="backgroundColor" systemColor="systemBackgroundColor" cocoaTouchSystemColor="whiteColor"/>
<constraints>
<constraint firstItem="Bcu-3y-fUS" firstAttribute="centerX" secondItem="obG-Y5-kRd" secondAttribute="centerX" id="5cz-MP-9tL"/>
<constraint firstItem="Bcu-3y-fUS" firstAttribute="bottom" secondItem="MN2-I3-ftu" secondAttribute="bottom" constant="20" id="OZV-Vh-mqD"/>
<constraint firstItem="Bcu-3y-fUS" firstAttribute="centerX" secondItem="GJd-Yh-RWb" secondAttribute="centerX" id="Q3B-4B-g5h"/>
<constraint firstItem="obG-Y5-kRd" firstAttribute="leading" secondItem="Bcu-3y-fUS" secondAttribute="leading" symbolic="YES" id="SfN-ll-jLj"/>
<constraint firstAttribute="bottom" secondItem="obG-Y5-kRd" secondAttribute="bottom" constant="20" id="Y44-ml-fuU"/>
<constraint firstItem="MN2-I3-ftu" firstAttribute="centerX" secondItem="Bcu-3y-fUS" secondAttribute="centerX" id="akx-eg-2ui"/>
<constraint firstItem="MN2-I3-ftu" firstAttribute="leading" secondItem="Bcu-3y-fUS" secondAttribute="leading" id="i1E-0Y-4RG"/>
<constraint firstItem="GJd-Yh-RWb" firstAttribute="centerY" secondItem="Ze5-6b-2t3" secondAttribute="bottom" multiplier="1/3" constant="1" id="moa-c2-u7t"/>
Expand Down