{"id":13451863,"url":"https://github.com/gregberge/react-teleporter","last_synced_at":"2025-05-15T04:04:52.678Z","repository":{"id":37952615,"uuid":"191229422","full_name":"gregberge/react-teleporter","owner":"gregberge","description":"Teleport React components in the same React tree 📡","archived":false,"fork":false,"pushed_at":"2023-03-14T09:12:50.000Z","size":1643,"stargazers_count":1134,"open_issues_count":0,"forks_count":18,"subscribers_count":4,"default_branch":"main","last_synced_at":"2025-05-14T08:58:12.027Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gregberge.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null},"funding":{"github":"gregberge"}},"created_at":"2019-06-10T19:04:55.000Z","updated_at":"2025-05-03T07:32:26.000Z","dependencies_parsed_at":"2024-01-06T01:55:03.515Z","dependency_job_id":"12413db6-287a-4390-a6ad-43462f12bff0","html_url":"https://github.com/gregberge/react-teleporter","commit_stats":{"total_commits":59,"total_committers":9,"mean_commits":6.555555555555555,"dds":0.4067796610169492,"last_synced_commit":"f65559e65807193da83f1d00ec37b6417290ebb1"},"previous_names":["smooth-code/react-teleporter"],"tags_count":13,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gregberge%2Freact-teleporter","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gregberge%2Freact-teleporter/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gregberge%2Freact-teleporter/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gregberge%2Freact-teleporter/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gregberge","download_url":"https://codeload.github.com/gregberge/react-teleporter/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":254270641,"owners_count":22042858,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-07-31T07:01:05.096Z","updated_at":"2025-05-15T04:04:52.651Z","avatar_url":"https://github.com/gregberge.png","language":"TypeScript","funding_links":["https://github.com/sponsors/gregberge"],"categories":["JavaScript","TypeScript"],"sub_categories":[],"readme":"# react-teleporter\n\n[![License](https://img.shields.io/npm/l/react-teleporter.svg)](https://github.com/gregberge/react-teleporter/blob/main/LICENSE)\n[![npm package](https://img.shields.io/npm/v/react-teleporter/latest.svg)](https://www.npmjs.com/package/react-teleporter)\n[![npm bundle size](https://img.shields.io/bundlephobia/minzip/react-teleporter)](https://bundlephobia.com/package/react-teleporter)\n[![CI](https://github.com/gregberge/react-teleporter/actions/workflows/ci.yml/badge.svg)](https://github.com/gregberge/react-teleporter/actions/workflows/ci.yml)\n[![codecov](https://codecov.io/gh/gregberge/react-teleporter/branch/main/graph/badge.svg)](https://codecov.io/gh/gregberge/react-teleporter)\n\nTeleport React components in the same React tree.\n\n👉 [**Read how to use it to create scalable layouts**](https://gregberge.com/blog/react-scalable-layout)\n\n👉 [**Checkout the demo on CodeSandbox**](https://codesandbox.io/s/react-teleporter-demo-ryklv)\n\n```bash\nnpm install react-teleporter\n```\n\n## Example\n\n```js\nimport { createTeleporter } from \"react-teleporter\";\n\nconst StatusBar = createTeleporter();\n\nfunction Header() {\n  return (\n    \u003cheader\u003e\n      \u003cStatusBar.Target /\u003e\n    \u003c/header\u003e\n  );\n}\n\nfunction Page() {\n  return (\n    \u003cmain\u003e\n      {/* Teleport \"Loading...\" into the header */}\n      \u003cStatusBar.Source\u003eLoading...\u003c/StatusBar.Source\u003e\n    \u003c/main\u003e\n  );\n}\n\nfunction App() {\n  return (\n    \u003cdiv\u003e\n      \u003cHeader /\u003e\n      \u003cPage /\u003e\n    \u003c/div\u003e\n  );\n}\n```\n\n## Why?\n\nIn complex app, you may have to configure a part of the application from another. If you know [react-helmet](https://github.com/nfl/react-helmet) it is the same philosophy. You want to configure a part of your application from another place.\n\n## Recipes\n\n### Use another target element\n\nUse `as` property on target to specify another tag.\n\n```js\nconst Teleporter = createTeleporter()\n\n\u003cTeleporter.Target as=\"footer\" /\u003e\n```\n\n\u003e Be careful of specifying an element with a ref to a DOM element, it uses [React Portals](https://reactjs.org/docs/portals.html) under the hood.\n\n### Use props on target\n\nAll props are forwarded to target.\n\n```js\nconst Teleporter = createTeleporter()\n\n\u003cTeleporter.Target onClick={/* ... */} /\u003e\n```\n\n### Create a custom target ref\n\nUse `useTargetRef` to create a custom target ref.\n\n```js\nconst Teleporter = createTeleporter();\n\nfunction CustomTarget() {\n  const targetRef = Teleporter.useTargetRef();\n  return \u003cdiv ref={targetRef} /\u003e;\n}\n```\n\n### Use multiple sources\n\nBy default only one `Source` is allowed to be injected into a `Target`. Sometimes you may want to inject multiple sources into a single target. Create teleporter with `{ multiSources: true }` option.\n\n```js\nconst Teleporter = createTeleporter({ multiSources: true })\n\n\u003cTeleporter.Source multiple\u003e\n  \u003ca href=\"#\"\u003eA link\u003c/a\u003e\n\u003c/Teleporter.Source\u003e\n\n\u003cTeleporter.Source multiple\u003e\n  \u003ca href=\"#\"\u003eAnother link\u003c/a\u003e\n\u003c/Teleporter.Source\u003e\n\n// The target will contains the two links\n```\n\n### Use function as children\n\nUseful for having access to the `Target` element. E.g., to dispatch an event through the `Target` when something happens in the `Source`.\n\n```js\nconst Teleporter = createTeleporter();\n\nconst forwardEvent = (element) =\u003e (event) =\u003e\n  element.dispatch(new Event(event.type, event));\n\n\u003cTeleporter.Source\u003e\n  {(element) =\u003e \u003cdiv onClick={forwardEvent(element)}\u003e\u003c/div\u003e}\n\u003c/Teleporter.Source\u003e;\n```\n\n## API\n\n### createTeleporter\n\n`createTeleporter` is the only method exposed by this package. It returns an object containing a `Target`, a `Source` and a `useTargetRef` to create a custom target.\n\n```js\nimport { createTeleporter } from \"react-teleporter\";\n\nconst Teleporter = createTeleporter();\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgregberge%2Freact-teleporter","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgregberge%2Freact-teleporter","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgregberge%2Freact-teleporter/lists"}