mirror of
https://github.com/zhigang1992/react-navigation.git
synced 2026-01-21 19:38:16 +08:00
Compare commits
27 Commits
@react-nav
...
fix/sortOn
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
073f04b6eb | ||
|
|
ed37e6aec0 | ||
|
|
f80ed7790e | ||
|
|
4c16083d51 | ||
|
|
e7631ea239 | ||
|
|
32fe3f17d0 | ||
|
|
b7c5305453 | ||
|
|
2ee435be3a | ||
|
|
016e7920df | ||
|
|
26ba019155 | ||
|
|
97772affa3 | ||
|
|
67f6950c14 | ||
|
|
fe6d20c10e | ||
|
|
7d74bd73a7 | ||
|
|
b46c433f1e | ||
|
|
7e71ee6c47 | ||
|
|
1287a784e6 | ||
|
|
56f7df5384 | ||
|
|
5996bbbce2 | ||
|
|
c3ba72df65 | ||
|
|
be40244214 | ||
|
|
7388e6d9bc | ||
|
|
00e70da0d4 | ||
|
|
70f4fe2ffa | ||
|
|
e639748b23 | ||
|
|
324ea7181d | ||
|
|
9d3731c2df |
@@ -75,9 +75,13 @@ jobs:
|
||||
- run:
|
||||
name: Build example for web
|
||||
command: yarn example expo build:web --no-pwa
|
||||
# Yarn does not execute the postinstall scripts if the package is in the cache
|
||||
- run:
|
||||
name: Install browsers
|
||||
command: yarn playwright install
|
||||
- run:
|
||||
name: Run integration tests
|
||||
command: yarn example test --maxWorkers=2
|
||||
command: yarn example test:e2e
|
||||
|
||||
build-packages:
|
||||
executor: default
|
||||
|
||||
@@ -26,5 +26,11 @@
|
||||
"rules": {
|
||||
"simple-import-sort/imports": "error",
|
||||
"simple-import-sort/exports": "error"
|
||||
}
|
||||
},
|
||||
"overrides": [{
|
||||
"files":["example/e2e/tests/*.ts"],
|
||||
"rules": {
|
||||
"jest/*": 0
|
||||
}
|
||||
}]
|
||||
}
|
||||
|
||||
31
.github/workflows/closed-issue.yml
vendored
Normal file
31
.github/workflows/closed-issue.yml
vendored
Normal file
@@ -0,0 +1,31 @@
|
||||
name: Comment on closed issue
|
||||
on:
|
||||
issue_comment:
|
||||
types: [created]
|
||||
|
||||
jobs:
|
||||
closed-issue:
|
||||
runs-on: ubuntu-latest
|
||||
if: ${{ github.event.issue.state == 'closed' }}
|
||||
steps:
|
||||
- uses: actions/github-script@v3
|
||||
with:
|
||||
github-token: ${{ secrets.GITHUB_TOKEN }}
|
||||
script: |
|
||||
const body = "Hey! This issue is closed and isn't watched by the core team. You are welcome to discuss the issue with others in this thread, but if you think this issue is still valid and needs to be tracked, please open a new issue with a repro.";
|
||||
const comments = await github.issues.listComments({
|
||||
issue_number: context.issue.number,
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
});
|
||||
|
||||
if (comments.data.some(comment => comment.body === body)) {
|
||||
return;
|
||||
}
|
||||
|
||||
await github.issues.createComment({
|
||||
issue_number: context.issue.number,
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
body,
|
||||
});
|
||||
5
.github/workflows/expo-preview.yml
vendored
5
.github/workflows/expo-preview.yml
vendored
@@ -16,10 +16,9 @@ jobs:
|
||||
node-version: 14.x
|
||||
|
||||
- name: Setup Expo
|
||||
uses: expo/expo-github-action@v5
|
||||
uses: expo/expo-github-action@v6
|
||||
with:
|
||||
expo-token: ${{ secrets.EXPO_TOKEN }}
|
||||
expo-cache: true
|
||||
token: ${{ secrets.EXPO_TOKEN }}
|
||||
|
||||
- name: Restore yarn cache
|
||||
id: yarn-cache
|
||||
|
||||
5
.github/workflows/expo.yml
vendored
5
.github/workflows/expo.yml
vendored
@@ -19,10 +19,9 @@ jobs:
|
||||
node-version: 14.x
|
||||
|
||||
- name: Setup Expo
|
||||
uses: expo/expo-github-action@v5
|
||||
uses: expo/expo-github-action@v6
|
||||
with:
|
||||
expo-token: ${{ secrets.EXPO_TOKEN }}
|
||||
expo-cache: true
|
||||
token: ${{ secrets.EXPO_TOKEN }}
|
||||
|
||||
- name: Restore yarn cache
|
||||
id: yarn-cache
|
||||
|
||||
File diff suppressed because one or more lines are too long
2
.yarnrc
2
.yarnrc
@@ -2,4 +2,4 @@
|
||||
# yarn lockfile v1
|
||||
|
||||
|
||||
yarn-path ".yarn/releases/yarn-1.18.0.js"
|
||||
yarn-path ".yarn/releases/yarn-1.22.10.cjs"
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
* <p>This source code is licensed under the MIT license found in the LICENSE file in the root
|
||||
* directory of this source tree.
|
||||
*/
|
||||
package com.reactnavigation;
|
||||
package org.reactnavigation.example;
|
||||
|
||||
import android.content.Context;
|
||||
import com.facebook.flipper.android.AndroidFlipperClient;
|
||||
@@ -66,4 +66,4 @@ public class ReactNativeFlipper {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,44 +0,0 @@
|
||||
import { page } from '../config/setup-playwright';
|
||||
|
||||
beforeEach(async () => {
|
||||
await page.click('[data-testid=LinkComponent]');
|
||||
});
|
||||
|
||||
const getPageInfo = async () => ({
|
||||
url: await page.evaluate(() => location.pathname + location.search),
|
||||
title: await page.evaluate(() => document.title),
|
||||
heading: (await page.accessibility.snapshot())?.children?.find(
|
||||
(it) => it.role === 'heading'
|
||||
)?.name,
|
||||
});
|
||||
|
||||
it('loads the article page', async () => {
|
||||
const { url, title, heading } = await getPageInfo();
|
||||
|
||||
expect(url).toBe('/link-component/article/gandalf');
|
||||
expect(title).toBe('Article by Gandalf - React Navigation Example');
|
||||
expect(heading).toBe('Article by Gandalf');
|
||||
});
|
||||
|
||||
it('goes to the album page and goes back', async () => {
|
||||
await page.click('[href="/link-component/music"]');
|
||||
|
||||
{
|
||||
const { url, title, heading } = await getPageInfo();
|
||||
|
||||
expect(url).toBe('/link-component/music');
|
||||
expect(title).toBe('Albums - React Navigation Example');
|
||||
expect(heading).toBe('Albums');
|
||||
}
|
||||
|
||||
await page.click('[aria-label="Article by Gandalf, back"]');
|
||||
await page.waitForNavigation();
|
||||
|
||||
{
|
||||
const { url, title, heading } = await getPageInfo();
|
||||
|
||||
expect(url).toBe('/link-component/article/gandalf');
|
||||
expect(title).toBe('Article by Gandalf - React Navigation Example');
|
||||
expect(heading).toBe('Article by Gandalf');
|
||||
}
|
||||
});
|
||||
@@ -1,28 +0,0 @@
|
||||
/* eslint-env jest */
|
||||
|
||||
import { Browser, BrowserContext, chromium, Page } from 'playwright';
|
||||
|
||||
let browser: Browser;
|
||||
let context: BrowserContext;
|
||||
let page: Page;
|
||||
|
||||
beforeAll(async () => {
|
||||
browser = await chromium.launch();
|
||||
});
|
||||
|
||||
afterAll(async () => {
|
||||
await browser.close();
|
||||
});
|
||||
|
||||
beforeEach(async () => {
|
||||
context = await browser.newContext();
|
||||
page = await context.newPage();
|
||||
|
||||
await page.goto('http://localhost:3579');
|
||||
});
|
||||
|
||||
afterEach(async () => {
|
||||
await context.close();
|
||||
});
|
||||
|
||||
export { browser, context, page };
|
||||
28
example/e2e/playwright.config.ts
Normal file
28
example/e2e/playwright.config.ts
Normal file
@@ -0,0 +1,28 @@
|
||||
import type { PlaywrightTestConfig } from '@playwright/test';
|
||||
import path from 'path';
|
||||
|
||||
const config: PlaywrightTestConfig = {
|
||||
testDir: path.join(__dirname, 'tests'),
|
||||
globalSetup: require.resolve('./config/setup-server.ts'),
|
||||
globalTeardown: require.resolve('./config/teardown-server.ts'),
|
||||
workers: 1,
|
||||
reporter: 'list',
|
||||
projects: [
|
||||
{
|
||||
name: 'Chromium',
|
||||
use: { browserName: 'chromium' },
|
||||
},
|
||||
|
||||
{
|
||||
name: 'Firefox',
|
||||
use: { browserName: 'firefox' },
|
||||
},
|
||||
|
||||
{
|
||||
name: 'WebKit',
|
||||
use: { browserName: 'webkit' },
|
||||
},
|
||||
],
|
||||
};
|
||||
|
||||
export default config;
|
||||
43
example/e2e/tests/Link.test.ts
Normal file
43
example/e2e/tests/Link.test.ts
Normal file
@@ -0,0 +1,43 @@
|
||||
import type { Page } from '@playwright/test';
|
||||
|
||||
import { expect, it } from './baseFixture';
|
||||
|
||||
it.beforeEach(async ({ page }) => {
|
||||
await page.click('[data-testid=LinkComponent]');
|
||||
});
|
||||
|
||||
const waitAndAssertPageHeading = async (
|
||||
page: Page,
|
||||
expectedHeading: string
|
||||
) => {
|
||||
await page.waitForSelector(`text=${expectedHeading}`);
|
||||
const heading = (await page.accessibility.snapshot())?.children?.find(
|
||||
(it) => it.role === 'heading'
|
||||
)?.name;
|
||||
expect(heading).toBe(expectedHeading);
|
||||
};
|
||||
|
||||
it('loads the article page', async ({ page }) => {
|
||||
await page.waitForURL('**/link-component/article/gandalf');
|
||||
expect(await page.title()).toBe(
|
||||
'Article by Gandalf - React Navigation Example'
|
||||
);
|
||||
await waitAndAssertPageHeading(page, 'Article by Gandalf');
|
||||
});
|
||||
|
||||
it('goes to the album page and goes back', async ({ page }) => {
|
||||
await page.click('[href="/link-component/music"]');
|
||||
|
||||
await page.waitForURL('**/link-component/music');
|
||||
expect(await page.title()).toBe('Albums - React Navigation Example');
|
||||
await waitAndAssertPageHeading(page, 'Albums');
|
||||
|
||||
await page.click('[aria-label="Article by Gandalf, back"]');
|
||||
await page.waitForNavigation();
|
||||
|
||||
await page.waitForURL('**/link-component/article/gandalf');
|
||||
expect(await page.title()).toBe(
|
||||
'Article by Gandalf - React Navigation Example'
|
||||
);
|
||||
await waitAndAssertPageHeading(page, 'Article by Gandalf');
|
||||
});
|
||||
11
example/e2e/tests/baseFixture.ts
Normal file
11
example/e2e/tests/baseFixture.ts
Normal file
@@ -0,0 +1,11 @@
|
||||
import { test as baseTest } from '@playwright/test';
|
||||
|
||||
const test = baseTest.extend({
|
||||
page: async ({ page }, use) => {
|
||||
await page.goto('http://localhost:3579');
|
||||
await use(page);
|
||||
},
|
||||
});
|
||||
|
||||
export const it = test;
|
||||
export const expect = test.expect;
|
||||
@@ -1,6 +1,6 @@
|
||||
import { page } from '../config/setup-playwright';
|
||||
import { expect, it } from './baseFixture';
|
||||
|
||||
it('loads the example app', async () => {
|
||||
it('loads the example app', async ({ page }) => {
|
||||
const snapshot = await page.accessibility.snapshot();
|
||||
|
||||
expect(
|
||||
@@ -1,3 +1,4 @@
|
||||
import { expect, test as it } from '@playwright/test';
|
||||
import cheerio from 'cheerio';
|
||||
import fetch from 'node-fetch';
|
||||
|
||||
@@ -23,15 +23,15 @@ PODS:
|
||||
- UMImageLoaderInterface
|
||||
- EXKeepAwake (9.1.2):
|
||||
- UMCore
|
||||
- EXPermissions (12.0.0):
|
||||
- EXPermissions (12.0.1):
|
||||
- UMCore
|
||||
- UMPermissionsInterface
|
||||
- EXSplashScreen (0.10.0):
|
||||
- EXSplashScreen (0.10.2):
|
||||
- React-Core
|
||||
- UMCore
|
||||
- EXStructuredHeaders (1.0.1):
|
||||
- UMCore
|
||||
- EXUpdates (0.5.4):
|
||||
- EXUpdates (0.5.5):
|
||||
- EXStructuredHeaders
|
||||
- React-Core
|
||||
- UMCore
|
||||
@@ -271,9 +271,9 @@ PODS:
|
||||
- React
|
||||
- react-native-flipper (0.80.0):
|
||||
- React-Core
|
||||
- react-native-safe-area-context (3.2.0):
|
||||
- react-native-pager-view (5.1.10):
|
||||
- React-Core
|
||||
- react-native-viewpager (5.0.12):
|
||||
- react-native-safe-area-context (3.2.0):
|
||||
- React-Core
|
||||
- React-RCTActionSheet (0.63.4):
|
||||
- React-Core/RCTActionSheetHeaders (= 0.63.4)
|
||||
@@ -335,13 +335,13 @@ PODS:
|
||||
- React-Core (= 0.63.4)
|
||||
- React-cxxreact (= 0.63.4)
|
||||
- React-jsi (= 0.63.4)
|
||||
- RNCAsyncStorage (1.15.1):
|
||||
- RNCAsyncStorage (1.15.5):
|
||||
- React-Core
|
||||
- RNCMaskedView (0.2.4):
|
||||
- React-Core
|
||||
- RNGestureHandler (1.10.3):
|
||||
- React-Core
|
||||
- RNReanimated (2.1.0):
|
||||
- RNReanimated (2.2.0):
|
||||
- DoubleConversion
|
||||
- FBLazyVector
|
||||
- FBReactNativeSpec
|
||||
@@ -370,8 +370,9 @@ PODS:
|
||||
- React-RCTVibration
|
||||
- ReactCommon/turbomodule/core
|
||||
- Yoga
|
||||
- RNScreens (3.0.0):
|
||||
- RNScreens (3.3.0):
|
||||
- React-Core
|
||||
- React-RCTImage
|
||||
- RNVectorIcons (8.1.0):
|
||||
- React-Core
|
||||
- UMAppLoader (2.1.0)
|
||||
@@ -451,8 +452,8 @@ DEPENDENCIES:
|
||||
- React-jsinspector (from `../../node_modules/react-native/ReactCommon/jsinspector`)
|
||||
- react-native-appearance (from `../../node_modules/react-native-appearance`)
|
||||
- react-native-flipper (from `../../node_modules/react-native-flipper`)
|
||||
- react-native-pager-view (from `../../node_modules/react-native-pager-view`)
|
||||
- react-native-safe-area-context (from `../../node_modules/react-native-safe-area-context`)
|
||||
- react-native-viewpager (from `../node_modules/react-native-pager-view`)
|
||||
- React-RCTActionSheet (from `../../node_modules/react-native/Libraries/ActionSheetIOS`)
|
||||
- React-RCTAnimation (from `../../node_modules/react-native/Libraries/NativeAnimation`)
|
||||
- React-RCTBlob (from `../../node_modules/react-native/Libraries/Blob`)
|
||||
@@ -464,7 +465,7 @@ DEPENDENCIES:
|
||||
- React-RCTVibration (from `../../node_modules/react-native/Libraries/Vibration`)
|
||||
- ReactCommon/turbomodule/core (from `../../node_modules/react-native/ReactCommon`)
|
||||
- "RNCAsyncStorage (from `../../node_modules/@react-native-async-storage/async-storage`)"
|
||||
- "RNCMaskedView (from `../node_modules/@react-native-masked-view/masked-view`)"
|
||||
- "RNCMaskedView (from `../../node_modules/@react-native-masked-view/masked-view`)"
|
||||
- RNGestureHandler (from `../../node_modules/react-native-gesture-handler`)
|
||||
- RNReanimated (from `../../node_modules/react-native-reanimated`)
|
||||
- RNScreens (from `../../node_modules/react-native-screens`)
|
||||
@@ -558,10 +559,10 @@ EXTERNAL SOURCES:
|
||||
:path: "../../node_modules/react-native-appearance"
|
||||
react-native-flipper:
|
||||
:path: "../../node_modules/react-native-flipper"
|
||||
react-native-pager-view:
|
||||
:path: "../../node_modules/react-native-pager-view"
|
||||
react-native-safe-area-context:
|
||||
:path: "../../node_modules/react-native-safe-area-context"
|
||||
react-native-viewpager:
|
||||
:path: "../node_modules/react-native-pager-view"
|
||||
React-RCTActionSheet:
|
||||
:path: "../../node_modules/react-native/Libraries/ActionSheetIOS"
|
||||
React-RCTAnimation:
|
||||
@@ -585,7 +586,7 @@ EXTERNAL SOURCES:
|
||||
RNCAsyncStorage:
|
||||
:path: "../../node_modules/@react-native-async-storage/async-storage"
|
||||
RNCMaskedView:
|
||||
:path: "../node_modules/@react-native-masked-view/masked-view"
|
||||
:path: "../../node_modules/@react-native-masked-view/masked-view"
|
||||
RNGestureHandler:
|
||||
:path: "../../node_modules/react-native-gesture-handler"
|
||||
RNReanimated:
|
||||
@@ -635,10 +636,10 @@ SPEC CHECKSUMS:
|
||||
EXFont: d6fb79f9863120f0d0b26b0c2d1453bc9511e9df
|
||||
EXImageLoader: da941c9399e01ec28f2d5b270bdd21f2c8ca596c
|
||||
EXKeepAwake: d4e4a3ed8c1c4fd940dd62fc5a8be2a190371fd4
|
||||
EXPermissions: 67ff17d3c12ea06066492dde4242f8047658fd62
|
||||
EXSplashScreen: 9d79ea338b7bb2ee94df51723870bac70b408d44
|
||||
EXPermissions: 8f8c1c05580c4e02d4ee2c8dd74bfe173ff6a723
|
||||
EXSplashScreen: a9baaf4fa866003884c90ba049f18760d6a8ce39
|
||||
EXStructuredHeaders: be834496a4d9fd0069cd12ec1cc57b31c6d3b256
|
||||
EXUpdates: e191b83e00d3e7ebfd7db3986806ceca09b7b322
|
||||
EXUpdates: efe0e8c514dcff06a8fd0b63be6019a6365fb9c7
|
||||
FBLazyVector: 3bb422f41b18121b71783a905c10e58606f7dc3e
|
||||
FBReactNativeSpec: f2c97f2529dd79c083355182cc158c9f98f4bd6e
|
||||
Flipper: d3da1aa199aad94455ae725e9f3aa43f3ec17021
|
||||
@@ -664,8 +665,8 @@ SPEC CHECKSUMS:
|
||||
React-jsinspector: 58aef7155bc9a9683f5b60b35eccea8722a4f53a
|
||||
react-native-appearance: 0f0e5fc2fcef70e03d48c8fe6b00b9158c2ba8aa
|
||||
react-native-flipper: 5a9d5959364fca6a8a9658d941343774cb197857
|
||||
react-native-pager-view: 967d50ce0f1b72e434a2d9f3b739ddbf7d5bbf83
|
||||
react-native-safe-area-context: f0906bf8bc9835ac9a9d3f97e8bde2a997d8da79
|
||||
react-native-viewpager: 98a850d1c7ac6263122d82618a77062a5f427073
|
||||
React-RCTActionSheet: 89a0ca9f4a06c1f93c26067af074ccdce0f40336
|
||||
React-RCTAnimation: 1bde3ecc0c104c55df246eda516e0deb03c4e49b
|
||||
React-RCTBlob: a97d378b527740cc667e03ebfa183a75231ab0f0
|
||||
@@ -676,11 +677,11 @@ SPEC CHECKSUMS:
|
||||
React-RCTText: 5c51df3f08cb9dedc6e790161195d12bac06101c
|
||||
React-RCTVibration: ae4f914cfe8de7d4de95ae1ea6cc8f6315d73d9d
|
||||
ReactCommon: 73d79c7039f473b76db6ff7c6b159c478acbbb3b
|
||||
RNCAsyncStorage: 08719e311ab90492c2dafd6d6fb7ffb396493638
|
||||
RNCAsyncStorage: 56a3355a10b5d660c48c6e37325ac85ebfd09885
|
||||
RNCMaskedView: fc29d354a40316a990e8fb46391f08aea829c3aa
|
||||
RNGestureHandler: a479ebd5ed4221a810967000735517df0d2db211
|
||||
RNReanimated: 70f662b5232dd5d19ccff581e919a54ea73df51c
|
||||
RNScreens: e8e8dd0588b5da0ab57dcca76ab9b2d8987757e0
|
||||
RNReanimated: d9da990fc90123f4ffbfdda93d00fc15174863a8
|
||||
RNScreens: bf59f17fbf001f1025243eeed5f19419d3c11ef2
|
||||
RNVectorIcons: 31cebfcf94e8cf8686eb5303ae0357da64d7a5a4
|
||||
UMAppLoader: fe2708bb0ac5cd70052bc207d06aa3b7e72b9e97
|
||||
UMBarCodeScannerInterface: 79f92bea5f7af39b381a4c82298105ceb537408a
|
||||
|
||||
@@ -1,6 +0,0 @@
|
||||
module.exports = {
|
||||
testRegex: '/__integration_tests__/.*\\.(test|spec)\\.(js|tsx?)$',
|
||||
globalSetup: './e2e/config/setup-server.tsx',
|
||||
globalTeardown: './e2e/config/teardown-server.tsx',
|
||||
setupFilesAfterEnv: ['./e2e/config/setup-playwright.tsx'],
|
||||
};
|
||||
@@ -11,65 +11,63 @@
|
||||
"ios": "react-native run-ios",
|
||||
"preios": "pod-install",
|
||||
"server": "nodemon -e '.js,.ts,.tsx' --exec \"babel-node -i '/node_modules[/\\](?react-native)/' -x '.web.tsx,.web.ts,.web.js,.tsx,.ts,.js' --config-file ./server/babel.config.js server\"",
|
||||
"test": "jest"
|
||||
"test:e2e": "playwright test --config=e2e/playwright.config.ts"
|
||||
},
|
||||
"dependencies": {
|
||||
"@expo/vector-icons": "^12.0.0",
|
||||
"@react-native-async-storage/async-storage": "^1.13.0",
|
||||
"@expo/vector-icons": "^12.0.5",
|
||||
"@react-native-async-storage/async-storage": "^1.15.5",
|
||||
"@react-native-masked-view/masked-view": "~0.2.4",
|
||||
"color": "^3.1.3",
|
||||
"expo": "^41.0.1",
|
||||
"expo-asset": "~8.3.1",
|
||||
"expo-asset": "~8.3.2",
|
||||
"expo-blur": "~9.0.3",
|
||||
"expo-linking": "~2.2.3",
|
||||
"expo-splash-screen": "~0.10.0",
|
||||
"expo-splash-screen": "~0.10.2",
|
||||
"expo-status-bar": "~1.0.4",
|
||||
"expo-updates": "~0.5.4",
|
||||
"expo-updates": "~0.5.5",
|
||||
"koa": "^2.13.0",
|
||||
"react": "16.13.1",
|
||||
"react-dom": "16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-appearance": "~0.3.3",
|
||||
"react-native-gesture-handler": "~1.10.2",
|
||||
"react-native-pager-view": "~5.0.12",
|
||||
"react-native-paper": "^4.9.0",
|
||||
"react-native-reanimated": "~2.1.0",
|
||||
"react-native-pager-view": "~5.1.10",
|
||||
"react-native-paper": "^4.9.1",
|
||||
"react-native-reanimated": "~2.2.0",
|
||||
"react-native-safe-area-context": "~3.2.0",
|
||||
"react-native-screens": "~3.0.0",
|
||||
"react-native-screens": "~3.3.0",
|
||||
"react-native-tab-view": "^3.0.1",
|
||||
"react-native-unimodules": "~0.13.1",
|
||||
"react-native-unimodules": "~0.13.3",
|
||||
"react-native-vector-icons": "^8.1.0",
|
||||
"react-native-web": "~0.15.0"
|
||||
"react-native-web": "~0.16.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@babel/core": "^7.9.0",
|
||||
"@babel/node": "^7.13.13",
|
||||
"@expo/webpack-config": "~0.12.63",
|
||||
"@types/cheerio": "^0.22.28",
|
||||
"@babel/core": "^7.14.3",
|
||||
"@babel/node": "^7.14.2",
|
||||
"@expo/webpack-config": "~0.12.76",
|
||||
"@playwright/test": "^1.12.2",
|
||||
"@types/cheerio": "^0.22.29",
|
||||
"@types/jest-dev-server": "^4.2.0",
|
||||
"@types/koa": "^2.13.1",
|
||||
"@types/koa": "^2.13.3",
|
||||
"@types/mock-require": "^2.0.0",
|
||||
"@types/node-fetch": "^2.5.9",
|
||||
"@types/react": "~16.9.35",
|
||||
"@types/react-dom": "~16.9.8",
|
||||
"@types/react-native": "~0.63.2",
|
||||
"babel-jest": "~25.2.6",
|
||||
"@types/node-fetch": "^2.5.10",
|
||||
"@types/react": "~17.0.9",
|
||||
"@types/react-dom": "~17.0.6",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"babel-loader": "^8.2.2",
|
||||
"babel-plugin-module-resolver": "^4.0.0",
|
||||
"babel-preset-expo": "8.3.0",
|
||||
"cheerio": "^1.0.0-rc.3",
|
||||
"expo-cli": "^4.4.4",
|
||||
"jest": "^26.6.3",
|
||||
"jest-dev-server": "^4.4.0",
|
||||
"cheerio": "^1.0.0-rc.9",
|
||||
"expo-cli": "^4.5.2",
|
||||
"jest-dev-server": "^5.0.3",
|
||||
"mock-require": "^3.0.3",
|
||||
"mock-require-assets": "^0.0.1",
|
||||
"node-fetch": "^2.6.1",
|
||||
"nodemon": "^2.0.6",
|
||||
"playwright": "^1.11.0",
|
||||
"pod-install": "^0.1.19",
|
||||
"pod-install": "^0.1.23",
|
||||
"react-native-flipper": "~0.80.0",
|
||||
"react-test-renderer": "~16.13.1",
|
||||
"serve": "^11.3.0",
|
||||
"typescript": "~4.2.3"
|
||||
"typescript": "^4.3.2"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,14 +7,9 @@ const alias = Object.fromEntries(
|
||||
fs
|
||||
.readdirSync(packages)
|
||||
.filter((name) => !name.startsWith('.'))
|
||||
.map((name) => [
|
||||
`@react-navigation/${name}`,
|
||||
path.resolve(
|
||||
packages,
|
||||
name,
|
||||
require(`../../packages/${name}/package.json`).source
|
||||
),
|
||||
])
|
||||
.map((name) => [name, require(`../../packages/${name}/package.json`)])
|
||||
.filter(([, pak]) => pak.source != null)
|
||||
.map(([name, pak]) => [pak.name, path.resolve(packages, name, pak.source)])
|
||||
);
|
||||
|
||||
module.exports = {
|
||||
|
||||
@@ -19,13 +19,10 @@ import Chat from '../Shared/Chat';
|
||||
import Contacts from '../Shared/Contacts';
|
||||
import SimpleStackScreen, { SimpleStackParams } from './SimpleStack';
|
||||
|
||||
const getTabBarIcon = (name: string) => ({
|
||||
color,
|
||||
size,
|
||||
}: {
|
||||
color: string;
|
||||
size: number;
|
||||
}) => <MaterialCommunityIcons name={name} color={color} size={size} />;
|
||||
const getTabBarIcon =
|
||||
(name: string) =>
|
||||
({ color, size }: { color: string; size: number }) =>
|
||||
<MaterialCommunityIcons name={name} color={color} size={size} />;
|
||||
|
||||
type BottomTabParams = {
|
||||
TabStack: NavigatorScreenParams<SimpleStackParams>;
|
||||
|
||||
@@ -15,7 +15,8 @@ type MaterialBottomTabParams = {
|
||||
TabChat: undefined;
|
||||
};
|
||||
|
||||
const MaterialBottomTabs = createMaterialBottomTabNavigator<MaterialBottomTabParams>();
|
||||
const MaterialBottomTabs =
|
||||
createMaterialBottomTabNavigator<MaterialBottomTabParams>();
|
||||
|
||||
export default function MaterialBottomTabsScreen() {
|
||||
return (
|
||||
|
||||
@@ -155,9 +155,8 @@ export default function App() {
|
||||
const [theme, setTheme] = React.useState(DefaultTheme);
|
||||
|
||||
const [isReady, setIsReady] = React.useState(Platform.OS === 'web');
|
||||
const [initialState, setInitialState] = React.useState<
|
||||
InitialState | undefined
|
||||
>();
|
||||
const [initialState, setInitialState] =
|
||||
React.useState<InitialState | undefined>();
|
||||
|
||||
React.useEffect(() => {
|
||||
const restoreState = async () => {
|
||||
|
||||
@@ -8,8 +8,6 @@ const packages = path.resolve(__dirname, '..', 'packages');
|
||||
module.exports = async function (env, argv) {
|
||||
const config = await createExpoWebpackConfigAsync(env, argv);
|
||||
|
||||
config.context = path.resolve(__dirname, '..');
|
||||
|
||||
config.module.rules.push({
|
||||
test: /\.(js|ts|tsx)$/,
|
||||
include: /(packages|example)\/.+/,
|
||||
@@ -27,11 +25,13 @@ module.exports = async function (env, argv) {
|
||||
fs.readdirSync(packages)
|
||||
.filter((name) => !name.startsWith('.'))
|
||||
.forEach((name) => {
|
||||
config.resolve.alias[`@react-navigation/${name}`] = path.resolve(
|
||||
packages,
|
||||
name,
|
||||
require(`../packages/${name}/package.json`).source
|
||||
);
|
||||
const pak = require(`../packages/${name}/package.json`);
|
||||
|
||||
if (pak.source == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
config.resolve.alias[pak.name] = path.resolve(packages, name, pak.source);
|
||||
});
|
||||
|
||||
return config;
|
||||
|
||||
20
package.json
20
package.json
@@ -29,21 +29,24 @@
|
||||
"release": "lerna publish",
|
||||
"example": "yarn --cwd example"
|
||||
},
|
||||
"dependencies": {
|
||||
"react-native-web": "~0.16.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@commitlint/config-conventional": "^12.1.1",
|
||||
"@types/jest": "^26.0.22",
|
||||
"@commitlint/config-conventional": "^12.1.4",
|
||||
"@types/jest": "^26.0.23",
|
||||
"babel-jest": "^26.6.3",
|
||||
"codecov": "^3.8.1",
|
||||
"commitlint": "^12.1.1",
|
||||
"eslint": "^7.23.0",
|
||||
"codecov": "^3.8.2",
|
||||
"commitlint": "^12.1.4",
|
||||
"eslint": "^7.27.0",
|
||||
"eslint-config-satya164": "^3.1.10",
|
||||
"eslint-plugin-simple-import-sort": "^7.0.0",
|
||||
"husky": "^4.3.6",
|
||||
"jest": "^26.6.3",
|
||||
"lerna": "^4.0.0",
|
||||
"metro-react-native-babel-preset": "^0.65.2",
|
||||
"prettier": "^2.2.1",
|
||||
"typescript": "^4.2.3"
|
||||
"metro-react-native-babel-preset": "^0.66.0",
|
||||
"prettier": "^2.3.0",
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"resolutions": {
|
||||
"react": "~16.13.1",
|
||||
@@ -67,6 +70,7 @@
|
||||
"preset": "react-native"
|
||||
},
|
||||
"prettier": {
|
||||
"quoteProps": "consistent",
|
||||
"tabWidth": 2,
|
||||
"useTabs": false,
|
||||
"singleQuote": true,
|
||||
|
||||
@@ -3,6 +3,30 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.19](https://github.com/react-navigation/react-navigation/compare/@react-navigation/bottom-tabs@6.0.0-next.18...@react-navigation/bottom-tabs@6.0.0-next.19) (2021-06-10)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/bottom-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.18](https://github.com/react-navigation/react-navigation/compare/@react-navigation/bottom-tabs@6.0.0-next.17...@react-navigation/bottom-tabs@6.0.0-next.18) (2021-06-01)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/bottom-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.17](https://github.com/react-navigation/react-navigation/compare/@react-navigation/bottom-tabs@6.0.0-next.16...@react-navigation/bottom-tabs@6.0.0-next.17) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/bottom-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.16](https://github.com/react-navigation/react-navigation/compare/@react-navigation/bottom-tabs@6.0.0-next.15...@react-navigation/bottom-tabs@6.0.0-next.16) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/bottom-tabs
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/bottom-tabs",
|
||||
"description": "Bottom tab navigator following iOS design guidelines",
|
||||
"version": "6.0.0-next.16",
|
||||
"version": "6.0.0-next.19",
|
||||
"keywords": [
|
||||
"react-native-component",
|
||||
"react-component",
|
||||
@@ -36,23 +36,23 @@
|
||||
"clean": "del lib"
|
||||
},
|
||||
"dependencies": {
|
||||
"@react-navigation/elements": "^1.0.0-next.15",
|
||||
"@react-navigation/elements": "^1.0.0-next.18",
|
||||
"color": "^3.1.3",
|
||||
"warn-once": "^0.1.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-navigation/native": "^6.0.0-next.12",
|
||||
"@react-navigation/native": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/color": "^3.0.1",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-native": "~0.64.4",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"del-cli": "^3.0.1",
|
||||
"react": "~16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-native-safe-area-context": "~3.2.0",
|
||||
"react-native-screens": "~3.0.0",
|
||||
"typescript": "^4.2.3"
|
||||
"react-native-screens": "~3.3.0",
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@react-navigation/native": "^6.0.0",
|
||||
|
||||
@@ -77,25 +77,21 @@ function BottomTabNavigator({
|
||||
);
|
||||
}
|
||||
|
||||
const {
|
||||
state,
|
||||
descriptors,
|
||||
navigation,
|
||||
NavigationContent,
|
||||
} = useNavigationBuilder<
|
||||
TabNavigationState<ParamListBase>,
|
||||
TabRouterOptions,
|
||||
TabActionHelpers<ParamListBase>,
|
||||
BottomTabNavigationOptions,
|
||||
BottomTabNavigationEventMap
|
||||
>(TabRouter, {
|
||||
initialRouteName,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
defaultScreenOptions,
|
||||
});
|
||||
const { state, descriptors, navigation, NavigationContent } =
|
||||
useNavigationBuilder<
|
||||
TabNavigationState<ParamListBase>,
|
||||
TabRouterOptions,
|
||||
TabActionHelpers<ParamListBase>,
|
||||
BottomTabNavigationOptions,
|
||||
BottomTabNavigationEventMap
|
||||
>(TabRouter, {
|
||||
initialRouteName,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
defaultScreenOptions,
|
||||
});
|
||||
|
||||
return (
|
||||
<NavigationContent>
|
||||
|
||||
@@ -48,9 +48,8 @@ const shouldUseHorizontalLabels = ({
|
||||
layout,
|
||||
dimensions,
|
||||
}: Options) => {
|
||||
const { tabBarLabelPosition, tabBarAdaptive = true } = descriptors[
|
||||
state.routes[state.index].key
|
||||
].options;
|
||||
const { tabBarLabelPosition, tabBarAdaptive = true } =
|
||||
descriptors[state.routes[state.index].key].options;
|
||||
|
||||
if (tabBarLabelPosition) {
|
||||
return tabBarLabelPosition === 'beside-icon';
|
||||
|
||||
@@ -137,7 +137,8 @@ export default function BottomTabView(props: Props) {
|
||||
header={header({
|
||||
layout: dimensions,
|
||||
route: descriptor.route,
|
||||
navigation: descriptor.navigation as BottomTabNavigationProp<ParamListBase>,
|
||||
navigation:
|
||||
descriptor.navigation as BottomTabNavigationProp<ParamListBase>,
|
||||
options: descriptor.options,
|
||||
})}
|
||||
style={sceneContainerStyle}
|
||||
|
||||
@@ -3,6 +3,28 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.14](https://github.com/react-navigation/react-navigation/compare/@react-navigation/core@6.0.0-next.13...@react-navigation/core@6.0.0-next.14) (2021-06-10)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* show stack trace in the flipper plugin ([97772af](https://github.com/react-navigation/react-navigation/commit/97772affa3c8f26489f0bdbfb6872ef4377b8ed1))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.13](https://github.com/react-navigation/react-navigation/compare/@react-navigation/core@6.0.0-next.12...@react-navigation/core@6.0.0-next.13) (2021-05-29)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* validate property names in linking config ([324ea71](https://github.com/react-navigation/react-navigation/commit/324ea7181db6b743f512854be267cc9d65975b6f))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.12](https://github.com/react-navigation/react-navigation/compare/@react-navigation/core@6.0.0-next.11...@react-navigation/core@6.0.0-next.12) (2021-05-29)
|
||||
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/core",
|
||||
"description": "Core utilities for building navigators",
|
||||
"version": "6.0.0-next.12",
|
||||
"version": "6.0.0-next.14",
|
||||
"keywords": [
|
||||
"react",
|
||||
"react-native",
|
||||
@@ -35,22 +35,22 @@
|
||||
"clean": "del lib"
|
||||
},
|
||||
"dependencies": {
|
||||
"@react-navigation/routers": "^6.0.0-next.4",
|
||||
"@react-navigation/routers": "^6.0.0-next.5",
|
||||
"escape-string-regexp": "^4.0.0",
|
||||
"nanoid": "^3.1.22",
|
||||
"nanoid": "^3.1.23",
|
||||
"query-string": "^7.0.0",
|
||||
"react-is": "^16.13.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-is": "^16.7.1",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-is": "^17.0.0",
|
||||
"del-cli": "^3.0.1",
|
||||
"immer": "^9.0.1",
|
||||
"immer": "^9.0.2",
|
||||
"react": "~16.13.1",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-test-renderer": "~16.13.1",
|
||||
"typescript": "^4.2.3"
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "*"
|
||||
|
||||
@@ -95,15 +95,10 @@ const BaseNavigationContainer = React.forwardRef(
|
||||
);
|
||||
}
|
||||
|
||||
const [
|
||||
state,
|
||||
getState,
|
||||
setState,
|
||||
scheduleUpdate,
|
||||
flushUpdates,
|
||||
] = useSyncState<State>(() =>
|
||||
getPartialState(initialState == null ? undefined : initialState)
|
||||
);
|
||||
const [state, getState, setState, scheduleUpdate, flushUpdates] =
|
||||
useSyncState<State>(() =>
|
||||
getPartialState(initialState == null ? undefined : initialState)
|
||||
);
|
||||
|
||||
const isFirstMountRef = React.useRef<boolean>(true);
|
||||
|
||||
@@ -223,7 +218,10 @@ const BaseNavigationContainer = React.forwardRef(
|
||||
|
||||
const onDispatchAction = React.useCallback(
|
||||
(action: NavigationAction, noop: boolean) => {
|
||||
emitter.emit({ type: '__unsafe_action__', data: { action, noop } });
|
||||
emitter.emit({
|
||||
type: '__unsafe_action__',
|
||||
data: { action, noop, stack: stackRef.current },
|
||||
});
|
||||
},
|
||||
[emitter]
|
||||
);
|
||||
@@ -246,12 +244,15 @@ const BaseNavigationContainer = React.forwardRef(
|
||||
[emitter]
|
||||
);
|
||||
|
||||
const stackRef = React.useRef<string | undefined>();
|
||||
|
||||
const builderContext = React.useMemo(
|
||||
() => ({
|
||||
addListener,
|
||||
addKeyedListener,
|
||||
onDispatchAction,
|
||||
onOptionsChange,
|
||||
stackRef,
|
||||
}),
|
||||
[addListener, addKeyedListener, onDispatchAction, onOptionsChange]
|
||||
);
|
||||
@@ -349,9 +350,8 @@ const BaseNavigationContainer = React.forwardRef(
|
||||
}
|
||||
}
|
||||
|
||||
const duplicateRouteNamesResult = checkDuplicateRouteNames(
|
||||
hydratedState
|
||||
);
|
||||
const duplicateRouteNamesResult =
|
||||
checkDuplicateRouteNames(hydratedState);
|
||||
|
||||
if (duplicateRouteNamesResult.length) {
|
||||
const message = `Found screens with the same name nested inside one another. Check:\n${duplicateRouteNamesResult.map(
|
||||
|
||||
@@ -4,8 +4,7 @@ import * as React from 'react';
|
||||
* Context which holds the values for the current navigation tree.
|
||||
* Intended for use in SSR. This is not safe to use on the client.
|
||||
*/
|
||||
const CurrentRenderContext = React.createContext<
|
||||
{ options?: object } | undefined
|
||||
>(undefined);
|
||||
const CurrentRenderContext =
|
||||
React.createContext<{ options?: object } | undefined>(undefined);
|
||||
|
||||
export default CurrentRenderContext;
|
||||
|
||||
@@ -6,13 +6,14 @@ type Props = {
|
||||
|
||||
const MULTIPLE_NAVIGATOR_ERROR = `Another navigator is already registered for this container. You likely have multiple navigators under a single "NavigationContainer" or "Screen". Make sure each navigator is under a separate "Screen" container. See https://reactnavigation.org/docs/nesting-navigators for a guide on nesting.`;
|
||||
|
||||
export const SingleNavigatorContext = React.createContext<
|
||||
| {
|
||||
register(key: string): void;
|
||||
unregister(key: string): void;
|
||||
}
|
||||
| undefined
|
||||
>(undefined);
|
||||
export const SingleNavigatorContext =
|
||||
React.createContext<
|
||||
| {
|
||||
register(key: string): void;
|
||||
unregister(key: string): void;
|
||||
}
|
||||
| undefined
|
||||
>(undefined);
|
||||
|
||||
/**
|
||||
* Component which ensures that there's only one navigator nested under it.
|
||||
|
||||
@@ -39,7 +39,10 @@ export type FocusedNavigationCallback<T> = (
|
||||
|
||||
export type FocusedNavigationListener = <T>(
|
||||
callback: FocusedNavigationCallback<T>
|
||||
) => { handled: boolean; result: T };
|
||||
) => {
|
||||
handled: boolean;
|
||||
result: T;
|
||||
};
|
||||
|
||||
export type GetStateListener = () => NavigationState;
|
||||
|
||||
@@ -58,6 +61,7 @@ const NavigationBuilderContext = React.createContext<{
|
||||
onRouteFocus?: (key: string) => void;
|
||||
onDispatchAction: (action: NavigationAction, noop: boolean) => void;
|
||||
onOptionsChange: (options: object) => void;
|
||||
stackRef?: React.MutableRefObject<string | undefined>;
|
||||
}>({
|
||||
onDispatchAction: () => undefined,
|
||||
onOptionsChange: () => undefined,
|
||||
|
||||
@@ -6,8 +6,9 @@ import type { NavigationContainerRef } from './types';
|
||||
/**
|
||||
* Context which holds the route prop for a screen.
|
||||
*/
|
||||
const NavigationContainerRefContext = React.createContext<
|
||||
NavigationContainerRef<ParamListBase> | undefined
|
||||
>(undefined);
|
||||
const NavigationContainerRefContext =
|
||||
React.createContext<NavigationContainerRef<ParamListBase> | undefined>(
|
||||
undefined
|
||||
);
|
||||
|
||||
export default NavigationContainerRefContext;
|
||||
|
||||
@@ -6,8 +6,7 @@ import type { NavigationProp } from './types';
|
||||
/**
|
||||
* Context which holds the navigation prop for a screen.
|
||||
*/
|
||||
const NavigationContext = React.createContext<
|
||||
NavigationProp<ParamListBase> | undefined
|
||||
>(undefined);
|
||||
const NavigationContext =
|
||||
React.createContext<NavigationProp<ParamListBase> | undefined>(undefined);
|
||||
|
||||
export default NavigationContext;
|
||||
|
||||
@@ -7,8 +7,7 @@ import type { NavigationHelpers } from './types';
|
||||
* Context which holds the navigation helpers of the parent navigator.
|
||||
* Navigators should use this context in their view component.
|
||||
*/
|
||||
const NavigationHelpersContext = React.createContext<
|
||||
NavigationHelpers<ParamListBase> | undefined
|
||||
>(undefined);
|
||||
const NavigationHelpersContext =
|
||||
React.createContext<NavigationHelpers<ParamListBase> | undefined>(undefined);
|
||||
|
||||
export default NavigationHelpersContext;
|
||||
|
||||
@@ -4,8 +4,7 @@ import * as React from 'react';
|
||||
/**
|
||||
* Context which holds the route prop for a screen.
|
||||
*/
|
||||
const NavigationRouteContext = React.createContext<Route<string> | undefined>(
|
||||
undefined
|
||||
);
|
||||
const NavigationRouteContext =
|
||||
React.createContext<Route<string> | undefined>(undefined);
|
||||
|
||||
export default NavigationRouteContext;
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
import type { NavigationAction } from '@react-navigation/routers';
|
||||
import * as React from 'react';
|
||||
|
||||
const UnhandledActionContext = React.createContext<
|
||||
((action: NavigationAction) => void) | undefined
|
||||
>(undefined);
|
||||
const UnhandledActionContext =
|
||||
React.createContext<((action: NavigationAction) => void) | undefined>(
|
||||
undefined
|
||||
);
|
||||
|
||||
export default UnhandledActionContext;
|
||||
|
||||
@@ -2196,6 +2196,7 @@ it('tries to match wildcard patterns at the end', () => {
|
||||
path: '/bar/:id/',
|
||||
screens: {
|
||||
404: '*',
|
||||
UserProfile: ':userSlug',
|
||||
Test: 'test',
|
||||
},
|
||||
},
|
||||
@@ -2420,3 +2421,57 @@ it('correctly applies initialRouteName for config with similar route names v2',
|
||||
getStateFromPath<object>(getPathFromState<object>(state, config), config)
|
||||
).toEqual(state);
|
||||
});
|
||||
|
||||
it('throws when invalid properties are specified in the config', () => {
|
||||
expect(() =>
|
||||
getStateFromPath<object>('', {
|
||||
Foo: 'foo',
|
||||
Bar: {
|
||||
path: 'bar',
|
||||
},
|
||||
} as any)
|
||||
).toThrowErrorMatchingInlineSnapshot(`
|
||||
"Found invalid properties in the configuration:
|
||||
- Foo
|
||||
- Bar
|
||||
|
||||
Did you forget to specify them under a 'screens' property?
|
||||
|
||||
You can only specify the following properties:
|
||||
- initialRouteName
|
||||
- screens
|
||||
|
||||
See https://reactnavigation.org/docs/configuring-links for more details on how to specify a linking configuration."
|
||||
`);
|
||||
|
||||
expect(() =>
|
||||
getStateFromPath<object>('', {
|
||||
screens: {
|
||||
Foo: 'foo',
|
||||
Bar: {
|
||||
path: 'bar',
|
||||
},
|
||||
Baz: {
|
||||
Qux: {
|
||||
path: 'qux',
|
||||
},
|
||||
},
|
||||
},
|
||||
} as any)
|
||||
).toThrowErrorMatchingInlineSnapshot(`
|
||||
"Found invalid properties in the configuration:
|
||||
- Qux
|
||||
|
||||
Did you forget to specify them under a 'screens' property?
|
||||
|
||||
You can only specify the following properties:
|
||||
- initialRouteName
|
||||
- screens
|
||||
- path
|
||||
- exact
|
||||
- stringify
|
||||
- parse
|
||||
|
||||
See https://reactnavigation.org/docs/configuring-links for more details on how to specify a linking configuration."
|
||||
`);
|
||||
});
|
||||
|
||||
@@ -31,19 +31,21 @@ it('fires focus and blur events in root navigator', () => {
|
||||
const fourthFocusCallback = jest.fn();
|
||||
const fourthBlurCallback = jest.fn();
|
||||
|
||||
const createComponent = (focusCallback: any, blurCallback: any) => ({
|
||||
navigation,
|
||||
}: any) => {
|
||||
React.useEffect(() => navigation.addListener('focus', focusCallback), [
|
||||
navigation,
|
||||
]);
|
||||
const createComponent =
|
||||
(focusCallback: any, blurCallback: any) =>
|
||||
({ navigation }: any) => {
|
||||
React.useEffect(
|
||||
() => navigation.addListener('focus', focusCallback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
React.useEffect(() => navigation.addListener('blur', blurCallback), [
|
||||
navigation,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => navigation.addListener('blur', blurCallback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
return null;
|
||||
};
|
||||
return null;
|
||||
};
|
||||
|
||||
const navigation = React.createRef<any>();
|
||||
|
||||
@@ -185,19 +187,21 @@ it('fires focus and blur events in nested navigator', () => {
|
||||
const fourthFocusCallback = jest.fn();
|
||||
const fourthBlurCallback = jest.fn();
|
||||
|
||||
const createComponent = (focusCallback: any, blurCallback: any) => ({
|
||||
navigation,
|
||||
}: any) => {
|
||||
React.useEffect(() => navigation.addListener('focus', focusCallback), [
|
||||
navigation,
|
||||
]);
|
||||
const createComponent =
|
||||
(focusCallback: any, blurCallback: any) =>
|
||||
({ navigation }: any) => {
|
||||
React.useEffect(
|
||||
() => navigation.addListener('focus', focusCallback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
React.useEffect(() => navigation.addListener('blur', blurCallback), [
|
||||
navigation,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => navigation.addListener('blur', blurCallback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
return null;
|
||||
};
|
||||
return null;
|
||||
};
|
||||
|
||||
const parent = React.createRef<any>();
|
||||
const child = React.createRef<any>();
|
||||
@@ -392,9 +396,10 @@ it('fires blur event when a route is removed with a delay', async () => {
|
||||
const First = () => null;
|
||||
|
||||
const Second = ({ navigation }: any) => {
|
||||
React.useEffect(() => navigation.addListener('blur', blurCallback), [
|
||||
navigation,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => navigation.addListener('blur', blurCallback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
return null;
|
||||
};
|
||||
@@ -447,13 +452,16 @@ it('fires custom events added with addListener', () => {
|
||||
const secondCallback = jest.fn();
|
||||
const thirdCallback = jest.fn();
|
||||
|
||||
const createComponent = (callback: any) => ({ navigation }: any) => {
|
||||
React.useEffect(() => navigation.addListener(eventName, callback), [
|
||||
navigation,
|
||||
]);
|
||||
const createComponent =
|
||||
(callback: any) =>
|
||||
({ navigation }: any) => {
|
||||
React.useEffect(
|
||||
() => navigation.addListener(eventName, callback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
return null;
|
||||
};
|
||||
return null;
|
||||
};
|
||||
|
||||
const ref = React.createRef<any>();
|
||||
|
||||
@@ -526,9 +534,10 @@ it("doesn't call same listener multiple times with addListener", () => {
|
||||
const callback = jest.fn();
|
||||
|
||||
const Test = ({ navigation }: any) => {
|
||||
React.useEffect(() => navigation.addListener(eventName, callback), [
|
||||
navigation,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => navigation.addListener(eventName, callback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
return null;
|
||||
};
|
||||
@@ -802,9 +811,10 @@ it('has option to prevent default', () => {
|
||||
};
|
||||
|
||||
const Test = ({ navigation }: any) => {
|
||||
React.useEffect(() => navigation.addListener(eventName, callback), [
|
||||
navigation,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => navigation.addListener(eventName, callback),
|
||||
[navigation]
|
||||
);
|
||||
|
||||
return null;
|
||||
};
|
||||
|
||||
@@ -7,6 +7,7 @@ import * as queryString from 'query-string';
|
||||
|
||||
import fromEntries from './fromEntries';
|
||||
import type { PathConfig, PathConfigMap } from './types';
|
||||
import validatePathConfig from './validatePathConfig';
|
||||
|
||||
type Options<ParamList> = {
|
||||
initialRouteName?: string;
|
||||
@@ -75,6 +76,10 @@ export default function getPathFromState<ParamList extends {}>(
|
||||
);
|
||||
}
|
||||
|
||||
if (options) {
|
||||
validatePathConfig(options);
|
||||
}
|
||||
|
||||
// Create a normalized configs object which will be easier to use
|
||||
const configs: Record<string, ConfigItem> = options?.screens
|
||||
? createNormalizedConfigs(options?.screens)
|
||||
|
||||
@@ -8,6 +8,7 @@ import * as queryString from 'query-string';
|
||||
|
||||
import findFocusedRoute from './findFocusedRoute';
|
||||
import type { PathConfigMap } from './types';
|
||||
import validatePathConfig from './validatePathConfig';
|
||||
|
||||
type Options<ParamList extends {}> = {
|
||||
initialRouteName?: string;
|
||||
@@ -65,6 +66,10 @@ export default function getStateFromPath<ParamList extends {}>(
|
||||
path: string,
|
||||
options?: Options<ParamList>
|
||||
): ResultState | undefined {
|
||||
if (options) {
|
||||
validatePathConfig(options);
|
||||
}
|
||||
|
||||
let initialRoutes: InitialRouteConfig[] = [];
|
||||
|
||||
if (options?.initialRouteName) {
|
||||
@@ -138,27 +143,31 @@ export default function getStateFromPath<ParamList extends {}>(
|
||||
const aParts = a.pattern.split('/');
|
||||
const bParts = b.pattern.split('/');
|
||||
|
||||
const aWildcardIndex = aParts.indexOf('*');
|
||||
const bWildcardIndex = bParts.indexOf('*');
|
||||
|
||||
// If only one of the patterns has a wildcard, move it down in the list
|
||||
if (aWildcardIndex === -1 && bWildcardIndex !== -1) {
|
||||
return -1;
|
||||
for (let i = 0; i < Math.max(aParts.length, bParts.length); i++) {
|
||||
// if b is longer, b get higher priority
|
||||
if (aParts[i] == null) {
|
||||
return 1;
|
||||
}
|
||||
// if a is longer, a get higher priority
|
||||
if (bParts[i] == null) {
|
||||
return -1;
|
||||
}
|
||||
const aWildCard = aParts[i] === '*' || aParts[i].startsWith(':');
|
||||
const bWildCard = bParts[i] === '*' || bParts[i].startsWith(':');
|
||||
// if both are wildcard we compare next component
|
||||
if (aWildCard && bWildCard) {
|
||||
continue;
|
||||
}
|
||||
// if only a is wild card, b get higher priority
|
||||
if (aWildCard) {
|
||||
return 1;
|
||||
}
|
||||
// if only b is wild card, a get higher priority
|
||||
if (bWildCard) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if (aWildcardIndex !== -1 && bWildcardIndex === -1) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (aWildcardIndex === bWildcardIndex) {
|
||||
// If `b` has more `/`, it's more exhaustive
|
||||
// So we move it up in the list
|
||||
return bParts.length - aParts.length;
|
||||
}
|
||||
|
||||
// If the wildcard appears later in the pattern (has higher index), it's more specific
|
||||
// So we move it up in the list
|
||||
return bWildcardIndex - aWildcardIndex;
|
||||
return bParts.length - aParts.length;
|
||||
});
|
||||
|
||||
// Check for duplicate patterns in the config
|
||||
|
||||
@@ -19,4 +19,5 @@ export { default as useNavigationBuilder } from './useNavigationBuilder';
|
||||
export { default as useNavigationContainerRef } from './useNavigationContainerRef';
|
||||
export { default as useNavigationState } from './useNavigationState';
|
||||
export { default as useRoute } from './useRoute';
|
||||
export { default as validatePathConfig } from './validatePathConfig';
|
||||
export * from '@react-navigation/routers';
|
||||
|
||||
@@ -524,43 +524,45 @@ export type NavigationContainerEventMap = {
|
||||
* Whether the action was a no-op, i.e. resulted any state changes.
|
||||
*/
|
||||
noop: boolean;
|
||||
/**
|
||||
* Stack trace of the action, this will only be available during development.
|
||||
*/
|
||||
stack: string | undefined;
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
export type NavigationContainerRef<
|
||||
ParamList extends {}
|
||||
> = NavigationHelpers<ParamList> &
|
||||
EventConsumer<NavigationContainerEventMap> & {
|
||||
/**
|
||||
* Reset the navigation state of the root navigator to the provided state.
|
||||
*
|
||||
* @param state Navigation state object.
|
||||
*/
|
||||
resetRoot(state?: PartialState<NavigationState> | NavigationState): void;
|
||||
/**
|
||||
* Get the rehydrated navigation state of the navigation tree.
|
||||
*/
|
||||
getRootState(): NavigationState;
|
||||
/**
|
||||
* Get the currently focused navigation route.
|
||||
*/
|
||||
getCurrentRoute(): Route<string> | undefined;
|
||||
/**
|
||||
* Get the currently focused route's options.
|
||||
*/
|
||||
getCurrentOptions(): object | undefined;
|
||||
/**
|
||||
* Whether the navigation container is ready to handle actions.
|
||||
*/
|
||||
isReady(): boolean;
|
||||
};
|
||||
export type NavigationContainerRef<ParamList extends {}> =
|
||||
NavigationHelpers<ParamList> &
|
||||
EventConsumer<NavigationContainerEventMap> & {
|
||||
/**
|
||||
* Reset the navigation state of the root navigator to the provided state.
|
||||
*
|
||||
* @param state Navigation state object.
|
||||
*/
|
||||
resetRoot(state?: PartialState<NavigationState> | NavigationState): void;
|
||||
/**
|
||||
* Get the rehydrated navigation state of the navigation tree.
|
||||
*/
|
||||
getRootState(): NavigationState;
|
||||
/**
|
||||
* Get the currently focused navigation route.
|
||||
*/
|
||||
getCurrentRoute(): Route<string> | undefined;
|
||||
/**
|
||||
* Get the currently focused route's options.
|
||||
*/
|
||||
getCurrentOptions(): object | undefined;
|
||||
/**
|
||||
* Whether the navigation container is ready to handle actions.
|
||||
*/
|
||||
isReady(): boolean;
|
||||
};
|
||||
|
||||
export type NavigationContainerRefWithCurrent<
|
||||
ParamList extends {}
|
||||
> = NavigationContainerRef<ParamList> & {
|
||||
current: NavigationContainerRef<ParamList> | null;
|
||||
};
|
||||
export type NavigationContainerRefWithCurrent<ParamList extends {}> =
|
||||
NavigationContainerRef<ParamList> & {
|
||||
current: NavigationContainerRef<ParamList> | null;
|
||||
};
|
||||
|
||||
export type TypedNavigator<
|
||||
ParamList extends ParamListBase,
|
||||
|
||||
@@ -60,10 +60,7 @@ type Options<
|
||||
navigation: any;
|
||||
options: ScreenOptions;
|
||||
}) => ScreenOptions);
|
||||
onAction: (
|
||||
action: NavigationAction,
|
||||
visitedNavigators?: Set<string>
|
||||
) => boolean;
|
||||
onAction: (action: NavigationAction) => boolean;
|
||||
getState: () => State;
|
||||
setState: (state: State) => void;
|
||||
addListener: AddListener;
|
||||
@@ -102,7 +99,7 @@ export default function useDescriptors<
|
||||
emitter,
|
||||
}: Options<State, ScreenOptions, EventMap>) {
|
||||
const [options, setOptions] = React.useState<Record<string, object>>({});
|
||||
const { onDispatchAction, onOptionsChange } = React.useContext(
|
||||
const { onDispatchAction, onOptionsChange, stackRef } = React.useContext(
|
||||
NavigationBuilderContext
|
||||
);
|
||||
|
||||
@@ -115,6 +112,7 @@ export default function useDescriptors<
|
||||
onRouteFocus,
|
||||
onDispatchAction,
|
||||
onOptionsChange,
|
||||
stackRef,
|
||||
}),
|
||||
[
|
||||
navigation,
|
||||
@@ -124,6 +122,7 @@ export default function useDescriptors<
|
||||
onRouteFocus,
|
||||
onDispatchAction,
|
||||
onOptionsChange,
|
||||
stackRef,
|
||||
]
|
||||
);
|
||||
|
||||
|
||||
@@ -2,11 +2,10 @@ import * as React from 'react';
|
||||
|
||||
import type { EventArg, EventConsumer, EventEmitter } from './types';
|
||||
|
||||
export type NavigationEventEmitter<
|
||||
T extends Record<string, any>
|
||||
> = EventEmitter<T> & {
|
||||
create: (target: string) => EventConsumer<T>;
|
||||
};
|
||||
export type NavigationEventEmitter<T extends Record<string, any>> =
|
||||
EventEmitter<T> & {
|
||||
create: (target: string) => EventConsumer<T>;
|
||||
};
|
||||
|
||||
type Listeners = ((e: any) => void)[];
|
||||
|
||||
|
||||
@@ -40,8 +40,8 @@ export default function useFocusedListenersChildrenAdapter({
|
||||
[focusedListeners, navigation]
|
||||
);
|
||||
|
||||
React.useEffect(() => addListener?.('focus', listener), [
|
||||
addListener,
|
||||
listener,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => addListener?.('focus', listener),
|
||||
[addListener, listener]
|
||||
);
|
||||
}
|
||||
|
||||
@@ -5,7 +5,6 @@ import type { KeyedListenerMap } from './NavigationBuilderContext';
|
||||
/**
|
||||
* Hook which lets child navigators add getters to be called for obtaining rehydrated state.
|
||||
*/
|
||||
|
||||
export default function useKeyedChildListeners() {
|
||||
const { current: keyedListeners } = React.useRef<
|
||||
{
|
||||
@@ -25,11 +24,9 @@ export default function useKeyedChildListeners() {
|
||||
key: string,
|
||||
listener: KeyedListenerMap[T]
|
||||
) => {
|
||||
// @ts-expect-error: listener should be correct type according to `type`
|
||||
keyedListeners[type][key] = listener;
|
||||
|
||||
return () => {
|
||||
// @ts-expect-error: listener should be correct type according to `type`
|
||||
keyedListeners[type][key] = undefined;
|
||||
};
|
||||
},
|
||||
|
||||
@@ -22,5 +22,5 @@ export default function useNavigation<
|
||||
}
|
||||
|
||||
// FIXME: Figure out a better way to do this
|
||||
return ((navigation ?? root) as unknown) as T;
|
||||
return (navigation ?? root) as unknown as T;
|
||||
}
|
||||
|
||||
@@ -220,7 +220,7 @@ export default function useNavigationBuilder<
|
||||
const { children, screenListeners, ...rest } = options;
|
||||
const { current: router } = React.useRef<Router<State, any>>(
|
||||
createRouter({
|
||||
...((rest as unknown) as RouterOptions),
|
||||
...(rest as unknown as RouterOptions),
|
||||
...(route?.params &&
|
||||
route.params.state == null &&
|
||||
route.params.initial !== false &&
|
||||
@@ -230,11 +230,8 @@ export default function useNavigationBuilder<
|
||||
})
|
||||
);
|
||||
|
||||
const routeConfigs = getRouteConfigsFromChildren<
|
||||
State,
|
||||
ScreenOptions,
|
||||
EventMap
|
||||
>(children);
|
||||
const routeConfigs =
|
||||
getRouteConfigsFromChildren<State, ScreenOptions, EventMap>(children);
|
||||
|
||||
const screens = routeConfigs.reduce<
|
||||
Record<string, ScreenConfigWithParent<State, ScreenOptions, EventMap>>
|
||||
|
||||
@@ -7,6 +7,7 @@ import {
|
||||
} from '@react-navigation/routers';
|
||||
import * as React from 'react';
|
||||
|
||||
import NavigationBuilderContext from './NavigationBuilderContext';
|
||||
import type { NavigationHelpers, NavigationProp } from './types';
|
||||
import type { NavigationEventEmitter } from './useEventEmitter';
|
||||
|
||||
@@ -51,6 +52,8 @@ export default function useNavigationCache<
|
||||
router,
|
||||
emitter,
|
||||
}: Options<State, EventMap>) {
|
||||
const { stackRef } = React.useContext(NavigationBuilderContext);
|
||||
|
||||
// Cache object which holds navigation objects for each screen
|
||||
// We use `React.useMemo` instead of `React.useRef` coz we want to invalidate it when deps change
|
||||
// In reality, these deps will rarely change, if ever
|
||||
@@ -70,6 +73,10 @@ export default function useNavigationCache<
|
||||
>((acc, route) => {
|
||||
const previous = cache.current[route.key];
|
||||
|
||||
type Thunk =
|
||||
| NavigationAction
|
||||
| ((state: State) => NavigationAction | null | undefined);
|
||||
|
||||
if (previous) {
|
||||
// If a cached navigation object already exists, reuse it
|
||||
acc[route.key] = previous;
|
||||
@@ -77,11 +84,7 @@ export default function useNavigationCache<
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const { emit, ...rest } = navigation;
|
||||
|
||||
const dispatch = (
|
||||
thunk:
|
||||
| NavigationAction
|
||||
| ((state: State) => NavigationAction | null | undefined)
|
||||
) => {
|
||||
const dispatch = (thunk: Thunk) => {
|
||||
const action = typeof thunk === 'function' ? thunk(getState()) : thunk;
|
||||
|
||||
if (action != null) {
|
||||
@@ -89,10 +92,36 @@ export default function useNavigationCache<
|
||||
}
|
||||
};
|
||||
|
||||
const withStack = (callback: () => void) => {
|
||||
let isStackSet = false;
|
||||
|
||||
try {
|
||||
if (
|
||||
process.env.NODE_ENV !== 'production' &&
|
||||
stackRef &&
|
||||
!stackRef.current
|
||||
) {
|
||||
// Capture the stack trace for devtools
|
||||
stackRef.current = new Error().stack;
|
||||
isStackSet = true;
|
||||
}
|
||||
|
||||
callback();
|
||||
} finally {
|
||||
if (isStackSet && stackRef) {
|
||||
stackRef.current = undefined;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const helpers = Object.keys(actions).reduce<Record<string, () => void>>(
|
||||
(acc, name) => {
|
||||
// @ts-expect-error: name is a valid key, but TypeScript is dumb
|
||||
acc[name] = (...args: any) => dispatch(actions[name](...args));
|
||||
acc[name] = (...args: any) =>
|
||||
withStack(() =>
|
||||
// @ts-expect-error: name is a valid key, but TypeScript is dumb
|
||||
dispatch(actions[name](...args))
|
||||
);
|
||||
|
||||
return acc;
|
||||
},
|
||||
{}
|
||||
@@ -103,7 +132,7 @@ export default function useNavigationCache<
|
||||
...helpers,
|
||||
// FIXME: too much work to fix the types for now
|
||||
...(emitter.create(route.key) as any),
|
||||
dispatch,
|
||||
dispatch: (thunk: Thunk) => withStack(() => dispatch(thunk)),
|
||||
setOptions: (options: object) =>
|
||||
setOptions((o) => ({
|
||||
...o,
|
||||
|
||||
@@ -6,9 +6,8 @@ import type { NavigationContainerRefWithCurrent } from './types';
|
||||
export default function useNavigationContainerRef<
|
||||
ParamList extends {} = ReactNavigation.RootParamList
|
||||
>(): NavigationContainerRefWithCurrent<ParamList> {
|
||||
const navigation = React.useRef<NavigationContainerRefWithCurrent<ParamList> | null>(
|
||||
null
|
||||
);
|
||||
const navigation =
|
||||
React.useRef<NavigationContainerRefWithCurrent<ParamList> | null>(null);
|
||||
|
||||
if (navigation.current == null) {
|
||||
navigation.current = createNavigationContainerRef<ParamList>();
|
||||
|
||||
@@ -17,10 +17,7 @@ import type { NavigationEventEmitter } from './useEventEmitter';
|
||||
PrivateValueStore;
|
||||
|
||||
type Options<State extends NavigationState, Action extends NavigationAction> = {
|
||||
onAction: (
|
||||
action: NavigationAction,
|
||||
visitedNavigators?: Set<string>
|
||||
) => boolean;
|
||||
onAction: (action: NavigationAction) => boolean;
|
||||
getState: () => State;
|
||||
emitter: NavigationEventEmitter<any>;
|
||||
router: Router<State, Action>;
|
||||
|
||||
@@ -52,9 +52,8 @@ export default function useOnAction({
|
||||
onDispatchAction,
|
||||
} = React.useContext(NavigationBuilderContext);
|
||||
|
||||
const routerConfigOptionsRef = React.useRef<RouterConfigOptions>(
|
||||
routerConfigOptions
|
||||
);
|
||||
const routerConfigOptionsRef =
|
||||
React.useRef<RouterConfigOptions>(routerConfigOptions);
|
||||
|
||||
React.useEffect(() => {
|
||||
routerConfigOptionsRef.current = routerConfigOptions;
|
||||
@@ -158,10 +157,10 @@ export default function useOnAction({
|
||||
beforeRemoveListeners,
|
||||
});
|
||||
|
||||
React.useEffect(() => addListenerParent?.('action', onAction), [
|
||||
addListenerParent,
|
||||
onAction,
|
||||
]);
|
||||
React.useEffect(
|
||||
() => addListenerParent?.('action', onAction),
|
||||
[addListenerParent, onAction]
|
||||
);
|
||||
|
||||
return onAction;
|
||||
}
|
||||
|
||||
32
packages/core/src/validatePathConfig.tsx
Normal file
32
packages/core/src/validatePathConfig.tsx
Normal file
@@ -0,0 +1,32 @@
|
||||
const formatToList = (items: string[]) =>
|
||||
items.map((key) => `- ${key}`).join('\n');
|
||||
|
||||
export default function validatePathConfig(config: any, root = true) {
|
||||
const validKeys = ['initialRouteName', 'screens'];
|
||||
|
||||
if (!root) {
|
||||
validKeys.push('path', 'exact', 'stringify', 'parse');
|
||||
}
|
||||
|
||||
const invalidKeys = Object.keys(config).filter(
|
||||
(key) => !validKeys.includes(key)
|
||||
);
|
||||
|
||||
if (invalidKeys.length) {
|
||||
throw new Error(
|
||||
`Found invalid properties in the configuration:\n${formatToList(
|
||||
invalidKeys
|
||||
)}\n\nDid you forget to specify them under a 'screens' property?\n\nYou can only specify the following properties:\n${formatToList(
|
||||
validKeys
|
||||
)}\n\nSee https://reactnavigation.org/docs/configuring-links for more details on how to specify a linking configuration.`
|
||||
);
|
||||
}
|
||||
|
||||
if (config.screens) {
|
||||
Object.entries(config.screens).forEach(([_, value]) => {
|
||||
if (typeof value !== 'string') {
|
||||
validatePathConfig(value, false);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
@@ -3,6 +3,25 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.15](https://github.com/react-navigation/react-navigation/compare/@react-navigation/devtools@6.0.0-next.14...@react-navigation/devtools@6.0.0-next.15) (2021-06-10)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* show stack trace in the flipper plugin ([97772af](https://github.com/react-navigation/react-navigation/commit/97772affa3c8f26489f0bdbfb6872ef4377b8ed1))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.14](https://github.com/react-navigation/react-navigation/compare/@react-navigation/devtools@6.0.0-next.13...@react-navigation/devtools@6.0.0-next.14) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/devtools
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.13](https://github.com/react-navigation/react-navigation/compare/@react-navigation/devtools@6.0.0-next.12...@react-navigation/devtools@6.0.0-next.13) (2021-05-29)
|
||||
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/devtools",
|
||||
"description": "Developer tools for React Navigation",
|
||||
"version": "6.0.0-next.13",
|
||||
"version": "6.0.0-next.15",
|
||||
"keywords": [
|
||||
"react",
|
||||
"react-native",
|
||||
@@ -37,18 +37,18 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"deep-equal": "^2.0.5",
|
||||
"nanoid": "^3.1.22"
|
||||
"nanoid": "^3.1.23"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-navigation/core": "^6.0.0-next.12",
|
||||
"@react-navigation/core": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/deep-equal": "^1.0.1",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react": "^17.0.9",
|
||||
"del-cli": "^3.0.1",
|
||||
"react": "~16.13.1",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-native-flipper": "^0.80.0",
|
||||
"typescript": "^4.2.3"
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"react": "*"
|
||||
|
||||
@@ -6,20 +6,42 @@ import type {
|
||||
import deepEqual from 'deep-equal';
|
||||
import * as React from 'react';
|
||||
|
||||
type StackFrame = {
|
||||
lineNumber: number | null;
|
||||
column: number | null;
|
||||
file: string | null;
|
||||
methodName: string;
|
||||
};
|
||||
|
||||
type StackFrameResult = StackFrame & {
|
||||
collapse: boolean;
|
||||
};
|
||||
|
||||
type StackResult = {
|
||||
stack: StackFrameResult[];
|
||||
};
|
||||
|
||||
type InitData = {
|
||||
type: 'init';
|
||||
state: NavigationState | undefined;
|
||||
};
|
||||
|
||||
type ActionData = {
|
||||
type: 'action';
|
||||
action: NavigationAction;
|
||||
state: NavigationState | undefined;
|
||||
stack: string | undefined;
|
||||
};
|
||||
|
||||
export default function useDevToolsBase(
|
||||
ref: React.RefObject<NavigationContainerRef<any>>,
|
||||
callback: (
|
||||
...args:
|
||||
| [type: 'init', state: NavigationState | undefined]
|
||||
| [
|
||||
type: 'action',
|
||||
action: NavigationAction,
|
||||
state: NavigationState | undefined
|
||||
]
|
||||
) => void
|
||||
callback: (result: InitData | ActionData) => void
|
||||
) {
|
||||
const lastStateRef = React.useRef<NavigationState | undefined>();
|
||||
const lastActionRef = React.useRef<NavigationAction | undefined>();
|
||||
const lastActionRef =
|
||||
React.useRef<
|
||||
{ action: NavigationAction; stack: string | undefined } | undefined
|
||||
>();
|
||||
const callbackRef = React.useRef(callback);
|
||||
const lastResetRef = React.useRef<NavigationState | undefined>(undefined);
|
||||
|
||||
@@ -27,8 +49,73 @@ export default function useDevToolsBase(
|
||||
callbackRef.current = callback;
|
||||
});
|
||||
|
||||
const symbolicate = async (stack: string | undefined) => {
|
||||
if (stack == null) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
const frames = stack
|
||||
.split('\n')
|
||||
.slice(2)
|
||||
.map((line): StackFrame | null => {
|
||||
const partMatch = line.match(/^((.+)@)?(.+):(\d+):(\d+)$/);
|
||||
|
||||
if (!partMatch) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const [, , methodName, file, lineNumber, column] = partMatch;
|
||||
|
||||
return {
|
||||
methodName,
|
||||
file,
|
||||
lineNumber: Number(lineNumber),
|
||||
column: Number(column),
|
||||
};
|
||||
})
|
||||
.filter(Boolean) as StackFrame[];
|
||||
|
||||
const urlMatch = frames[0].file?.match(/^https?:\/\/.+(:\d+)?\//);
|
||||
|
||||
if (!urlMatch) {
|
||||
return stack;
|
||||
}
|
||||
|
||||
try {
|
||||
const result: StackResult = await fetch(`${urlMatch[0]}symbolicate`, {
|
||||
method: 'POST',
|
||||
body: JSON.stringify({ stack: frames }),
|
||||
}).then((res) => res.json());
|
||||
|
||||
return result.stack
|
||||
.filter((it) => !it.collapse)
|
||||
.map(
|
||||
({ methodName, file, lineNumber, column }) =>
|
||||
`${methodName}@${file}:${lineNumber}:${column}`
|
||||
)
|
||||
.join('\n');
|
||||
} catch (err) {
|
||||
return stack;
|
||||
}
|
||||
};
|
||||
|
||||
const pendingPromiseRef = React.useRef<Promise<void>>(Promise.resolve());
|
||||
|
||||
const send = React.useCallback((data: ActionData) => {
|
||||
// We need to make sure that our callbacks executed in the same order
|
||||
pendingPromiseRef.current = pendingPromiseRef.current.then(async () => {
|
||||
if (data.stack) {
|
||||
const stack = await symbolicate(data.stack);
|
||||
|
||||
callbackRef.current({ ...data, stack });
|
||||
} else {
|
||||
callbackRef.current(data);
|
||||
}
|
||||
});
|
||||
}, []);
|
||||
|
||||
React.useEffect(() => {
|
||||
let timer: number;
|
||||
let timer: any;
|
||||
let unsubscribeAction: (() => void) | undefined;
|
||||
let unsubscribeState: (() => void) | undefined;
|
||||
|
||||
@@ -43,7 +130,7 @@ export default function useDevToolsBase(
|
||||
const state = ref.current.getRootState();
|
||||
|
||||
lastStateRef.current = state;
|
||||
callbackRef.current('init', state);
|
||||
callbackRef.current({ type: 'init', state });
|
||||
}
|
||||
}, 100);
|
||||
});
|
||||
@@ -56,9 +143,14 @@ export default function useDevToolsBase(
|
||||
|
||||
if (e.data.noop) {
|
||||
// Even if the state didn't change, it's useful to show the action
|
||||
callbackRef.current('action', action, lastStateRef.current);
|
||||
send({
|
||||
type: 'action',
|
||||
action,
|
||||
state: lastStateRef.current,
|
||||
stack: e.data.stack,
|
||||
});
|
||||
} else {
|
||||
lastActionRef.current = action;
|
||||
lastActionRef.current = e.data;
|
||||
}
|
||||
});
|
||||
|
||||
@@ -74,17 +166,22 @@ export default function useDevToolsBase(
|
||||
|
||||
const state = navigation.getRootState();
|
||||
const lastState = lastStateRef.current;
|
||||
const action = lastActionRef.current;
|
||||
const lastChange = lastActionRef.current;
|
||||
|
||||
lastActionRef.current = undefined;
|
||||
lastStateRef.current = state;
|
||||
|
||||
// If we don't have an action and the state didn't change, then it's probably extraneous
|
||||
if (action === undefined && deepEqual(state, lastState)) {
|
||||
if (lastChange === undefined && deepEqual(state, lastState)) {
|
||||
return;
|
||||
}
|
||||
|
||||
callbackRef.current('action', action ?? { type: '@@UNKNOWN' }, state);
|
||||
send({
|
||||
type: 'action',
|
||||
action: lastChange ? lastChange.action : { type: '@@UNKNOWN' },
|
||||
state,
|
||||
stack: lastChange?.stack,
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
@@ -95,7 +192,7 @@ export default function useDevToolsBase(
|
||||
unsubscribeState?.();
|
||||
clearTimeout(timer);
|
||||
};
|
||||
}, [ref]);
|
||||
}, [ref, send]);
|
||||
|
||||
const resetRoot = React.useCallback(
|
||||
(state: NavigationState) => {
|
||||
|
||||
@@ -26,25 +26,26 @@ export default function useFlipper(
|
||||
|
||||
const connectionRef = React.useRef<Flipper.FlipperConnection>();
|
||||
|
||||
const { resetRoot } = useDevToolsBase(ref, (...args) => {
|
||||
const { resetRoot } = useDevToolsBase(ref, (result) => {
|
||||
const connection = connectionRef.current;
|
||||
|
||||
if (!connection) {
|
||||
return;
|
||||
}
|
||||
|
||||
switch (args[0]) {
|
||||
switch (result.type) {
|
||||
case 'init':
|
||||
connection.send('init', {
|
||||
id: nanoid(),
|
||||
state: args[1],
|
||||
state: result.state,
|
||||
});
|
||||
break;
|
||||
case 'action':
|
||||
connection.send('action', {
|
||||
id: nanoid(),
|
||||
action: args[1],
|
||||
state: args[2],
|
||||
action: result.action,
|
||||
state: result.state,
|
||||
stack: result.stack,
|
||||
});
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -32,19 +32,19 @@ export default function useReduxDevToolsExtension(
|
||||
});
|
||||
}
|
||||
|
||||
const { resetRoot } = useDevToolsBase(ref, (...args) => {
|
||||
const { resetRoot } = useDevToolsBase(ref, (result) => {
|
||||
const devTools = devToolsRef.current;
|
||||
|
||||
if (!devTools) {
|
||||
return;
|
||||
}
|
||||
|
||||
switch (args[0]) {
|
||||
switch (result.type) {
|
||||
case 'init':
|
||||
devTools.init(args[1]);
|
||||
devTools.init(result.state);
|
||||
break;
|
||||
case 'action':
|
||||
devTools.send(args[1], args[2]);
|
||||
devTools.send(result.action, result.state);
|
||||
break;
|
||||
}
|
||||
});
|
||||
|
||||
@@ -3,6 +3,30 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.18](https://github.com/react-navigation/react-navigation/compare/@react-navigation/drawer@6.0.0-next.17...@react-navigation/drawer@6.0.0-next.18) (2021-06-10)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/drawer
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.17](https://github.com/react-navigation/react-navigation/compare/@react-navigation/drawer@6.0.0-next.16...@react-navigation/drawer@6.0.0-next.17) (2021-06-01)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/drawer
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.16](https://github.com/react-navigation/react-navigation/compare/@react-navigation/drawer@6.0.0-next.15...@react-navigation/drawer@6.0.0-next.16) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/drawer
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.15](https://github.com/react-navigation/react-navigation/compare/@react-navigation/drawer@6.0.0-next.14...@react-navigation/drawer@6.0.0-next.15) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/drawer
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/drawer",
|
||||
"description": "Drawer navigator component with animated transitions and gesturess",
|
||||
"version": "6.0.0-next.15",
|
||||
"version": "6.0.0-next.18",
|
||||
"keywords": [
|
||||
"react-native-component",
|
||||
"react-component",
|
||||
@@ -41,24 +41,24 @@
|
||||
"clean": "del lib"
|
||||
},
|
||||
"dependencies": {
|
||||
"@react-navigation/elements": "^1.0.0-next.15",
|
||||
"@react-navigation/elements": "^1.0.0-next.18",
|
||||
"color": "^3.1.3",
|
||||
"warn-once": "^0.1.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-navigation/native": "^6.0.0-next.12",
|
||||
"@react-navigation/native": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-native": "~0.64.4",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"del-cli": "^3.0.1",
|
||||
"react": "~16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-native-gesture-handler": "~1.10.2",
|
||||
"react-native-reanimated": "~2.1.0",
|
||||
"react-native-reanimated": "~2.2.0",
|
||||
"react-native-safe-area-context": "~3.2.0",
|
||||
"react-native-screens": "~3.0.0",
|
||||
"typescript": "^4.2.3"
|
||||
"react-native-screens": "~3.3.0",
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@react-navigation/native": "^6.0.0",
|
||||
|
||||
@@ -74,26 +74,22 @@ function DrawerNavigator({
|
||||
);
|
||||
}
|
||||
|
||||
const {
|
||||
state,
|
||||
descriptors,
|
||||
navigation,
|
||||
NavigationContent,
|
||||
} = useNavigationBuilder<
|
||||
DrawerNavigationState<ParamListBase>,
|
||||
DrawerRouterOptions,
|
||||
DrawerActionHelpers<ParamListBase>,
|
||||
DrawerNavigationOptions,
|
||||
DrawerNavigationEventMap
|
||||
>(DrawerRouter, {
|
||||
initialRouteName,
|
||||
defaultStatus,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
defaultScreenOptions,
|
||||
});
|
||||
const { state, descriptors, navigation, NavigationContent } =
|
||||
useNavigationBuilder<
|
||||
DrawerNavigationState<ParamListBase>,
|
||||
DrawerRouterOptions,
|
||||
DrawerActionHelpers<ParamListBase>,
|
||||
DrawerNavigationOptions,
|
||||
DrawerNavigationEventMap
|
||||
>(DrawerRouter, {
|
||||
initialRouteName,
|
||||
defaultStatus,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
defaultScreenOptions,
|
||||
});
|
||||
|
||||
return (
|
||||
<NavigationContent>
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
import * as React from 'react';
|
||||
|
||||
const DrawerStatusContext = React.createContext<'open' | 'closed' | undefined>(
|
||||
undefined
|
||||
);
|
||||
const DrawerStatusContext =
|
||||
React.createContext<'open' | 'closed' | undefined>(undefined);
|
||||
|
||||
export default DrawerStatusContext;
|
||||
|
||||
@@ -9,9 +9,8 @@ export default function DrawerContent({
|
||||
state,
|
||||
...rest
|
||||
}: DrawerContentComponentProps) {
|
||||
const { drawerContentStyle, drawerContentContainerStyle } = descriptors[
|
||||
state.routes[state.index].key
|
||||
].options;
|
||||
const { drawerContentStyle, drawerContentContainerStyle } =
|
||||
descriptors[state.routes[state.index].key].options;
|
||||
|
||||
return (
|
||||
<DrawerContentScrollView
|
||||
|
||||
@@ -26,7 +26,7 @@ export default function DrawerItemList({
|
||||
}: Props) {
|
||||
const buildLink = useLinkBuilder();
|
||||
|
||||
return (state.routes.map((route, i) => {
|
||||
return state.routes.map((route, i) => {
|
||||
const focused = i === state.index;
|
||||
const {
|
||||
title,
|
||||
@@ -69,5 +69,5 @@ export default function DrawerItemList({
|
||||
}}
|
||||
/>
|
||||
);
|
||||
}) as React.ReactNode) as React.ReactElement;
|
||||
}) as React.ReactNode as React.ReactElement;
|
||||
}
|
||||
|
||||
@@ -238,7 +238,8 @@ function DrawerViewBase({
|
||||
header={header({
|
||||
layout: dimensions,
|
||||
route: descriptor.route,
|
||||
navigation: descriptor.navigation as DrawerNavigationProp<ParamListBase>,
|
||||
navigation:
|
||||
descriptor.navigation as DrawerNavigationProp<ParamListBase>,
|
||||
options: descriptor.options,
|
||||
})}
|
||||
style={sceneContainerStyle}
|
||||
|
||||
@@ -9,9 +9,11 @@ const Dummy: any = ({ children }: { children: React.ReactNode }) => (
|
||||
<>{children}</>
|
||||
);
|
||||
|
||||
export const PanGestureHandler = Dummy as React.ComponentType<PanGestureHandlerProperties>;
|
||||
export const PanGestureHandler =
|
||||
Dummy as React.ComponentType<PanGestureHandlerProperties>;
|
||||
|
||||
export const TapGestureHandler = Dummy as React.ComponentType<TapGestureHandlerProperties>;
|
||||
export const TapGestureHandler =
|
||||
Dummy as React.ComponentType<TapGestureHandlerProperties>;
|
||||
|
||||
export const GestureHandlerRootView = View;
|
||||
|
||||
|
||||
@@ -471,10 +471,8 @@ export default class DrawerView extends React.Component<DrawerProps> {
|
||||
};
|
||||
|
||||
private toggleStatusBar = (hidden: boolean) => {
|
||||
const {
|
||||
hideStatusBarOnOpen: hideStatusBar,
|
||||
statusBarAnimation,
|
||||
} = this.props;
|
||||
const { hideStatusBarOnOpen: hideStatusBar, statusBarAnimation } =
|
||||
this.props;
|
||||
|
||||
if (hideStatusBar && this.isStatusBarHidden !== hidden) {
|
||||
this.isStatusBarHidden = hidden;
|
||||
|
||||
@@ -3,6 +3,33 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [1.0.0-next.18](https://github.com/react-navigation/react-navigation/compare/@react-navigation/elements@1.0.0-next.17...@react-navigation/elements@1.0.0-next.18) (2021-06-10)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/elements
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [1.0.0-next.17](https://github.com/react-navigation/react-navigation/compare/@react-navigation/elements@1.0.0-next.16...@react-navigation/elements@1.0.0-next.17) (2021-06-01)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* tweak opacity animation for PlatformPressable ([b46c433](https://github.com/react-navigation/react-navigation/commit/b46c433f1e012fc3215ec32ac787c7c018963505))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [1.0.0-next.16](https://github.com/react-navigation/react-navigation/compare/@react-navigation/elements@1.0.0-next.15...@react-navigation/elements@1.0.0-next.16) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/elements
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [1.0.0-next.15](https://github.com/react-navigation/react-navigation/compare/@react-navigation/elements@1.0.0-next.14...@react-navigation/elements@1.0.0-next.15) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/elements
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/elements",
|
||||
"description": "UI Components for React Navigation",
|
||||
"version": "1.0.0-next.15",
|
||||
"version": "1.0.0-next.18",
|
||||
"keywords": [
|
||||
"react-native",
|
||||
"react-navigation",
|
||||
@@ -37,16 +37,16 @@
|
||||
"clean": "del lib"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-native-masked-view/masked-view": "^0.2.3",
|
||||
"@react-navigation/native": "^6.0.0-next.12",
|
||||
"@react-native-masked-view/masked-view": "^0.2.4",
|
||||
"@react-navigation/native": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-native": "~0.64.4",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"del-cli": "^3.0.1",
|
||||
"react": "~16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"typescript": "^4.2.3"
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@react-navigation/native": "^6.0.0",
|
||||
|
||||
@@ -35,9 +35,8 @@ export default function HeaderBackButton({
|
||||
}: HeaderBackButtonProps) {
|
||||
const { colors } = useTheme();
|
||||
|
||||
const [initialLabelWidth, setInitialLabelWidth] = React.useState<
|
||||
undefined | number
|
||||
>(undefined);
|
||||
const [initialLabelWidth, setInitialLabelWidth] =
|
||||
React.useState<undefined | number>(undefined);
|
||||
|
||||
const tintColor =
|
||||
customTintColor !== undefined
|
||||
|
||||
@@ -4,7 +4,8 @@
|
||||
import * as React from 'react';
|
||||
import { UIManager } from 'react-native';
|
||||
|
||||
type MaskedViewType = typeof import('@react-native-masked-view/masked-view').default;
|
||||
type MaskedViewType =
|
||||
typeof import('@react-native-masked-view/masked-view').default;
|
||||
|
||||
type Props = React.ComponentProps<MaskedViewType> & {
|
||||
children: React.ReactElement;
|
||||
|
||||
@@ -53,7 +53,7 @@ export default function PlatformPressable({
|
||||
};
|
||||
|
||||
const handlePressIn = (e: GestureResponderEvent) => {
|
||||
animateTo(pressOpacity, 150);
|
||||
animateTo(pressOpacity, 0);
|
||||
onPressIn?.(e);
|
||||
};
|
||||
|
||||
|
||||
@@ -3,6 +3,25 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [1.2.0](https://github.com/react-navigation/react-navigation/compare/flipper-plugin-react-navigation@1.1.4...flipper-plugin-react-navigation@1.2.0) (2021-06-10)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* show stack trace in the flipper plugin ([97772af](https://github.com/react-navigation/react-navigation/commit/97772affa3c8f26489f0bdbfb6872ef4377b8ed1))
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [1.1.4](https://github.com/react-navigation/react-navigation/compare/flipper-plugin-react-navigation@1.1.3...flipper-plugin-react-navigation@1.1.4) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package flipper-plugin-react-navigation
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [1.1.3](https://github.com/react-navigation/react-navigation/compare/flipper-plugin-react-navigation@1.1.2...flipper-plugin-react-navigation@1.1.3) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package flipper-plugin-react-navigation
|
||||
|
||||
21
packages/flipper-plugin-react-navigation/LICENSE
Normal file
21
packages/flipper-plugin-react-navigation/LICENSE
Normal file
@@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2017 React Navigation Contributors
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
5
packages/flipper-plugin-react-navigation/README.md
Normal file
5
packages/flipper-plugin-react-navigation/README.md
Normal file
@@ -0,0 +1,5 @@
|
||||
# `flipper-plugin-react-navigation`
|
||||
|
||||
Flipper plugin with developer tools for React Navigation.
|
||||
|
||||
Installation instructions and documentation can be found on the [React Navigation website](https://reactnavigation.org/docs/6.x/devtools).
|
||||
@@ -1,17 +1,23 @@
|
||||
{
|
||||
"$schema": "https://fbflipper.com/schemas/plugin-package/v2.json",
|
||||
"name": "flipper-plugin-react-navigation",
|
||||
"id": "react-navigation",
|
||||
"version": "1.1.3",
|
||||
"pluginType": "client",
|
||||
"description": "Developer tools for React Navigation",
|
||||
"version": "1.2.0",
|
||||
"main": "dist/bundle.js",
|
||||
"flipperBundlerEntry": "src/index.tsx",
|
||||
"license": "MIT",
|
||||
"keywords": [
|
||||
"flipper-plugin"
|
||||
],
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/react-navigation/react-navigation.git",
|
||||
"directory": "packages/flipper-plugin-react-navigation"
|
||||
},
|
||||
"id": "react-navigation",
|
||||
"pluginType": "client",
|
||||
"icon": "directions",
|
||||
"title": "React Navigation",
|
||||
"flipperBundlerEntry": "src/index.tsx",
|
||||
"scripts": {
|
||||
"lint": "flipper-pkg lint",
|
||||
"prepack": "flipper-pkg lint && flipper-pkg bundle",
|
||||
@@ -28,17 +34,14 @@
|
||||
"@ant-design/icons": "^4.6.2",
|
||||
"@babel/preset-react": "^7.12.13",
|
||||
"@babel/preset-typescript": "^7.13.0",
|
||||
"@react-navigation/core": "^6.0.0-next.12",
|
||||
"@types/react": "^17.0.3",
|
||||
"@types/react-dom": "^17.0.2",
|
||||
"antd": "^4.14.0",
|
||||
"flipper": "^0.90.2",
|
||||
"flipper-pkg": "^0.90.2",
|
||||
"flipper-plugin": "^0.90.2",
|
||||
"@react-navigation/core": "^6.0.0-next.14",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-dom": "^17.0.6",
|
||||
"antd": "^4.16.1",
|
||||
"flipper": "^0.92.0",
|
||||
"flipper-pkg": "^0.92.0",
|
||||
"flipper-plugin": "^0.92.0",
|
||||
"react": "^17.0.1",
|
||||
"react-dom": "^17.0.1"
|
||||
},
|
||||
"dependencies": {
|
||||
"shortid": "^2.2.16"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,13 +19,11 @@ export function LinkingTester({ linking, active }: Props) {
|
||||
const [rawConfig, setRawConfig] = React.useState('');
|
||||
const [path, setPath] = React.useState('');
|
||||
|
||||
const [state, setState] = React.useState<
|
||||
ReturnType<typeof getStateFromPath> | undefined
|
||||
>();
|
||||
const [state, setState] =
|
||||
React.useState<ReturnType<typeof getStateFromPath> | undefined>();
|
||||
|
||||
const [action, setAction] = React.useState<
|
||||
ReturnType<typeof getActionFromState> | undefined
|
||||
>();
|
||||
const [action, setAction] =
|
||||
React.useState<ReturnType<typeof getActionFromState> | undefined>();
|
||||
|
||||
const [error, setError] = React.useState<string | undefined>();
|
||||
|
||||
|
||||
@@ -45,7 +45,11 @@ export function Logs({ active, logs, index, resetTo }: Props) {
|
||||
{active ? (
|
||||
<DetailSidebar>
|
||||
{selectedItem && (
|
||||
<Sidebar action={selectedItem.action} state={selectedItem.state} />
|
||||
<Sidebar
|
||||
action={selectedItem.action}
|
||||
state={selectedItem.state}
|
||||
stack={selectedItem.stack}
|
||||
/>
|
||||
)}
|
||||
</DetailSidebar>
|
||||
) : null}
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { Layout, ManagedDataInspector } from 'flipper';
|
||||
import { Layout, ManagedDataInspector, styled } from 'flipper';
|
||||
import { theme } from 'flipper-plugin';
|
||||
import * as React from 'react';
|
||||
|
||||
import { Title4 } from './Typography';
|
||||
@@ -6,12 +7,65 @@ import { Title4 } from './Typography';
|
||||
export function Sidebar({
|
||||
action,
|
||||
state,
|
||||
stack,
|
||||
}: {
|
||||
action: object;
|
||||
state: object | undefined;
|
||||
stack: string | undefined;
|
||||
}) {
|
||||
return (
|
||||
<Layout.Container gap pad>
|
||||
{stack ? (
|
||||
<>
|
||||
<Title4>Stack</Title4>
|
||||
<Code>
|
||||
{stack.split('\n').map((line, index) => {
|
||||
const match = line.match(/^(.+)@(.+):(\d+):(\d+)$/);
|
||||
|
||||
if (match) {
|
||||
const [, methodName, file, lineNumber, column] = match;
|
||||
|
||||
if (file.includes('/node_modules/@react-navigation')) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return (
|
||||
// eslint-disable-next-line react/no-array-index-key
|
||||
<div key={index}>
|
||||
{methodName.split('.').map((part, i, self) => {
|
||||
if (i === self.length - 1 && i !== 0) {
|
||||
return <Method>{part}</Method>;
|
||||
}
|
||||
|
||||
if (self.length !== 1) {
|
||||
return (
|
||||
<>
|
||||
{part}
|
||||
<Separator>.</Separator>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
return part;
|
||||
})}{' '}
|
||||
<Separator>(</Separator>
|
||||
<StringToken>{file.split('/').pop()}</StringToken>
|
||||
<Separator>:</Separator>
|
||||
<NumberToken>{lineNumber}</NumberToken>:
|
||||
<NumberToken>{column}</NumberToken>
|
||||
<Separator>)</Separator>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
// eslint-disable-next-line react/no-array-index-key
|
||||
<div key={index}>{line}</div>
|
||||
);
|
||||
})}
|
||||
</Code>
|
||||
</>
|
||||
) : null}
|
||||
<Title4>Action</Title4>
|
||||
<ManagedDataInspector data={action} expandRoot={false} />
|
||||
<Title4>State</Title4>
|
||||
@@ -19,3 +73,25 @@ export function Sidebar({
|
||||
</Layout.Container>
|
||||
);
|
||||
}
|
||||
|
||||
const Code = styled.div({
|
||||
fontSize: 11,
|
||||
fontFamily: theme.monospace.fontFamily,
|
||||
margin: '7.5px 0px',
|
||||
});
|
||||
|
||||
const StringToken = styled.span({
|
||||
color: 'rgb(224, 76, 96)',
|
||||
});
|
||||
|
||||
const NumberToken = styled.span({
|
||||
color: 'rgb(77, 187, 166)',
|
||||
});
|
||||
|
||||
const Method = styled.span({
|
||||
color: 'rgb(123, 100, 192)',
|
||||
});
|
||||
|
||||
const Separator = styled.span({
|
||||
color: '#555',
|
||||
});
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
import { styled } from 'flipper';
|
||||
import { theme } from 'flipper-plugin';
|
||||
|
||||
export const Title4 = styled.h4({
|
||||
fontWeight: 600,
|
||||
fontSize: 14,
|
||||
fontSize: theme.fontSize.default,
|
||||
lineHeight: 1.4,
|
||||
letterSpacing: -0.24,
|
||||
marginBottom: 0,
|
||||
|
||||
@@ -30,6 +30,7 @@ export type Log = {
|
||||
id: string;
|
||||
action: NavigationAction;
|
||||
state: NavigationState | undefined;
|
||||
stack: string | undefined;
|
||||
};
|
||||
|
||||
export type StoreType = {
|
||||
|
||||
@@ -3,6 +3,30 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.15](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-bottom-tabs@6.0.0-next.14...@react-navigation/material-bottom-tabs@6.0.0-next.15) (2021-06-10)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-bottom-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.14](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-bottom-tabs@6.0.0-next.13...@react-navigation/material-bottom-tabs@6.0.0-next.14) (2021-06-01)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-bottom-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.13](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-bottom-tabs@6.0.0-next.12...@react-navigation/material-bottom-tabs@6.0.0-next.13) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-bottom-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.12](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-bottom-tabs@6.0.0-next.11...@react-navigation/material-bottom-tabs@6.0.0-next.12) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-bottom-tabs
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/material-bottom-tabs",
|
||||
"description": "Integration for bottom navigation component from react-native-paper",
|
||||
"version": "6.0.0-next.12",
|
||||
"version": "6.0.0-next.15",
|
||||
"keywords": [
|
||||
"react-native-component",
|
||||
"react-component",
|
||||
@@ -41,22 +41,22 @@
|
||||
"clean": "del lib"
|
||||
},
|
||||
"dependencies": {
|
||||
"@react-navigation/elements": "^1.0.0-next.15"
|
||||
"@react-navigation/elements": "^1.0.0-next.18"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-navigation/native": "^6.0.0-next.12",
|
||||
"@react-navigation/native": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-native": "~0.64.4",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"@types/react-native-vector-icons": "^6.4.6",
|
||||
"del-cli": "^3.0.1",
|
||||
"react": "~16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-native-paper": "^4.9.0",
|
||||
"react-native-paper": "^4.9.1",
|
||||
"react-native-safe-area-context": "~3.2.0",
|
||||
"react-native-vector-icons": "^8.1.0",
|
||||
"typescript": "^4.2.3"
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@react-navigation/native": "^6.0.0",
|
||||
|
||||
@@ -34,24 +34,20 @@ function MaterialBottomTabNavigator({
|
||||
screenOptions,
|
||||
...rest
|
||||
}: Props) {
|
||||
const {
|
||||
state,
|
||||
descriptors,
|
||||
navigation,
|
||||
NavigationContent,
|
||||
} = useNavigationBuilder<
|
||||
TabNavigationState<ParamListBase>,
|
||||
TabRouterOptions,
|
||||
TabActionHelpers<ParamListBase>,
|
||||
MaterialBottomTabNavigationOptions,
|
||||
MaterialBottomTabNavigationEventMap
|
||||
>(TabRouter, {
|
||||
initialRouteName,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
});
|
||||
const { state, descriptors, navigation, NavigationContent } =
|
||||
useNavigationBuilder<
|
||||
TabNavigationState<ParamListBase>,
|
||||
TabRouterOptions,
|
||||
TabActionHelpers<ParamListBase>,
|
||||
MaterialBottomTabNavigationOptions,
|
||||
MaterialBottomTabNavigationEventMap
|
||||
>(TabRouter, {
|
||||
initialRouteName,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
});
|
||||
|
||||
return (
|
||||
<NavigationContent>
|
||||
|
||||
@@ -37,8 +37,8 @@ let MaterialCommunityIcons: React.ComponentType<
|
||||
|
||||
try {
|
||||
// Optionally require vector-icons
|
||||
MaterialCommunityIcons = require('react-native-vector-icons/MaterialCommunityIcons')
|
||||
.default;
|
||||
MaterialCommunityIcons =
|
||||
require('react-native-vector-icons/MaterialCommunityIcons').default;
|
||||
} catch (e) {
|
||||
let isErrorLogged = false;
|
||||
|
||||
|
||||
@@ -3,6 +3,22 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.15](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-top-tabs@6.0.0-next.14...@react-navigation/material-top-tabs@6.0.0-next.15) (2021-06-10)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-top-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.14](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-top-tabs@6.0.0-next.13...@react-navigation/material-top-tabs@6.0.0-next.14) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-top-tabs
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.13](https://github.com/react-navigation/react-navigation/compare/@react-navigation/material-top-tabs@6.0.0-next.12...@react-navigation/material-top-tabs@6.0.0-next.13) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/material-top-tabs
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/material-top-tabs",
|
||||
"description": "Integration for the animated tab view component from react-native-tab-view",
|
||||
"version": "6.0.0-next.13",
|
||||
"version": "6.0.0-next.15",
|
||||
"keywords": [
|
||||
"react-native-component",
|
||||
"react-component",
|
||||
@@ -45,17 +45,17 @@
|
||||
"warn-once": "^0.1.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-navigation/native": "^6.0.0-next.12",
|
||||
"@react-navigation/native": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-native": "~0.64.4",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"del-cli": "^3.0.1",
|
||||
"react": "~16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-native-pager-view": "^5.0.12",
|
||||
"react-native-pager-view": "^5.1.10",
|
||||
"react-native-tab-view": "^3.0.1",
|
||||
"typescript": "^4.2.3"
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@react-navigation/native": "^6.0.0",
|
||||
|
||||
@@ -78,24 +78,20 @@ function MaterialTopTabNavigator({
|
||||
);
|
||||
}
|
||||
|
||||
const {
|
||||
state,
|
||||
descriptors,
|
||||
navigation,
|
||||
NavigationContent,
|
||||
} = useNavigationBuilder<
|
||||
TabNavigationState<ParamListBase>,
|
||||
TabRouterOptions,
|
||||
TabActionHelpers<ParamListBase>,
|
||||
MaterialTopTabNavigationOptions,
|
||||
MaterialTopTabNavigationEventMap
|
||||
>(TabRouter, {
|
||||
initialRouteName,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
});
|
||||
const { state, descriptors, navigation, NavigationContent } =
|
||||
useNavigationBuilder<
|
||||
TabNavigationState<ParamListBase>,
|
||||
TabRouterOptions,
|
||||
TabActionHelpers<ParamListBase>,
|
||||
MaterialTopTabNavigationOptions,
|
||||
MaterialTopTabNavigationEventMap
|
||||
>(TabRouter, {
|
||||
initialRouteName,
|
||||
backBehavior,
|
||||
children,
|
||||
screenListeners,
|
||||
screenOptions,
|
||||
});
|
||||
|
||||
return (
|
||||
<NavigationContent>
|
||||
|
||||
@@ -3,6 +3,30 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
# [6.0.0-next.8](https://github.com/react-navigation/react-navigation/compare/@react-navigation/native-stack@6.0.0-next.7...@react-navigation/native-stack@6.0.0-next.8) (2021-06-10)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/native-stack
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.7](https://github.com/react-navigation/react-navigation/compare/@react-navigation/native-stack@6.0.0-next.6...@react-navigation/native-stack@6.0.0-next.7) (2021-06-01)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/native-stack
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.6](https://github.com/react-navigation/react-navigation/compare/@react-navigation/native-stack@6.0.0-next.5...@react-navigation/native-stack@6.0.0-next.6) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/native-stack
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
# [6.0.0-next.5](https://github.com/react-navigation/react-navigation/compare/@react-navigation/native-stack@6.0.0-next.4...@react-navigation/native-stack@6.0.0-next.5) (2021-05-29)
|
||||
|
||||
**Note:** Version bump only for package @react-navigation/native-stack
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@react-navigation/native-stack",
|
||||
"description": "Native stack navigator using react-native-screens",
|
||||
"version": "6.0.0-next.5",
|
||||
"version": "6.0.0-next.8",
|
||||
"keywords": [
|
||||
"react-native-component",
|
||||
"react-component",
|
||||
@@ -41,19 +41,19 @@
|
||||
"clean": "del lib"
|
||||
},
|
||||
"dependencies": {
|
||||
"@react-navigation/elements": "^1.0.0-next.15",
|
||||
"@react-navigation/elements": "^1.0.0-next.18",
|
||||
"warn-once": "^0.1.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@react-navigation/native": "^6.0.0-next.12",
|
||||
"@react-navigation/native": "^6.0.0-next.14",
|
||||
"@testing-library/react-native": "^7.2.0",
|
||||
"@types/react": "^16.9.53",
|
||||
"@types/react-native": "~0.64.4",
|
||||
"@types/react": "^17.0.9",
|
||||
"@types/react-native": "~0.64.9",
|
||||
"react": "~16.13.1",
|
||||
"react-native": "~0.63.4",
|
||||
"react-native-builder-bob": "^0.18.1",
|
||||
"react-native-screens": "^3.0.0",
|
||||
"typescript": "^4.2.3"
|
||||
"react-native-screens": "^3.3.0",
|
||||
"typescript": "^4.3.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@react-navigation/native": "^6.0.0",
|
||||
|
||||
@@ -234,7 +234,7 @@ export type NativeStackNavigationOptions = {
|
||||
*
|
||||
* @platform ios
|
||||
*/
|
||||
headerSearchBar?: SearchBarProps;
|
||||
headerSearchBarOptions?: SearchBarProps;
|
||||
/**
|
||||
* Sets the status bar animation (similar to the `StatusBar` component).
|
||||
* Requires setting `View controller-based status bar appearance -> YES` (or removing the config) in your `Info.plist` file.
|
||||
@@ -243,7 +243,7 @@ export type NativeStackNavigationOptions = {
|
||||
*
|
||||
* @platform ios
|
||||
*/
|
||||
statusBarAnimation?: ScreenStackHeaderConfigProps['statusBarAnimation'];
|
||||
statusBarAnimation?: ScreenProps['statusBarAnimation'];
|
||||
/**
|
||||
* Whether the status bar should be hidden on this screen.
|
||||
* Requires setting `View controller-based status bar appearance -> YES` in your Info.plist file.
|
||||
@@ -261,7 +261,7 @@ export type NativeStackNavigationOptions = {
|
||||
*
|
||||
* @platform ios
|
||||
*/
|
||||
statusBarStyle?: ScreenStackHeaderConfigProps['statusBarStyle'];
|
||||
statusBarStyle?: ScreenProps['statusBarStyle'];
|
||||
/**
|
||||
* Style object for the scene content.
|
||||
*/
|
||||
@@ -319,7 +319,7 @@ export type NativeStackNavigationOptions = {
|
||||
* - "landscape_left": landscape-left orientation is permitted.
|
||||
* - "landscape_right": landscape-right orientation is permitted.
|
||||
*/
|
||||
orientation?: ScreenStackHeaderConfigProps['screenOrientation'];
|
||||
orientation?: ScreenProps['screenOrientation'];
|
||||
};
|
||||
|
||||
export type NativeStackNavigatorProps = DefaultNavigatorOptions<
|
||||
|
||||
33
packages/native-stack/src/views/DebugContainer.native.tsx
Normal file
33
packages/native-stack/src/views/DebugContainer.native.tsx
Normal file
@@ -0,0 +1,33 @@
|
||||
import * as React from 'react';
|
||||
import { Platform, View, ViewProps } from 'react-native';
|
||||
// @ts-ignore Getting private component
|
||||
import AppContainer from 'react-native/Libraries/ReactNative/AppContainer';
|
||||
import type { StackPresentationTypes } from 'react-native-screens';
|
||||
|
||||
type ContainerProps = ViewProps & {
|
||||
stackPresentation: StackPresentationTypes;
|
||||
children: React.ReactNode;
|
||||
};
|
||||
|
||||
let Container = View as unknown as React.ComponentType<ContainerProps>;
|
||||
|
||||
if (process.env.NODE_ENV !== 'production') {
|
||||
const DebugContainer = (props: ContainerProps) => {
|
||||
const { stackPresentation, ...rest } = props;
|
||||
|
||||
if (Platform.OS === 'ios' && stackPresentation !== 'push') {
|
||||
// This is necessary for LogBox
|
||||
return (
|
||||
<AppContainer>
|
||||
<View {...rest} />
|
||||
</AppContainer>
|
||||
);
|
||||
}
|
||||
|
||||
return <View {...rest} />;
|
||||
};
|
||||
|
||||
Container = DebugContainer;
|
||||
}
|
||||
|
||||
export default Container;
|
||||
14
packages/native-stack/src/views/DebugContainer.tsx
Normal file
14
packages/native-stack/src/views/DebugContainer.tsx
Normal file
@@ -0,0 +1,14 @@
|
||||
import * as React from 'react';
|
||||
import { View, ViewProps } from 'react-native';
|
||||
import type { StackPresentationTypes } from 'react-native-screens';
|
||||
|
||||
type ContainerProps = ViewProps & {
|
||||
stackPresentation: StackPresentationTypes;
|
||||
children: React.ReactNode;
|
||||
};
|
||||
|
||||
export default function Container(props: ContainerProps) {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
const { stackPresentation: _, ...rest } = props;
|
||||
return <View {...rest} />;
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user