expo-router 0.0.5 → 0.0.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/babel.js CHANGED
@@ -58,6 +58,21 @@ module.exports = function (api) {
58
58
  return;
59
59
  }
60
60
 
61
+ // Used for log box and stuff
62
+ if (
63
+ t.isIdentifier(parent.node.property, {
64
+ name: "EXPO_PROJECT_ROOT",
65
+ }) &&
66
+ !parent.parentPath.isAssignmentExpression()
67
+ ) {
68
+ parent.replaceWith(
69
+ t.stringLiteral(
70
+ process.env.EXPO_PROJECT_ROOT || state.file.opts.root || ""
71
+ )
72
+ );
73
+ return;
74
+ }
75
+
61
76
  if (
62
77
  !t.isIdentifier(parent.node.property, {
63
78
  name: "EXPO_ROUTER_APP_ROOT",
@@ -1 +1 @@
1
- {"version":3,"file":"ContextNavigator.d.ts","sourceRoot":"","sources":["../src/ContextNavigator.tsx"],"names":[],"mappings":";AAOA,OAAO,EAAE,cAAc,EAAE,MAAM,SAAS,CAAC;AA0DzC,wBAAgB,gBAAgB,CAAC,EAAE,OAAO,EAAE,EAAE;IAAE,OAAO,EAAE,cAAc,CAAA;CAAE,eAsBxE"}
1
+ {"version":3,"file":"ContextNavigator.d.ts","sourceRoot":"","sources":["../src/ContextNavigator.tsx"],"names":[],"mappings":";AAOA,OAAO,EAAE,cAAc,EAAE,MAAM,SAAS,CAAC;AA0DzC,wBAAgB,gBAAgB,CAAC,EAAE,OAAO,EAAE,EAAE;IAAE,OAAO,EAAE,cAAc,CAAA;CAAE,eAmBxE"}
@@ -45,9 +45,9 @@ export function ContextNavigator({ context }) {
45
45
  if (Tutorial) {
46
46
  return React.createElement(Tutorial, null);
47
47
  }
48
- const children = useMemo(() => (React.createElement(Route, { filename: "./" },
49
- React.createElement(ContextNavigationContainer, null,
50
- React.createElement(NativeStack, { screenOptions: { animation: "none", headerShown: false } })))), []);
51
- return (React.createElement(RoutesContextProvider, { context: context }, children));
48
+ return (React.createElement(RoutesContextProvider, { context: context },
49
+ React.createElement(Route, { filename: "./" },
50
+ React.createElement(ContextNavigationContainer, null,
51
+ React.createElement(NativeStack, { screenOptions: { animation: "none", headerShown: false } })))));
52
52
  }
53
53
  //# sourceMappingURL=ContextNavigator.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"ContextNavigator.js","sourceRoot":"","sources":["../src/ContextNavigator.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,OAAO,EAAE,MAAM,OAAO,CAAC;AAEvC,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,0BAA0B,EAAE,MAAM,8BAA8B,CAAC;AAC1E,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AACpD,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAIhC,SAAS,wBAAwB,CAAC,OAAuB;IACrD,4CAA4C;IAC5C,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,CAAC,OAAO,CAAC,CAAC,CAAC;IACtD,OAAO,OAAO,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC;AACrD,CAAC;AAED,SAAS,qBAAqB,CAAC,EAC3B,OAAO,EACP,QAAQ,GAIX;IACG,MAAM,MAAM,GAAG,wBAAwB,CAAC,OAAO,CAAC,CAAC;IACjD,OAAO,CACH,oBAAC,aAAa,CAAC,QAAQ,IAAC,KAAK,EAAE,MAAM,IAAG,QAAQ,CAA0B,CAC7E,CAAC;AACN,CAAC;AAED,SAAS,0BAA0B,CAC/B,SAAc;IAEd,OAAO,CACH,CAAC,CAAC,SAAS;QACX,CAAC,OAAO,SAAS,KAAK,UAAU;YAC5B,SAAS,EAAE,SAAS,EAAE,gBAAgB;YACtC,SAAS,CAAC,QAAQ,KAAK,MAAM,CAAC,GAAG,CAAC,mBAAmB,CAAC,CAAC,CAC9D,CAAC;AACN,CAAC;AAED,yIAAyI;AACzI,SAAS,WAAW,CAAC,OAAuB;IACxC,IAAI,OAAO,CAAC,GAAG,CAAC,QAAQ,KAAK,YAAY,EAAE;QACvC,OAAO,IAAI,CAAC;KACf;IAED,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,CAAC,OAAO,CAAC,CAAC,CAAC;IACtD,MAAM,oBAAoB,GAAG,OAAO,CAAC,GAAG,EAAE;QACtC,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE;YACpB,2FAA2F;YAC3F,MAAM,SAAS,GAAG,OAAO,CAAC,GAAG,CAAC,EAAE,OAAO,CAAC;YACxC,IAAI,0BAA0B,CAAC,SAAS,CAAC,EAAE;gBACvC,OAAO,IAAI,CAAC;aACf;SACJ;QACD,OAAO,KAAK,CAAC;IACjB,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC;IAEX,IAAI,oBAAoB,EAAE;QACtB,OAAO,IAAI,CAAC;KACf;IAED,OAAO,OAAO,CAAC,oBAAoB,CAAC,CAAC,QAAQ,CAAC;AAClD,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,EAAE,OAAO,EAA+B;IACrE,MAAM,QAAQ,GAAG,WAAW,CAAC,OAAO,CAAC,CAAC;IACtC,IAAI,QAAQ,EAAE;QACV,OAAO,oBAAC,QAAQ,OAAG,CAAC;KACvB;IAED,MAAM,QAAQ,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,CAC3B,oBAAC,KAAK,IAAC,QAAQ,EAAC,IAAI;QAChB,oBAAC,0BAA0B;YAEvB,oBAAC,WAAW,IACR,aAAa,EAAE,EAAE,SAAS,EAAE,MAAM,EAAE,WAAW,EAAE,KAAK,EAAE,GAC1D,CACuB,CACzB,CACX,EAAE,EAAE,CAAC,CAAC;IAEP,OAAO,CACH,oBAAC,qBAAqB,IAAC,OAAO,EAAE,OAAO,IAClC,QAAQ,CACW,CAC3B,CAAC;AACN,CAAC","sourcesContent":["import React, { useMemo } from 'react';\n\nimport { RoutesContext } from './context';\nimport { ContextNavigationContainer } from './ContextNavigationContainer';\nimport { getRoutes } from './getRoutes';\nimport { NativeStack } from './layouts/NativeStack';\nimport { Route } from './Route';\nimport { RequireContext } from './types';\n\n\nfunction useContextModuleAsRoutes(context: RequireContext) {\n // TODO: Is this an optimal hook dependency?\n const keys = useMemo(() => context.keys(), [context]);\n return useMemo(() => getRoutes(context), [keys]);\n}\n\nfunction RoutesContextProvider({\n context,\n children,\n}: {\n context: RequireContext;\n children: React.ReactNode;\n}) {\n const routes = useContextModuleAsRoutes(context);\n return (\n <RoutesContext.Provider value={routes}>{children}</RoutesContext.Provider>\n );\n}\n\nfunction isFunctionOrReactComponent(\n Component: any\n): Component is React.ComponentType {\n return (\n !!Component &&\n (typeof Component === \"function\" ||\n Component?.prototype?.isReactComponent ||\n Component.$$typeof === Symbol.for(\"react.forward_ref\"))\n );\n}\n\n/** Returns the Tutorial component if there are no React components exported as default from any files in the provided context module. */\nfunction useTutorial(context: RequireContext) {\n if (process.env.NODE_ENV === \"production\") {\n return null;\n }\n\n const keys = useMemo(() => context.keys(), [context]);\n const hasAnyValidComponent = useMemo(() => {\n for (const key of keys) {\n // NOTE(EvanBacon): This should only ever occur in development as it breaks lazily loading.\n const component = context(key)?.default;\n if (isFunctionOrReactComponent(component)) {\n return true;\n }\n }\n return false;\n }, [keys]);\n\n if (hasAnyValidComponent) {\n return null;\n }\n\n return require(\"./onboard/Tutorial\").Tutorial;\n}\n\nexport function ContextNavigator({ context }: { context: RequireContext }) {\n const Tutorial = useTutorial(context);\n if (Tutorial) {\n return <Tutorial />;\n }\n\n const children = useMemo(() => (\n <Route filename=\"./\">\n <ContextNavigationContainer>\n {/* Using a switch navigator at the root to host all pages. */}\n <NativeStack\n screenOptions={{ animation: \"none\", headerShown: false }}\n />\n </ContextNavigationContainer>\n </Route>\n ), []);\n\n return (\n <RoutesContextProvider context={context}>\n {children}\n </RoutesContextProvider>\n );\n}\n\n"]}
1
+ {"version":3,"file":"ContextNavigator.js","sourceRoot":"","sources":["../src/ContextNavigator.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,OAAO,EAAE,MAAM,OAAO,CAAC;AAEvC,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,0BAA0B,EAAE,MAAM,8BAA8B,CAAC;AAC1E,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EAAE,WAAW,EAAE,MAAM,uBAAuB,CAAC;AACpD,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAC;AAIhC,SAAS,wBAAwB,CAAC,OAAuB;IACrD,4CAA4C;IAC5C,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,CAAC,OAAO,CAAC,CAAC,CAAC;IACtD,OAAO,OAAO,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC;AACrD,CAAC;AAED,SAAS,qBAAqB,CAAC,EAC3B,OAAO,EACP,QAAQ,GAIX;IACG,MAAM,MAAM,GAAG,wBAAwB,CAAC,OAAO,CAAC,CAAC;IACjD,OAAO,CACH,oBAAC,aAAa,CAAC,QAAQ,IAAC,KAAK,EAAE,MAAM,IAAG,QAAQ,CAA0B,CAC7E,CAAC;AACN,CAAC;AAED,SAAS,0BAA0B,CAC/B,SAAc;IAEd,OAAO,CACH,CAAC,CAAC,SAAS;QACX,CAAC,OAAO,SAAS,KAAK,UAAU;YAC5B,SAAS,EAAE,SAAS,EAAE,gBAAgB;YACtC,SAAS,CAAC,QAAQ,KAAK,MAAM,CAAC,GAAG,CAAC,mBAAmB,CAAC,CAAC,CAC9D,CAAC;AACN,CAAC;AAED,yIAAyI;AACzI,SAAS,WAAW,CAAC,OAAuB;IACxC,IAAI,OAAO,CAAC,GAAG,CAAC,QAAQ,KAAK,YAAY,EAAE;QACvC,OAAO,IAAI,CAAC;KACf;IAED,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,CAAC,OAAO,CAAC,CAAC,CAAC;IACtD,MAAM,oBAAoB,GAAG,OAAO,CAAC,GAAG,EAAE;QACtC,KAAK,MAAM,GAAG,IAAI,IAAI,EAAE;YACpB,2FAA2F;YAC3F,MAAM,SAAS,GAAG,OAAO,CAAC,GAAG,CAAC,EAAE,OAAO,CAAC;YACxC,IAAI,0BAA0B,CAAC,SAAS,CAAC,EAAE;gBACvC,OAAO,IAAI,CAAC;aACf;SACJ;QACD,OAAO,KAAK,CAAC;IACjB,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC;IAEX,IAAI,oBAAoB,EAAE;QACtB,OAAO,IAAI,CAAC;KACf;IAED,OAAO,OAAO,CAAC,oBAAoB,CAAC,CAAC,QAAQ,CAAC;AAClD,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,EAAE,OAAO,EAA+B;IACrE,MAAM,QAAQ,GAAG,WAAW,CAAC,OAAO,CAAC,CAAC;IACtC,IAAI,QAAQ,EAAE;QACV,OAAO,oBAAC,QAAQ,OAAG,CAAC;KACvB;IAGD,OAAO,CACH,oBAAC,qBAAqB,IAAC,OAAO,EAAE,OAAO;QACnC,oBAAC,KAAK,IAAC,QAAQ,EAAC,IAAI;YAChB,oBAAC,0BAA0B;gBAEvB,oBAAC,WAAW,IACR,aAAa,EAAE,EAAE,SAAS,EAAE,MAAM,EAAE,WAAW,EAAE,KAAK,EAAE,GAC1D,CACuB,CACzB,CACY,CAC3B,CAAC;AACN,CAAC","sourcesContent":["import React, { useMemo } from 'react';\n\nimport { RoutesContext } from './context';\nimport { ContextNavigationContainer } from './ContextNavigationContainer';\nimport { getRoutes } from './getRoutes';\nimport { NativeStack } from './layouts/NativeStack';\nimport { Route } from './Route';\nimport { RequireContext } from './types';\n\n\nfunction useContextModuleAsRoutes(context: RequireContext) {\n // TODO: Is this an optimal hook dependency?\n const keys = useMemo(() => context.keys(), [context]);\n return useMemo(() => getRoutes(context), [keys]);\n}\n\nfunction RoutesContextProvider({\n context,\n children,\n}: {\n context: RequireContext;\n children: React.ReactNode;\n}) {\n const routes = useContextModuleAsRoutes(context);\n return (\n <RoutesContext.Provider value={routes}>{children}</RoutesContext.Provider>\n );\n}\n\nfunction isFunctionOrReactComponent(\n Component: any\n): Component is React.ComponentType {\n return (\n !!Component &&\n (typeof Component === \"function\" ||\n Component?.prototype?.isReactComponent ||\n Component.$$typeof === Symbol.for(\"react.forward_ref\"))\n );\n}\n\n/** Returns the Tutorial component if there are no React components exported as default from any files in the provided context module. */\nfunction useTutorial(context: RequireContext) {\n if (process.env.NODE_ENV === \"production\") {\n return null;\n }\n\n const keys = useMemo(() => context.keys(), [context]);\n const hasAnyValidComponent = useMemo(() => {\n for (const key of keys) {\n // NOTE(EvanBacon): This should only ever occur in development as it breaks lazily loading.\n const component = context(key)?.default;\n if (isFunctionOrReactComponent(component)) {\n return true;\n }\n }\n return false;\n }, [keys]);\n\n if (hasAnyValidComponent) {\n return null;\n }\n\n return require(\"./onboard/Tutorial\").Tutorial;\n}\n\nexport function ContextNavigator({ context }: { context: RequireContext }) {\n const Tutorial = useTutorial(context);\n if (Tutorial) {\n return <Tutorial />;\n }\n\n\n return (\n <RoutesContextProvider context={context}>\n <Route filename=\"./\">\n <ContextNavigationContainer>\n {/* Using a switch navigator at the root to host all pages. */}\n <NativeStack\n screenOptions={{ animation: \"none\", headerShown: false }}\n />\n </ContextNavigationContainer>\n </Route>\n </RoutesContextProvider>\n );\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"getLinkingConfig.d.ts","sourceRoot":"","sources":["../src/getLinkingConfig.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAWzE,OAAO,EAAE,SAAS,EAAE,MAAM,SAAS,CAAC;AAqBpC,wBAAgB,kCAAkC,CAChD,KAAK,EAAE,SAAS,EAAE,EAClB,OAAO,GAAE,MAAM,EAAO,GACrB,aAAa,CAAC,EAAE,CAAC,CAwBnB;AAED,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,SAAS,EAAE,GAAG,cAAc,CAAC,EAAE,CAAC,CAgBxE"}
1
+ {"version":3,"file":"getLinkingConfig.d.ts","sourceRoot":"","sources":["../src/getLinkingConfig.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,MAAM,0BAA0B,CAAC;AAYzE,OAAO,EAAE,SAAS,EAAE,MAAM,SAAS,CAAC;AAqBpC,wBAAgB,kCAAkC,CAChD,KAAK,EAAE,SAAS,EAAE,EAClB,OAAO,GAAE,MAAM,EAAO,GACrB,aAAa,CAAC,EAAE,CAAC,CAwBnB;AAED,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,SAAS,EAAE,GAAG,cAAc,CAAC,EAAE,CAAC,CA0FxE"}
@@ -1,4 +1,5 @@
1
1
  import * as Linking from "expo-linking";
2
+ import Constants, { ExecutionEnvironment } from "expo-constants";
2
3
  import { getAllWebRedirects } from "./aasa";
3
4
  import getPathFromState from "./fork/getPathFromState";
4
5
  import getStateFromPath from "./fork/getStateFromPath";
@@ -40,10 +41,11 @@ export function treeToReactNavigationLinkingRoutes(nodes, parents = []) {
40
41
  return firstPass;
41
42
  }
42
43
  export function getLinkingConfig(routes) {
44
+ const rootURL = Linking.createURL("/");
43
45
  return {
44
46
  prefixes: [
45
47
  /* your linking prefixes */
46
- Linking.createURL("/"),
48
+ rootURL,
47
49
  // This ensures that we can redirect correctly when the user comes from an associated domain
48
50
  // i.e. iOS Safari banner.
49
51
  ...getAllWebRedirects(),
@@ -51,6 +53,70 @@ export function getLinkingConfig(routes) {
51
53
  config: {
52
54
  screens: treeToReactNavigationLinkingRoutes(routes),
53
55
  },
56
+ // A custom getInitialURL is used on native to ensure the app always starts at
57
+ // the root path if it's launched from something other than a deep link.
58
+ // This helps keep the native functionality working like the web functionality.
59
+ // For example, if you had a root navigator where the first screen was `/settings` and the second was `/index`
60
+ // then `/index` would be used on web and `/settings` would be used on native.
61
+ async getInitialURL() {
62
+ const url = await Promise.race([
63
+ (async () => {
64
+ const url = await Linking.getInitialURL();
65
+ // NOTE(EvanBacon): This could probably be wrapped with the development boundary
66
+ // since Expo Go is mostly just used in development.
67
+ // Expo Go is weird and requires the root path to be `/--/`
68
+ if (url &&
69
+ Constants.executionEnvironment === ExecutionEnvironment.StoreClient) {
70
+ const parsed = Linking.parse(url);
71
+ // If the URL is defined (default in Expo Go dev apps) and the URL has no path:
72
+ // `exp://192.168.87.39:19000/` then use the default `exp://192.168.87.39:19000/--/`
73
+ if (parsed.path === null || ["", "/"].includes(parsed.path)) {
74
+ return rootURL;
75
+ }
76
+ }
77
+ // The path will be nullish in bare apps when the app is launched from the home screen.
78
+ // TODO(EvanBacon): define some policy around notifications.
79
+ return url ?? rootURL;
80
+ })(),
81
+ new Promise((resolve) =>
82
+ // Timeout in 150ms if `getInitialState` doesn't resolve
83
+ // Workaround for https://github.com/facebook/react-native/issues/25675
84
+ setTimeout(() => resolve(rootURL), 150)),
85
+ ]);
86
+ return url;
87
+ },
88
+ subscribe: (listener) => {
89
+ let callback = undefined;
90
+ if (Constants.executionEnvironment === ExecutionEnvironment.StoreClient) {
91
+ // This extra work is only done in the Expo Go app.
92
+ callback = ({ url }) => {
93
+ const parsed = Linking.parse(url);
94
+ // If the URL is defined (default in Expo Go dev apps) and the URL has no path:
95
+ // `exp://192.168.87.39:19000/` then use the default `exp://192.168.87.39:19000/--/`
96
+ if (parsed.path === null || ["", "/"].includes(parsed.path)) {
97
+ listener(rootURL);
98
+ }
99
+ else {
100
+ listener(url);
101
+ }
102
+ };
103
+ }
104
+ else {
105
+ callback = ({ url }) => listener(url);
106
+ }
107
+ const subscription = Linking.addEventListener("url", callback);
108
+ // Storing this in a local variable stops Jest from complaining about import after teardown
109
+ const removeEventListener = Linking.removeEventListener?.bind(Linking);
110
+ return () => {
111
+ // https://github.com/facebook/react-native/commit/6d1aca806cee86ad76de771ed3a1cc62982ebcd7
112
+ if (subscription?.remove) {
113
+ subscription.remove();
114
+ }
115
+ else {
116
+ removeEventListener?.("url", callback);
117
+ }
118
+ };
119
+ },
54
120
  getStateFromPath,
55
121
  getPathFromState,
56
122
  };
@@ -1 +1 @@
1
- {"version":3,"file":"getLinkingConfig.js","sourceRoot":"","sources":["../src/getLinkingConfig.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,OAAO,MAAM,cAAc,CAAC;AAExC,OAAO,EAAE,kBAAkB,EAAE,MAAM,QAAQ,CAAC;AAC5C,OAAO,gBAAgB,MAAM,yBAAyB,CAAC;AACvD,OAAO,gBAAgB,MAAM,yBAAyB,CAAC;AACvD,OAAO,EACL,yBAAyB,EACzB,gBAAgB,EAChB,iBAAiB,GAClB,MAAM,YAAY,CAAC;AAGpB,sBAAsB;AACtB,mBAAmB;AACnB,SAAS,oCAAoC,CAAC,IAAY;IACxD,IAAI,yBAAyB,CAAC,IAAI,CAAC,EAAE;QACnC,OAAO,GAAG,CAAC;KACZ;IACD,MAAM,WAAW,GAAG,gBAAgB,CAAC,IAAI,CAAC,CAAC;IAE3C,IAAI,WAAW,EAAE;QACf,OAAO,IAAI,WAAW,EAAE,CAAC;KAC1B;IAED,IAAI,IAAI,KAAK,OAAO,IAAI,iBAAiB,CAAC,IAAI,CAAC,EAAE;QAC/C,OAAO,EAAE,CAAC;KACX;IAED,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,UAAU,kCAAkC,CAChD,KAAkB,EAClB,UAAoB,EAAE;IAEtB,kEAAkE;IAClE,yFAAyF;IACzF,MAAM,SAAS,GAAG,KAAK;SACpB,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QACZ,MAAM,IAAI,GAAG,oCAAoC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAE9D,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE;YACzB,OAAO,CAAC,IAAI,CAAC,KAAK,EAAE,IAAI,CAAC,CAAC;SAC3B;QAED,MAAM,OAAO,GAAG,kCAAkC,CAAC,IAAI,CAAC,QAAQ,EAAE;YAChE,GAAG,OAAO;YACV,IAAI;SACL,CAAC,CAAC;QAEH,OAAO,CAAC,IAAI,CAAC,KAAK,EAAE,EAAE,IAAI,EAAE,OAAO,EAAE,CAAU,CAAC;IAClD,CAAC,CAAC;SACD,MAAM,CAAoB,CAAC,GAAG,EAAE,CAAC,KAAK,EAAE,OAAO,CAAC,EAAE,EAAE;QACnD,GAAG,CAAC,KAAK,CAAC,GAAG,OAAO,CAAC;QACrB,OAAO,GAAG,CAAC;IACb,CAAC,EAAE,EAAE,CAAC,CAAC;IAET,OAAO,SAAS,CAAC;AACnB,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,MAAmB;IAClD,OAAO;QACL,QAAQ,EAAE;YACR,2BAA2B;YAC3B,OAAO,CAAC,SAAS,CAAC,GAAG,CAAC;YAEtB,4FAA4F;YAC5F,0BAA0B;YAC1B,GAAG,kBAAkB,EAAE;SACxB;QACD,MAAM,EAAE;YACN,OAAO,EAAE,kCAAkC,CAAC,MAAM,CAAC;SACpD;QACD,gBAAgB;QAChB,gBAAgB;KACjB,CAAC;AACJ,CAAC","sourcesContent":["import { LinkingOptions, PathConfigMap } from \"@react-navigation/native\";\nimport * as Linking from \"expo-linking\";\n\nimport { getAllWebRedirects } from \"./aasa\";\nimport getPathFromState from \"./fork/getPathFromState\";\nimport getStateFromPath from \"./fork/getStateFromPath\";\nimport {\n matchDeepDynamicRouteName,\n matchDynamicName,\n matchFragmentName,\n} from \"./matchers\";\nimport { RouteNode } from \"./Route\";\n\n// `[page]` -> `:page`\n// `page` -> `page`\nfunction convertDynamicRouteToReactNavigation(name: string) {\n if (matchDeepDynamicRouteName(name)) {\n return \"*\";\n }\n const dynamicName = matchDynamicName(name);\n\n if (dynamicName) {\n return `:${dynamicName}`;\n }\n\n if (name === \"index\" || matchFragmentName(name)) {\n return \"\";\n }\n\n return name;\n}\n\nexport function treeToReactNavigationLinkingRoutes(\n nodes: RouteNode[],\n parents: string[] = []\n): PathConfigMap<{}> {\n // TODO: Intercept errors, strip invalid routes, and warn instead.\n // Our warnings can be more helpful than upstream since we know the associated file name.\n const firstPass = nodes\n .map((node) => {\n const path = convertDynamicRouteToReactNavigation(node.route);\n\n if (!node.children.length) {\n return [node.route, path];\n }\n\n const screens = treeToReactNavigationLinkingRoutes(node.children, [\n ...parents,\n path,\n ]);\n\n return [node.route, { path, screens }] as const;\n })\n .reduce<PathConfigMap<{}>>((acc, [route, current]) => {\n acc[route] = current;\n return acc;\n }, {});\n\n return firstPass;\n}\n\nexport function getLinkingConfig(routes: RouteNode[]): LinkingOptions<{}> {\n return {\n prefixes: [\n /* your linking prefixes */\n Linking.createURL(\"/\"),\n\n // This ensures that we can redirect correctly when the user comes from an associated domain\n // i.e. iOS Safari banner.\n ...getAllWebRedirects(),\n ],\n config: {\n screens: treeToReactNavigationLinkingRoutes(routes),\n },\n getStateFromPath,\n getPathFromState,\n };\n}\n"]}
1
+ {"version":3,"file":"getLinkingConfig.js","sourceRoot":"","sources":["../src/getLinkingConfig.ts"],"names":[],"mappings":"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","sourcesContent":["import { LinkingOptions, PathConfigMap } from \"@react-navigation/native\";\nimport * as Linking from \"expo-linking\";\n\nimport Constants, { ExecutionEnvironment } from \"expo-constants\";\nimport { getAllWebRedirects } from \"./aasa\";\nimport getPathFromState from \"./fork/getPathFromState\";\nimport getStateFromPath from \"./fork/getStateFromPath\";\nimport {\n matchDeepDynamicRouteName,\n matchDynamicName,\n matchFragmentName,\n} from \"./matchers\";\nimport { RouteNode } from \"./Route\";\n\n// `[page]` -> `:page`\n// `page` -> `page`\nfunction convertDynamicRouteToReactNavigation(name: string) {\n if (matchDeepDynamicRouteName(name)) {\n return \"*\";\n }\n const dynamicName = matchDynamicName(name);\n\n if (dynamicName) {\n return `:${dynamicName}`;\n }\n\n if (name === \"index\" || matchFragmentName(name)) {\n return \"\";\n }\n\n return name;\n}\n\nexport function treeToReactNavigationLinkingRoutes(\n nodes: RouteNode[],\n parents: string[] = []\n): PathConfigMap<{}> {\n // TODO: Intercept errors, strip invalid routes, and warn instead.\n // Our warnings can be more helpful than upstream since we know the associated file name.\n const firstPass = nodes\n .map((node) => {\n const path = convertDynamicRouteToReactNavigation(node.route);\n\n if (!node.children.length) {\n return [node.route, path];\n }\n\n const screens = treeToReactNavigationLinkingRoutes(node.children, [\n ...parents,\n path,\n ]);\n\n return [node.route, { path, screens }] as const;\n })\n .reduce<PathConfigMap<{}>>((acc, [route, current]) => {\n acc[route] = current;\n return acc;\n }, {});\n\n return firstPass;\n}\n\nexport function getLinkingConfig(routes: RouteNode[]): LinkingOptions<{}> {\n const rootURL = Linking.createURL(\"/\");\n\n return {\n prefixes: [\n /* your linking prefixes */\n rootURL,\n\n // This ensures that we can redirect correctly when the user comes from an associated domain\n // i.e. iOS Safari banner.\n ...getAllWebRedirects(),\n ],\n config: {\n screens: treeToReactNavigationLinkingRoutes(routes),\n },\n // A custom getInitialURL is used on native to ensure the app always starts at\n // the root path if it's launched from something other than a deep link.\n // This helps keep the native functionality working like the web functionality.\n // For example, if you had a root navigator where the first screen was `/settings` and the second was `/index`\n // then `/index` would be used on web and `/settings` would be used on native.\n async getInitialURL(): Promise<string> {\n const url = await Promise.race<string>([\n (async () => {\n const url = await Linking.getInitialURL();\n\n // NOTE(EvanBacon): This could probably be wrapped with the development boundary\n // since Expo Go is mostly just used in development.\n\n // Expo Go is weird and requires the root path to be `/--/`\n if (\n url &&\n Constants.executionEnvironment === ExecutionEnvironment.StoreClient\n ) {\n const parsed = Linking.parse(url);\n // If the URL is defined (default in Expo Go dev apps) and the URL has no path:\n // `exp://192.168.87.39:19000/` then use the default `exp://192.168.87.39:19000/--/`\n if (parsed.path === null || [\"\", \"/\"].includes(parsed.path)) {\n return rootURL;\n }\n }\n // The path will be nullish in bare apps when the app is launched from the home screen.\n // TODO(EvanBacon): define some policy around notifications.\n return url ?? rootURL;\n })(),\n new Promise<string>((resolve) =>\n // Timeout in 150ms if `getInitialState` doesn't resolve\n // Workaround for https://github.com/facebook/react-native/issues/25675\n setTimeout(() => resolve(rootURL), 150)\n ),\n ]);\n return url;\n },\n subscribe: (listener) => {\n let callback: (({ url }: { url: string }) => void) | undefined =\n undefined;\n\n if (Constants.executionEnvironment === ExecutionEnvironment.StoreClient) {\n // This extra work is only done in the Expo Go app.\n callback = ({ url }: { url: string }) => {\n const parsed = Linking.parse(url);\n // If the URL is defined (default in Expo Go dev apps) and the URL has no path:\n // `exp://192.168.87.39:19000/` then use the default `exp://192.168.87.39:19000/--/`\n if (parsed.path === null || [\"\", \"/\"].includes(parsed.path)) {\n listener(rootURL);\n } else {\n listener(url);\n }\n };\n } else {\n callback = ({ url }: { url: string }) => listener(url);\n }\n const subscription = Linking.addEventListener(\"url\", callback) as\n | { remove(): void }\n | undefined;\n\n // Storing this in a local variable stops Jest from complaining about import after teardown\n const removeEventListener = Linking.removeEventListener?.bind(Linking);\n\n return () => {\n // https://github.com/facebook/react-native/commit/6d1aca806cee86ad76de771ed3a1cc62982ebcd7\n if (subscription?.remove) {\n subscription.remove();\n } else {\n removeEventListener?.(\"url\", callback);\n }\n };\n },\n getStateFromPath,\n getPathFromState,\n };\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"Tutorial.d.ts","sourceRoot":"","sources":["../../src/onboard/Tutorial.tsx"],"names":[],"mappings":";AAmCA,wBAAgB,QAAQ,gBAoDvB"}
1
+ {"version":3,"file":"Tutorial.d.ts","sourceRoot":"","sources":["../../src/onboard/Tutorial.tsx"],"names":[],"mappings":";AAmCA,wBAAgB,QAAQ,gBAsDvB"}
@@ -17,16 +17,18 @@ function Header() {
17
17
  const canAutoTouchFile = process.env.EXPO_ROUTER_APP_ROOT != null;
18
18
  export function Tutorial() {
19
19
  React.useEffect(() => {
20
- // Reset the route on web so the initial route isn't a 404 after
21
- // the user has created the entry file.
22
- // This is useful for cases where you are testing the tutorial.
23
- // To test: touch the new file, then navigate to a missing route `/foobar`, then delete the app folder.
24
- // you should see the tutorial again and be able to create the entry file once more.
25
- if (typeof location !== "undefined" && location.pathname !== "/") {
26
- location.replace("/");
27
- }
28
- if (typeof window !== "undefined") {
29
- window.document.title = "npx expo start";
20
+ if (Platform.OS === "web") {
21
+ // Reset the route on web so the initial route isn't a 404 after
22
+ // the user has created the entry file.
23
+ // This is useful for cases where you are testing the tutorial.
24
+ // To test: touch the new file, then navigate to a missing route `/foobar`, then delete the app folder.
25
+ // you should see the tutorial again and be able to create the entry file once more.
26
+ if (typeof location !== "undefined" && location.pathname !== "/") {
27
+ location.replace("/");
28
+ }
29
+ if (typeof window !== "undefined" && typeof window.document !== "undefined") {
30
+ window.document.title = "npx expo start";
31
+ }
30
32
  }
31
33
  }, []);
32
34
  return (React.createElement(View, { style: {
@@ -1 +1 @@
1
- {"version":3,"file":"Tutorial.js","sourceRoot":"","sources":["../../src/onboard/Tutorial.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from \"react\";\nimport { SafeAreaView, StatusBar, Platform } from \"react-native\";\nimport { View, Text, Pressable, StyleSheet } from \"@bacons/react-views\";\nimport { createEntryFileAsync } from \"./createEntryFile\";\n\n// TODO: Use openLinkFromBrowser thing\nfunction Header() {\n return (\n <Pressable>\n {({ hovered }) => (\n <Text\n accessibilityRole=\"heading\"\n accessibilityLevel={1}\n style={[styles.title, Platform.OS !== \"web\" && { textAlign: \"left\" }]}\n >\n Welcome to{\" \"}\n <Text\n href=\"https://github.com/expo/expo-router/\"\n style={[\n hovered && {\n textDecorationColor: \"white\",\n textDecorationLine: \"underline\",\n },\n ]}\n >\n Expo\n </Text>\n </Text>\n )}\n </Pressable>\n );\n}\n\nconst canAutoTouchFile = process.env.EXPO_ROUTER_APP_ROOT != null;\n\nexport function Tutorial() {\n React.useEffect(() => {\n // Reset the route on web so the initial route isn't a 404 after\n // the user has created the entry file.\n // This is useful for cases where you are testing the tutorial.\n // To test: touch the new file, then navigate to a missing route `/foobar`, then delete the app folder.\n // you should see the tutorial again and be able to create the entry file once more.\n if (typeof location !== \"undefined\" && location.pathname !== \"/\") {\n location.replace(\"/\");\n }\n if (typeof window !== \"undefined\") {\n window.document.title = \"npx expo start\";\n }\n }, []);\n\n return (\n <View\n style={{\n backgroundColor: \"black\",\n flex: 1,\n backgroundImage:\n \"radial-gradient(circle at 1px 1px, rgba(255,255,255,0.15) 1px, transparent 0)\",\n backgroundPosition: \"-3px -3px\",\n backgroundSize: \"40px 40px\",\n }}\n >\n <StatusBar barStyle=\"light-content\" />\n\n <SafeAreaView\n style={{\n flex: 1,\n maxWidth: 960,\n marginHorizontal: \"auto\",\n alignItems: \"stretch\",\n }}\n >\n <View accessibilityRole=\"main\" style={styles.container}>\n <Header />\n <Text\n accessibilityRole=\"heading\"\n accessibilityLevel={2}\n style={styles.subtitle}\n >\n Get started by creating a file{\"\\n\"}in the{\" \"}\n <Text style={{ fontWeight: \"bold\" }}>app</Text> directory{\"\\n\"}that\n exports a React component.\n </Text>\n {canAutoTouchFile && <Button />}\n </View>\n </SafeAreaView>\n </View>\n );\n}\n\nfunction Button() {\n return (\n <Pressable\n onPress={() => {\n createEntryFileAsync();\n }}\n style={{\n ...Platform.select({\n native: {\n position: \"absolute\",\n bottom: 8,\n left: 24,\n right: 24,\n },\n }),\n }}\n >\n {({ pressed, hovered }) => (\n <View\n style={[\n {\n transitionDuration: \"200ms\",\n backgroundColor: \"transparent\",\n borderColor: \"white\",\n borderWidth: 2,\n paddingVertical: 12,\n paddingHorizontal: 24,\n },\n hovered && {\n backgroundColor: \"white\",\n },\n pressed && {\n backgroundColor: \"rgba(255,255,255,0.7)\",\n },\n ]}\n >\n <Text\n selectable={false}\n style={[\n {\n fontSize: 18,\n transitionDuration: \"200ms\",\n fontWeight: \"bold\",\n color: \"white\",\n },\n styles.code,\n hovered && { color: \"black\" },\n ]}\n >\n <Text style={{ color: \"#BCC3CD\" }}>$</Text> touch app/index.js\n </Text>\n </View>\n )}\n </Pressable>\n );\n}\n\nconst styles = StyleSheet.create({\n container: {\n flex: 1,\n padding: 24,\n alignItems: \"start\",\n justifyContent: \"center\",\n },\n title: {\n color: \"white\",\n fontSize: 64,\n paddingBottom: 24,\n fontWeight: \"bold\",\n },\n buttonText: {\n color: \"black\",\n },\n code: {\n fontFamily: Platform.select({\n default: \"Courier\",\n ios: \"Courier New\",\n android: \"monospace\",\n }),\n },\n subtitle: {\n color: \"#BCC3CD\",\n fontSize: 36,\n fontWeight: \"light\",\n paddingBottom: 36,\n maxWidth: 960,\n },\n});\n"]}
1
+ {"version":3,"file":"Tutorial.js","sourceRoot":"","sources":["../../src/onboard/Tutorial.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from \"react\";\nimport { SafeAreaView, StatusBar, Platform } from \"react-native\";\nimport { View, Text, Pressable, StyleSheet } from \"@bacons/react-views\";\nimport { createEntryFileAsync } from \"./createEntryFile\";\n\n// TODO: Use openLinkFromBrowser thing\nfunction Header() {\n return (\n <Pressable>\n {({ hovered }) => (\n <Text\n accessibilityRole=\"heading\"\n accessibilityLevel={1}\n style={[styles.title, Platform.OS !== \"web\" && { textAlign: \"left\" }]}\n >\n Welcome to{\" \"}\n <Text\n href=\"https://github.com/expo/expo-router/\"\n style={[\n hovered && {\n textDecorationColor: \"white\",\n textDecorationLine: \"underline\",\n },\n ]}\n >\n Expo\n </Text>\n </Text>\n )}\n </Pressable>\n );\n}\n\nconst canAutoTouchFile = process.env.EXPO_ROUTER_APP_ROOT != null;\n\nexport function Tutorial() {\n React.useEffect(() => {\n if (Platform.OS === \"web\") {\n // Reset the route on web so the initial route isn't a 404 after\n // the user has created the entry file.\n // This is useful for cases where you are testing the tutorial.\n // To test: touch the new file, then navigate to a missing route `/foobar`, then delete the app folder.\n // you should see the tutorial again and be able to create the entry file once more.\n if (typeof location !== \"undefined\" && location.pathname !== \"/\") {\n location.replace(\"/\");\n }\n if (typeof window !== \"undefined\" && typeof window.document !== \"undefined\") {\n window.document.title = \"npx expo start\";\n }\n }\n }, []);\n\n return (\n <View\n style={{\n backgroundColor: \"black\",\n flex: 1,\n backgroundImage:\n \"radial-gradient(circle at 1px 1px, rgba(255,255,255,0.15) 1px, transparent 0)\",\n backgroundPosition: \"-3px -3px\",\n backgroundSize: \"40px 40px\",\n }}\n >\n <StatusBar barStyle=\"light-content\" />\n\n <SafeAreaView\n style={{\n flex: 1,\n maxWidth: 960,\n marginHorizontal: \"auto\",\n alignItems: \"stretch\",\n }}\n >\n <View accessibilityRole=\"main\" style={styles.container}>\n <Header />\n <Text\n accessibilityRole=\"heading\"\n accessibilityLevel={2}\n style={styles.subtitle}\n >\n Get started by creating a file{\"\\n\"}in the{\" \"}\n <Text style={{ fontWeight: \"bold\" }}>app</Text> directory{\"\\n\"}that\n exports a React component.\n </Text>\n {canAutoTouchFile && <Button />}\n </View>\n </SafeAreaView>\n </View>\n );\n}\n\nfunction Button() {\n return (\n <Pressable\n onPress={() => {\n createEntryFileAsync();\n }}\n style={{\n ...Platform.select({\n native: {\n position: \"absolute\",\n bottom: 8,\n left: 24,\n right: 24,\n },\n }),\n }}\n >\n {({ pressed, hovered }) => (\n <View\n style={[\n {\n transitionDuration: \"200ms\",\n backgroundColor: \"transparent\",\n borderColor: \"white\",\n borderWidth: 2,\n paddingVertical: 12,\n paddingHorizontal: 24,\n },\n hovered && {\n backgroundColor: \"white\",\n },\n pressed && {\n backgroundColor: \"rgba(255,255,255,0.7)\",\n },\n ]}\n >\n <Text\n selectable={false}\n style={[\n {\n fontSize: 18,\n transitionDuration: \"200ms\",\n fontWeight: \"bold\",\n color: \"white\",\n },\n styles.code,\n hovered && { color: \"black\" },\n ]}\n >\n <Text style={{ color: \"#BCC3CD\" }}>$</Text> touch app/index.js\n </Text>\n </View>\n )}\n </Pressable>\n );\n}\n\nconst styles = StyleSheet.create({\n container: {\n flex: 1,\n padding: 24,\n alignItems: \"start\",\n justifyContent: \"center\",\n },\n title: {\n color: \"white\",\n fontSize: 64,\n paddingBottom: 24,\n fontWeight: \"bold\",\n },\n buttonText: {\n color: \"black\",\n },\n code: {\n fontFamily: Platform.select({\n default: \"Courier\",\n ios: \"Courier New\",\n android: \"monospace\",\n }),\n },\n subtitle: {\n color: \"#BCC3CD\",\n fontSize: 36,\n fontWeight: \"light\",\n paddingBottom: 36,\n maxWidth: 960,\n },\n});\n"]}
@@ -11,28 +11,28 @@ export function useScreens() {
11
11
  }
12
12
  function getSortedChildren(children, order) {
13
13
  if (!order?.length) {
14
- return Object.values(children).sort(sortRoutes).map((route) => ({ route, props: {} }));
14
+ return children.sort(sortRoutes).map((route) => ({ route, props: {} }));
15
15
  }
16
- const entries = Object.entries(children);
16
+ const entries = [...children];
17
17
  const ordered = order.map(({ name, initialParams, options }) => {
18
- if (entries.length === 0) {
18
+ if (!entries.length) {
19
19
  console.warn(`[Layout children]: Too many screens defined. Route "${name}" is extraneous.`);
20
20
  return null;
21
21
  }
22
- const matchIndex = entries.findIndex((child) => child[0] === name);
22
+ const matchIndex = entries.findIndex((child) => child.route === name);
23
23
  if (matchIndex === -1) {
24
- console.warn(`[Layout children]: No route named "${name}" exists in nested children:`, Object.keys(children));
24
+ console.warn(`[Layout children]: No route named "${name}" exists in nested children:`, children.map(({ route }) => route));
25
25
  return null;
26
26
  }
27
27
  else {
28
28
  // Get match and remove from entries
29
- const [, match] = entries[matchIndex];
29
+ const match = entries[matchIndex];
30
30
  entries.splice(matchIndex, 1);
31
31
  return { route: match, props: { initialParams, options } };
32
32
  }
33
33
  }).filter(Boolean);
34
34
  // Add any remaining children
35
- ordered.push(...entries.map(([, child]) => child).sort(sortRoutes).map((route) => ({ route, props: {} })));
35
+ ordered.push(...entries.sort(sortRoutes).map((route) => ({ route, props: {} })));
36
36
  return ordered;
37
37
  }
38
38
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"useScreens.js","sourceRoot":"","sources":["../src/useScreens.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\n\nimport { Screen } from './primitives';\nimport { Route, RouteNode, sortRoutes, useRoutes } from './Route';\nimport { Try } from './views/Try';\n\n/**\n * @returns React Navigation screens for the route.\n */\nexport function useScreens(): React.ReactNode[] {\n const children = useRoutes();\n return React.useMemo(() => children.map((value) => routeToScreen(value)), [children]);\n}\n\nexport type ScreenProps<TOptions extends Record<string, any> = Record<string, any>> = {\n /** Name is required when used inside a Layout component. */\n name?: string,\n initialParams?: { [key: string]: any };\n options?: TOptions;\n}\n\nfunction getSortedChildren(children: RouteNode[], order?: ScreenProps[]): { route: RouteNode, props: any }[] {\n if (!order?.length) {\n return Object.values(children).sort(sortRoutes).map((route) => ({ route, props: {} }));\n }\n const entries = Object.entries(children);\n\n const ordered = order.map(({ name, initialParams, options }) => {\n if (entries.length === 0) {\n console.warn(`[Layout children]: Too many screens defined. Route \"${name}\" is extraneous.`);\n return null;\n }\n const matchIndex = entries.findIndex((child) => child[0] === name)\n if (matchIndex === -1) {\n console.warn(`[Layout children]: No route named \"${name}\" exists in nested children:`, Object.keys(children));\n return null;\n } else {\n // Get match and remove from entries\n const [, match] = entries[matchIndex];\n entries.splice(matchIndex, 1);\n\n return { route: match, props: { initialParams, options } }\n }\n }).filter(Boolean) as {\n route: RouteNode;\n props: Partial<ScreenProps>;\n }[]\n\n // Add any remaining children\n ordered.push(...entries.map(([, child]) => child).sort(sortRoutes).map((route) => ({ route, props: {} })));\n\n return ordered;\n}\n\n\n/** \n * @returns React Navigation screens sorted by the `route` property.\n */\nexport function useSortedScreens(order: ScreenProps[]): React.ReactNode[] {\n const children = useRoutes();\n const sorted = getSortedChildren(children, order);\n return React.useMemo(() =>\n sorted.map((value) => routeToScreen(value.route, value.props)), [sorted]);\n}\n\n\n// TODO: Maybe there's a more React-y way to do this?\n// Without this store, the process enters a recursive loop.\nconst qualifiedStore = new WeakMap<RouteNode, React.ComponentType<any>>();\n\n/** Wrap the component with various enhancements and add access to child routes. */\nfunction getQualifiedRouteComponent(value: RouteNode) {\n if (qualifiedStore.has(value)) {\n return qualifiedStore.get(value);\n }\n\n const Component = value.getComponent();\n\n const { ErrorBoundary } = value.getExtras();\n\n const QualifiedRoute = React.forwardRef(\n (props: { route: any; navigation: any }, ref: any) => {\n // Surface dynamic name as props to the view\n const children = React.createElement(Component, {\n ...props,\n ref,\n });\n\n const errorBoundary = ErrorBoundary ? (\n <Try catch={ErrorBoundary}>{children}</Try>\n ) : (\n children\n );\n\n return (\n <Route filename={value.contextKey}>\n {errorBoundary}\n </Route>\n );\n }\n );\n\n QualifiedRoute.displayName = `Route(${Component.displayName || Component.name || value.route})`;\n qualifiedStore.set(value, QualifiedRoute);\n return QualifiedRoute;\n}\n\nfunction routeToScreen(route: RouteNode, { options, ...props }: Partial<ScreenProps> = {}) {\n const staticOptions = route.getExtras()?.getNavOptions;\n return (\n // @ts-expect-error: fixme\n <Screen\n {...props}\n name={route.route}\n key={route.route}\n options={options ? (args) => {\n const staticResult = typeof staticOptions === 'function' ? staticOptions(args) : staticOptions;\n const dynamicResult = typeof options === 'function' ? options?.(args) : options;\n return {\n ...staticResult,\n ...dynamicResult,\n };\n } : staticOptions}\n component={getQualifiedRouteComponent(route)}\n />\n );\n}\n"]}
1
+ {"version":3,"file":"useScreens.js","sourceRoot":"","sources":["../src/useScreens.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\n\nimport { Screen } from './primitives';\nimport { Route, RouteNode, sortRoutes, useRoutes } from './Route';\nimport { Try } from './views/Try';\n\n/**\n * @returns React Navigation screens for the route.\n */\nexport function useScreens(): React.ReactNode[] {\n const children = useRoutes();\n return React.useMemo(() => children.map((value) => routeToScreen(value)), [children]);\n}\n\nexport type ScreenProps<TOptions extends Record<string, any> = Record<string, any>> = {\n /** Name is required when used inside a Layout component. */\n name?: string,\n initialParams?: { [key: string]: any };\n options?: TOptions;\n}\n\nfunction getSortedChildren(children: RouteNode[], order?: ScreenProps[]): { route: RouteNode, props: any }[] {\n if (!order?.length) {\n return children.sort(sortRoutes).map((route) => ({ route, props: {} }));\n }\n const entries = [...children];\n\n const ordered = order.map(({ name, initialParams, options }) => {\n if (!entries.length) {\n console.warn(`[Layout children]: Too many screens defined. Route \"${name}\" is extraneous.`);\n return null;\n }\n const matchIndex = entries.findIndex((child) => child.route === name)\n if (matchIndex === -1) {\n console.warn(`[Layout children]: No route named \"${name}\" exists in nested children:`, children.map(({ route }) => route));\n return null;\n } else {\n // Get match and remove from entries\n const match = entries[matchIndex];\n entries.splice(matchIndex, 1);\n\n return { route: match, props: { initialParams, options } }\n }\n }).filter(Boolean) as {\n route: RouteNode;\n props: Partial<ScreenProps>;\n }[]\n\n // Add any remaining children\n ordered.push(...entries.sort(sortRoutes).map((route) => ({ route, props: {} })));\n\n return ordered;\n}\n\n\n/** \n * @returns React Navigation screens sorted by the `route` property.\n */\nexport function useSortedScreens(order: ScreenProps[]): React.ReactNode[] {\n const children = useRoutes();\n const sorted = getSortedChildren(children, order);\n return React.useMemo(() =>\n sorted.map((value) => routeToScreen(value.route, value.props)), [sorted]);\n}\n\n\n// TODO: Maybe there's a more React-y way to do this?\n// Without this store, the process enters a recursive loop.\nconst qualifiedStore = new WeakMap<RouteNode, React.ComponentType<any>>();\n\n/** Wrap the component with various enhancements and add access to child routes. */\nfunction getQualifiedRouteComponent(value: RouteNode) {\n if (qualifiedStore.has(value)) {\n return qualifiedStore.get(value);\n }\n\n const Component = value.getComponent();\n\n const { ErrorBoundary } = value.getExtras();\n\n const QualifiedRoute = React.forwardRef(\n (props: { route: any; navigation: any }, ref: any) => {\n // Surface dynamic name as props to the view\n const children = React.createElement(Component, {\n ...props,\n ref,\n });\n\n const errorBoundary = ErrorBoundary ? (\n <Try catch={ErrorBoundary}>{children}</Try>\n ) : (\n children\n );\n\n return (\n <Route filename={value.contextKey}>\n {errorBoundary}\n </Route>\n );\n }\n );\n\n QualifiedRoute.displayName = `Route(${Component.displayName || Component.name || value.route})`;\n qualifiedStore.set(value, QualifiedRoute);\n return QualifiedRoute;\n}\n\nfunction routeToScreen(route: RouteNode, { options, ...props }: Partial<ScreenProps> = {}) {\n const staticOptions = route.getExtras()?.getNavOptions;\n return (\n // @ts-expect-error: fixme\n <Screen\n {...props}\n name={route.route}\n key={route.route}\n options={options ? (args) => {\n const staticResult = typeof staticOptions === 'function' ? staticOptions(args) : staticOptions;\n const dynamicResult = typeof options === 'function' ? options?.(args) : options;\n return {\n ...staticResult,\n ...dynamicResult,\n };\n } : staticOptions}\n component={getQualifiedRouteComponent(route)}\n />\n );\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"Directory.d.ts","sourceRoot":"","sources":["../../src/views/Directory.tsx"],"names":[],"mappings":";AACA,OAAO,EAAE,4BAA4B,EAAE,MAAM,gCAAgC,CAAC;AAwE9E,wBAAgB,aAAa,IAAI,4BAA4B,CAqB5D;AAED,wBAAgB,SAAS,gBAmCxB"}
1
+ {"version":3,"file":"Directory.d.ts","sourceRoot":"","sources":["../../src/views/Directory.tsx"],"names":[],"mappings":";AAEA,OAAO,EAAE,4BAA4B,EAAE,MAAM,gCAAgC,CAAC;AAwE9E,wBAAgB,aAAa,IAAI,4BAA4B,CAqB5D;AAED,wBAAgB,SAAS,gBAmCxB"}
@@ -1,9 +1,10 @@
1
1
  import { Image, Pressable, StyleSheet, Text, View } from "@bacons/react-views";
2
+ import { useNavigation } from "@react-navigation/native";
2
3
  import React from "react";
3
- import { ScrollView, StatusBar, useWindowDimensions } from "react-native";
4
+ import { ScrollView, Platform, StatusBar, useWindowDimensions } from "react-native";
4
5
  import { useSafeAreaInsets } from "react-native-safe-area-context";
5
6
  import { useRoutesContext } from "../context";
6
- import { matchFragmentName } from "../matchers";
7
+ import { matchDeepDynamicRouteName, matchFragmentName } from "../matchers";
7
8
  import { Link } from "./Link";
8
9
  const INDENT = 18;
9
10
  function useSortedRoutes() {
@@ -101,10 +102,15 @@ export function Directory() {
101
102
  }
102
103
  function FileItem({ route, level = 0, parents = [], }) {
103
104
  const disabled = route.children.length > 0;
105
+ const navigation = useNavigation();
104
106
  const href = React.useMemo(() => {
105
107
  return ("/" +
106
108
  [...parents, route.route]
107
109
  .map((v) => {
110
+ // add an extra layer of entropy to the url for deep dynamic routes
111
+ if (matchDeepDynamicRouteName(v)) {
112
+ return v + '/' + Date.now();
113
+ }
108
114
  // groups and index must be erased
109
115
  return !!matchFragmentName(v) || v === "index" ? "" : v;
110
116
  })
@@ -112,7 +118,14 @@ function FileItem({ route, level = 0, parents = [], }) {
112
118
  .join("/"));
113
119
  }, [parents, route.route]);
114
120
  return (React.createElement(React.Fragment, null,
115
- React.createElement(Link, { href: href, disabled: disabled, asChild: true },
121
+ React.createElement(Link, { href: href, onPress: () => {
122
+ if (Platform.OS !== 'web') {
123
+ // Ensure the modal pops
124
+ navigation.goBack();
125
+ }
126
+ },
127
+ // @ts-expect-error: disabled not on type
128
+ disabled: disabled, asChild: true },
116
129
  React.createElement(Pressable, null, ({ pressed, hovered }) => (React.createElement(View, { style: [
117
130
  styles.itemPressable,
118
131
  {
@@ -1 +1 @@
1
- {"version":3,"file":"Directory.js","sourceRoot":"","sources":["../../src/views/Directory.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Image, Pressable, StyleSheet, Text, View } from \"@bacons/react-views\";\nimport { NativeStackNavigationOptions } from \"@react-navigation/native-stack\";\nimport React from \"react\";\nimport { ScrollView, StatusBar, useWindowDimensions } from \"react-native\";\nimport { useSafeAreaInsets } from \"react-native-safe-area-context\";\n\nimport { useRoutesContext } from \"../context\";\nimport { matchFragmentName } from \"../matchers\";\nimport { RouteNode } from \"../Route\";\nimport { Link } from \"./Link\";\n\nconst INDENT = 18;\n\nfunction useSortedRoutes() {\n const ctx = useRoutesContext();\n\n const routes = React.useMemo(\n () =>\n ctx\n .filter((route) => !route.internal)\n .sort((a, b) => {\n // Emulate vscode's sorting\n if (a.route < b.route) {\n return -1;\n }\n if (a.route > b.route) {\n return 1;\n }\n return 0;\n }),\n [ctx]\n );\n return routes;\n}\n\nconst styles = StyleSheet.create({\n container: {\n backgroundColor: \"black\",\n flex: 1,\n alignItems: \"stretch\",\n },\n main: {\n marginHorizontal: \"auto\",\n flex: 1,\n\n alignItems: \"stretch\",\n },\n scroll: {\n padding: 12,\n flex: 1,\n // paddingTop: top + 12,\n alignItems: \"stretch\",\n },\n itemContainer: {\n borderWidth: 1,\n borderColor: \"#323232\",\n borderRadius: 19,\n marginBottom: 12,\n overflow: \"hidden\",\n },\n itemPressable: {\n paddingHorizontal: INDENT,\n paddingVertical: 16,\n flexDirection: \"row\",\n justifyContent: \"space-between\",\n alignItems: \"center\",\n transitionDuration: \"100ms\",\n },\n filename: { color: \"white\", fontSize: 20, marginLeft: 12 },\n virtual: { textAlign: \"right\", color: \"white\" },\n image: { width: 24, height: 24, resizeMode: \"contain\" },\n});\n\nexport function getNavOptions(): NativeStackNavigationOptions {\n return {\n title: \"Index\",\n headerShown: true,\n presentation: \"modal\",\n animation: \"default\",\n headerLargeTitle: true,\n headerTitleStyle: {\n color: \"white\",\n },\n\n headerTintColor: \"white\",\n headerLargeTitleStyle: {\n color: \"white\",\n },\n headerStyle: {\n backgroundColor: \"black\",\n // @ts-expect-error: mistyped\n borderBottomColor: \"#323232\",\n },\n }\n}\n\nexport function Directory() {\n const routes = useSortedRoutes();\n const { bottom } = useSafeAreaInsets();\n const { width } = useWindowDimensions();\n return (\n <View style={styles.container}>\n\n <StatusBar barStyle=\"light-content\" />\n <View\n style={[\n styles.main,\n {\n minWidth: Math.min(960, width * 0.9),\n },\n ]}\n >\n <ScrollView\n contentInsetAdjustmentBehavior=\"automatic\"\n contentContainerStyle={[\n styles.scroll,\n {\n paddingBottom: bottom + 12,\n },\n ]}\n style={{ flex: 1 }}\n >\n {routes.map((child) => (\n <View key={child.contextKey} style={styles.itemContainer}>\n <FileItem route={child} />\n </View>\n ))}\n </ScrollView>\n </View>\n </View>\n );\n}\n\nfunction FileItem({\n route,\n level = 0,\n parents = [],\n}: {\n route: RouteNode;\n level?: number;\n parents?: string[];\n}) {\n const disabled = route.children.length > 0;\n\n const href = React.useMemo(() => {\n return (\n \"/\" +\n [...parents, route.route]\n .map((v) => {\n // groups and index must be erased\n return !!matchFragmentName(v) || v === \"index\" ? \"\" : v;\n })\n .filter(Boolean)\n .join(\"/\")\n );\n }, [parents, route.route]);\n\n return (\n <>\n {/* @ts-expect-error: disabled not on type */}\n <Link href={href} disabled={disabled} asChild>\n <Pressable>\n {({ pressed, hovered }) => (\n <View\n style={[\n styles.itemPressable,\n {\n paddingLeft: INDENT + level * INDENT,\n backgroundColor: hovered\n ? \"rgba(255,255,255,0.1)\"\n : \"transparent\",\n },\n pressed && { backgroundColor: \"#323232\" },\n disabled && { opacity: 0.4 },\n ]}\n >\n <View style={{ flexDirection: \"row\", alignItems: \"center\" }}>\n {route.children.length ? <PkgIcon /> : <FileIcon />}\n <Text style={styles.filename}>{route.contextKey}</Text>\n </View>\n\n {!disabled && <ForwardIcon />}\n {route.generated && <Text style={styles.virtual}>Virtual</Text>}\n </View>\n )}\n </Pressable>\n </Link>\n {route.children.map((child, index) => (\n <FileItem\n key={child.contextKey}\n route={child}\n parents={[...parents, route.route]}\n level={level + 1}\n />\n ))}\n </>\n );\n}\n\nfunction FileIcon() {\n return (\n <Image\n style={styles.image}\n source={require(\"expo-router/assets/file.png\")}\n />\n );\n}\n\nfunction PkgIcon() {\n return (\n <Image\n style={styles.image}\n source={require(\"expo-router/assets/pkg.png\")}\n />\n );\n}\n\nfunction ForwardIcon() {\n return (\n <Image\n style={styles.image}\n source={require(\"expo-router/assets/forward.png\")}\n />\n );\n}\n"]}
1
+ {"version":3,"file":"Directory.js","sourceRoot":"","sources":["../../src/views/Directory.tsx"],"names":[],"mappings":"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","sourcesContent":["import { Image, Pressable, StyleSheet, Text, View } from \"@bacons/react-views\";\nimport { useNavigation } from \"@react-navigation/native\";\nimport { NativeStackNavigationOptions } from \"@react-navigation/native-stack\";\nimport React from \"react\";\nimport { ScrollView, Platform, StatusBar, useWindowDimensions } from \"react-native\";\nimport { useSafeAreaInsets } from \"react-native-safe-area-context\";\n\nimport { useRoutesContext } from \"../context\";\nimport { matchDeepDynamicRouteName, matchFragmentName } from \"../matchers\";\nimport { RouteNode } from \"../Route\";\nimport { Link } from \"./Link\";\n\nconst INDENT = 18;\n\nfunction useSortedRoutes() {\n const ctx = useRoutesContext();\n\n const routes = React.useMemo(\n () =>\n ctx\n .filter((route) => !route.internal)\n .sort((a, b) => {\n // Emulate vscode's sorting\n if (a.route < b.route) {\n return -1;\n }\n if (a.route > b.route) {\n return 1;\n }\n return 0;\n }),\n [ctx]\n );\n return routes;\n}\n\nconst styles = StyleSheet.create({\n container: {\n backgroundColor: \"black\",\n flex: 1,\n alignItems: \"stretch\",\n },\n main: {\n marginHorizontal: \"auto\",\n flex: 1,\n\n alignItems: \"stretch\",\n },\n scroll: {\n padding: 12,\n flex: 1,\n // paddingTop: top + 12,\n alignItems: \"stretch\",\n },\n itemContainer: {\n borderWidth: 1,\n borderColor: \"#323232\",\n borderRadius: 19,\n marginBottom: 12,\n overflow: \"hidden\",\n },\n itemPressable: {\n paddingHorizontal: INDENT,\n paddingVertical: 16,\n flexDirection: \"row\",\n justifyContent: \"space-between\",\n alignItems: \"center\",\n transitionDuration: \"100ms\",\n },\n filename: { color: \"white\", fontSize: 20, marginLeft: 12 },\n virtual: { textAlign: \"right\", color: \"white\" },\n image: { width: 24, height: 24, resizeMode: \"contain\" },\n});\n\nexport function getNavOptions(): NativeStackNavigationOptions {\n return {\n title: \"Index\",\n headerShown: true,\n presentation: \"modal\",\n animation: \"default\",\n headerLargeTitle: true,\n headerTitleStyle: {\n color: \"white\",\n },\n\n headerTintColor: \"white\",\n headerLargeTitleStyle: {\n color: \"white\",\n },\n headerStyle: {\n backgroundColor: \"black\",\n // @ts-expect-error: mistyped\n borderBottomColor: \"#323232\",\n },\n }\n}\n\nexport function Directory() {\n const routes = useSortedRoutes();\n const { bottom } = useSafeAreaInsets();\n const { width } = useWindowDimensions();\n return (\n <View style={styles.container}>\n\n <StatusBar barStyle=\"light-content\" />\n <View\n style={[\n styles.main,\n {\n minWidth: Math.min(960, width * 0.9),\n },\n ]}\n >\n <ScrollView\n contentInsetAdjustmentBehavior=\"automatic\"\n contentContainerStyle={[\n styles.scroll,\n {\n paddingBottom: bottom + 12,\n },\n ]}\n style={{ flex: 1 }}\n >\n {routes.map((child) => (\n <View key={child.contextKey} style={styles.itemContainer}>\n <FileItem route={child} />\n </View>\n ))}\n </ScrollView>\n </View>\n </View>\n );\n}\n\nfunction FileItem({\n route,\n level = 0,\n parents = [],\n}: {\n route: RouteNode;\n level?: number;\n parents?: string[];\n}) {\n const disabled = route.children.length > 0;\n\n const navigation = useNavigation();\n const href = React.useMemo(() => {\n return (\n \"/\" +\n [...parents, route.route]\n .map((v) => {\n // add an extra layer of entropy to the url for deep dynamic routes\n if (matchDeepDynamicRouteName(v)) {\n return v + '/' + Date.now()\n }\n // groups and index must be erased\n return !!matchFragmentName(v) || v === \"index\" ? \"\" : v;\n })\n .filter(Boolean)\n .join(\"/\")\n );\n }, [parents, route.route]);\n\n return (\n <>\n <Link href={href} onPress={() => {\n if (Platform.OS !== 'web') {\n // Ensure the modal pops\n navigation.goBack();\n }\n }}\n // @ts-expect-error: disabled not on type\n disabled={disabled} asChild>\n <Pressable>\n {({ pressed, hovered }) => (\n <View\n style={[\n styles.itemPressable,\n {\n paddingLeft: INDENT + level * INDENT,\n backgroundColor: hovered\n ? \"rgba(255,255,255,0.1)\"\n : \"transparent\",\n },\n pressed && { backgroundColor: \"#323232\" },\n disabled && { opacity: 0.4 },\n ]}\n >\n <View style={{ flexDirection: \"row\", alignItems: \"center\" }}>\n {route.children.length ? <PkgIcon /> : <FileIcon />}\n <Text style={styles.filename}>{route.contextKey}</Text>\n </View>\n\n {!disabled && <ForwardIcon />}\n {route.generated && <Text style={styles.virtual}>Virtual</Text>}\n </View>\n )}\n </Pressable>\n </Link>\n {route.children.map((child, index) => (\n <FileItem\n key={child.contextKey}\n route={child}\n parents={[...parents, route.route]}\n level={level + 1}\n />\n ))}\n </>\n );\n}\n\nfunction FileIcon() {\n return (\n <Image\n style={styles.image}\n source={require(\"expo-router/assets/file.png\")}\n />\n );\n}\n\nfunction PkgIcon() {\n return (\n <Image\n style={styles.image}\n source={require(\"expo-router/assets/pkg.png\")}\n />\n );\n}\n\nfunction ForwardIcon() {\n return (\n <Image\n style={styles.image}\n source={require(\"expo-router/assets/forward.png\")}\n />\n );\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "expo-router",
3
- "version": "0.0.5",
3
+ "version": "0.0.7",
4
4
  "main": "build/index.js",
5
5
  "files": [
6
6
  "entry.js",