Skip to content

Commit c2a4e84

Browse files
authored
Merge pull request #216 from flexbox/fix/dark-mode
fix dark mode switcher closes #213
2 parents b0516fb + 62a7460 commit c2a4e84

File tree

11 files changed

+138
-43
lines changed

11 files changed

+138
-43
lines changed

challenges/data/02.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,7 @@ async function fetchData() {
9898
}
9999

100100
export function useStarships() {
101-
return useQuery(["starships"], fetchData);
101+
return useQuery({ queryKey: ["starships"], queryFn: fetchData} );
102102
}
103103
```
104104

challenges/ecosystem/02.md

Lines changed: 13 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -124,17 +124,18 @@ module.exports = {
124124
env: {
125125
node: true
126126
},
127-
parser: "@typescript-eslint/parser",
128-
root: true,
127+
parser: "@typescript-eslint/parser", // Specifies the ESLint parser
128+
root: true, // make sure eslint picks up the config at the root of the directory
129129
extends: [
130-
"eslint:recommended",
131-
"plugin:@typescript-eslint/recommended",
132-
"plugin:react/recommended",
133-
"plugin:prettier/recommended"
130+
"eslint:recommended", // ESLint rules
131+
"plugin:@typescript-eslint/recommended", // TypeScript rules
132+
"plugin:react/recommended", // React rules
133+
"plugin:react/jsx-runtime", // support for React 17 JSX
134+
"plugin:prettier/recommended" // Prettier recommended rules
134135
],
135-
plugins: ["react", "react-native", "simple-import-sort"],
136+
plugins: ["react", "react-native", "simple-import-sort"], // add React and React Native plugins
136137
rules: {
137-
"prettier/prettier": [
138+
"prettier/prettier": [ // Prettier rules
138139
"warn",
139140
{
140141
usePrettierrc: true
@@ -222,4 +223,8 @@ You can share your VSCode settings with your team by adding a `.vscode` folder a
222223
}
223224
```
224225

226+
This will make sure everyone in your team is using the same settings.
227+
228+
- [ ] create a ``.vscode` folder and paste the previous `settings.json` files.
229+
225230
- [ ] Install [TanStack Query ESLint plugin](https://tanstack.com/query/v4/docs/react/eslint/eslint-plugin-query).

challenges/ecosystem/05.md

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -161,6 +161,12 @@ Ran all test suites.
161161
✨ Done in 16.14s.
162162
```
163163

164+
At this point, TypeScript will complain on your `hello.test.ts` file because we need to install jest types.
165+
166+
```console
167+
npm i --save-dev @types/jest
168+
```
169+
164170
### Installing React Native Testing Library
165171

166172
we need to install `@testing-library/react-native` and `@testing-library/jest-native`.
@@ -199,8 +205,13 @@ Let's now create a workflow to quickly add units tests on your codebase.
199205
+ "test:watch": "jest --watch"
200206
```
201207

202-
Now you can run `yarn test:watch` to watch your files and run tests automatically.
208+
Now you can run `npm run test:watch` to watch your files and run tests automatically.
203209

204210
### Testing a component
205211

206212
- [ ] Create tests files for your components
213+
214+
## Learning More
215+
216+
- https://reactnativetesting.io/
217+
- https://github.com/vanGalilea/react-native-testing?tab=readme-ov-file#covered-examples-

challenges/react-navigation/01.md

Lines changed: 44 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -25,35 +25,22 @@ Here is a preview of our application user flow:
2525

2626
**🔭 Hint:** you just installed **the core packages**, for every type of navigator (`Native Stack`, `Drawer`, `Bottom Tabs`…) you will need to **install other packages**.
2727

28-
### Organise your routes
29-
30-
We are going to create a "sitemap" of all our routes. This will help-us to have a single source of truth.
31-
32-
> We will use a [TypeScript feature called `const` assertions](https://www.typescriptlang.org/docs/handbook/release-notes/typescript-3-4.html#const-assertions).
33-
34-
```javascript
35-
// ./src/navigation/Routes.ts
36-
37-
const Routes {
38-
LOGIN_SCREEN = 'Login',
39-
TERMS_SCREEN = 'Terms',
40-
STARSHIP_FEED_SCREEN = 'Starships',
41-
STARSHIP_DETAIL_SCREEN = 'Starship',
42-
} as const;
43-
```
44-
45-
- [ ] Create a `Routes.ts` file in `./src/navigation/`
46-
4728
### Create a Navigator file
4829

49-
- [ ] Create a new component called `Navigator.tsx` on `./src/navigation/Routes.ts` and update the **entry point of your application**, such as `App.tsx`.
50-
- [ ] Wrap your `Stack` [with a `NavigationContainer`](https://reactnavigation.org/docs/getting-started#wrapping-your-app-in-navigationcontainer).
30+
- [ ] Create a new component called `Navigator.tsx` on `./src/navigation/`
31+
- [ ] return a [`NavigationContainer` from `@react-navigation/native`](https://reactnavigation.org/docs/getting-started#wrapping-your-app-in-navigationcontainer).
32+
- [ ] Update the **entry point of your application**, `App.tsx` to import your component `<Navigator />`.
5133

5234
### Create your first Stack
5335

5436
- [ ] Read the [`Stack.Navigator` documentation](https://reactnavigation.org/docs/hello-react-navigation).
5537
- [ ] Create a Stack Navigator in `./src/navigation/Navigator.tsx` that shows the `LoginScreen` and the `TermsScreen`.
56-
- [ ] Use `LOGIN_SCREEN` and `TERMS_SCREEN` from `Routes.ts`as screen names to maintain consistency when navigating
38+
39+
You will have something like this:
40+
41+
```javascript
42+
<Stack.Screen name="Terms" component={TermsScreen} />
43+
```
5744

5845
**🔭 Hint:** You can have multiple `function`s in the same file.
5946

@@ -75,7 +62,7 @@ Here is a function to navigate between screens:
7562

7663
```javascript
7764
function navigateToTerms() {
78-
navigation.navigate('Routes.TERMS_SCREEN');
65+
navigation.navigate('Terms');
7966
}
8067
```
8168

@@ -90,3 +77,37 @@ function navigateToTerms() {
9077
...
9178
</Stack.Navigator>
9279
```
80+
81+
## 👽 Bonus
82+
83+
### Create a files with all your screens
84+
85+
We are going to create a "sitemap" of all our routes. This will help-us in the long run to have a single source of truth.
86+
87+
> We will use a [TypeScript feature called `const` assertions](https://www.typescriptlang.org/docs/handbook/release-notes/typescript-3-4.html#const-assertions).
88+
89+
```javascript
90+
// ./src/navigation/Routes.ts
91+
92+
const Routes {
93+
LOGIN_SCREEN: "Login",
94+
TERMS_SCREEN: "Terms", // We will use Routes.TERMS_SCREEN to navigate later
95+
STARSHIP_FEED_SCREEN: "Starships",
96+
STARSHIP_DETAIL_SCREEN: "Starship",
97+
} as const;
98+
```
99+
100+
- [ ] Create a `Routes.ts` file in `./src/navigation/`
101+
- [ ] Update the `name` of the screens with the `Routes` constants.
102+
103+
```javascript
104+
<Stack.Screen name={Routes.TERMS_SCREEN} component={TermsScreen} />
105+
```
106+
107+
- [ ] Udpate when using `navigate` props, use the `Routes` constants.
108+
109+
```javascript
110+
function navigateToTerms() {
111+
navigation.navigate(Routes.TERMS_SCREEN);
112+
}
113+
```

hackathon/spacecraft/App.tsx

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,14 +5,17 @@ import { NetworkProvider } from "react-native-offline";
55
import { Provider as PaperProvider } from "react-native-paper";
66

77
import { AuthenticationProvider } from "~/context/Authentication";
8+
import { useAppearanceTheme } from "~/hooks/useAppearanceTheme";
89
import { Navigator } from "~/navigation/Navigator";
910

1011
const queryClient = new QueryClient();
1112

1213
const App = () => {
14+
const appearanceTheme = useAppearanceTheme();
15+
1316
return (
1417
<QueryClientProvider client={queryClient}>
15-
<PaperProvider>
18+
<PaperProvider theme={appearanceTheme}>
1619
<NetworkProvider>
1720
<AuthenticationProvider>
1821
<Navigator />

hackathon/spacecraft/package.json

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434
"@tanstack/react-query": "^4.29.12",
3535
"babel-core": "^7.0.0-bridge.0",
3636
"babel-jest": "^29.5.0",
37+
"deepmerge": "^4.3.1",
3738
"expo": "^49.0.5",
3839
"expo-constants": "~14.4.2",
3940
"expo-image": "~1.3.2",
@@ -56,10 +57,6 @@
5657
"rn-placeholder": "^3.0.3"
5758
},
5859
"devDependencies": {
59-
"app-icon-badge": "^0.0.13",
60-
"jest": "^29.6.4",
61-
"jest-expo": "^49.0.0",
62-
"@types/jest": "^29.5.4",
6360
"@babel/core": "^7.19.3",
6461
"@babel/preset-typescript": "^7.18.6",
6562
"@react-native-community/datetimepicker": "7.2.0",
@@ -73,8 +70,10 @@
7370
"@tanstack/eslint-plugin-query": "^4.29.9",
7471
"@testing-library/jest-native": "^5.4.3",
7572
"@testing-library/react-native": "^12.1.2",
73+
"@types/jest": "^29.5.4",
7674
"@types/react": "~18.2.14",
7775
"@types/react-dom": "~18.0.8",
76+
"app-icon-badge": "^0.0.13",
7877
"babel-loader": "^8.3.0",
7978
"babel-plugin-module-resolver": "^4.1.0",
8079
"babel-plugin-root-import": "^6.6.0",
@@ -83,6 +82,8 @@
8382
"eslint-config-react-native-wcandillon": "^3.9.0",
8483
"eslint-import-resolver-babel-plugin-root-import": "^1.1.1",
8584
"eslint-plugin-import": "^2.25.3",
85+
"jest": "^29.6.4",
86+
"jest-expo": "^49.0.0",
8687
"typescript": "^5.1.3"
8788
}
8889
}

hackathon/spacecraft/src/components/ScreenContainer.tsx

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import { useNavigation } from "@react-navigation/native";
22
import type { ReactNode } from "react";
33
import React from "react";
44
import { ScrollView, StyleSheet, View } from "react-native";
5-
import { IconButton, Text } from "react-native-paper";
5+
import { IconButton, Text, useTheme } from "react-native-paper";
66

77
import { Offline } from "~/components/Offline";
88

@@ -52,9 +52,13 @@ export const ScreenContainer = ({
5252
withGoBack = false,
5353
accessoryFooter,
5454
}: ScreenContainerProps) => {
55+
const theme = useTheme();
56+
5557
if (withScrollView) {
5658
return (
57-
<ScrollView style={styles.container}>
59+
<ScrollView
60+
style={[styles.container, { backgroundColor: theme.colors.background }]}
61+
>
5862
<ScreenContainerTitle title={title} withGoBack={withGoBack} />
5963
{children}
6064
<Offline />
@@ -64,7 +68,9 @@ export const ScreenContainer = ({
6468
}
6569

6670
return (
67-
<View style={styles.container}>
71+
<View
72+
style={[styles.container, { backgroundColor: theme.colors.background }]}
73+
>
6874
<ScreenContainerTitle title={title} withGoBack={withGoBack} />
6975
{children}
7076
<Offline />
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
import { useEffect, useState } from "react";
2+
import type { AppStateStatus } from "react-native";
3+
import { Appearance, AppState } from "react-native";
4+
5+
import { CombinedDarkTheme, CombinedDefaultTheme } from "~/theme/theme";
6+
7+
export const useAppearanceTheme = () => {
8+
const [theme, setTheme] = useState(
9+
Appearance.getColorScheme() === "dark"
10+
? CombinedDarkTheme
11+
: CombinedDefaultTheme
12+
);
13+
14+
useEffect(() => {
15+
const handleAppStateChange = (nextAppState: AppStateStatus) => {
16+
if (nextAppState === "active") {
17+
const colorScheme = Appearance.getColorScheme();
18+
setTheme(
19+
colorScheme === "dark" ? CombinedDarkTheme : CombinedDefaultTheme
20+
);
21+
}
22+
};
23+
24+
AppState.addEventListener("change", handleAppStateChange);
25+
}, []);
26+
27+
return theme;
28+
};

hackathon/spacecraft/src/navigation/Navigator.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,14 +6,16 @@ import { BottomTabNavigator } from "./BottomTabNavigator";
66
import { AuthNavigator } from "./AuthNavigator";
77

88
import { useAuthentication } from "~/context/Authentication";
9+
import { useAppearanceTheme } from "~/hooks/useAppearanceTheme";
910

1011
const Stack = createNativeStackNavigator();
1112

1213
export const Navigator = () => {
1314
const { user } = useAuthentication();
15+
const appearanceTheme = useAppearanceTheme();
1416

1517
return (
16-
<NavigationContainer>
18+
<NavigationContainer theme={appearanceTheme}>
1719
<Stack.Navigator screenOptions={{ headerShown: false }}>
1820
{user ? (
1921
<Stack.Screen name={"BOTTOM_TABS"} component={BottomTabNavigator} />
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
import {
2+
DarkTheme as NavigationDarkTheme,
3+
DefaultTheme as NavigationDefaultTheme,
4+
} from "@react-navigation/native";
5+
import {
6+
MD3DarkTheme,
7+
MD3LightTheme,
8+
adaptNavigationTheme,
9+
} from "react-native-paper";
10+
import merge from "deepmerge";
11+
12+
const { LightTheme, DarkTheme } = adaptNavigationTheme({
13+
reactNavigationLight: NavigationDefaultTheme,
14+
reactNavigationDark: NavigationDarkTheme,
15+
});
16+
17+
export const CombinedDefaultTheme = merge(MD3LightTheme, LightTheme);
18+
export const CombinedDarkTheme = merge(MD3DarkTheme, DarkTheme);

0 commit comments

Comments
 (0)