diff --git a/README.md b/README.md
index 2346e1a4..cb915edd 100644
--- a/README.md
+++ b/README.md
@@ -77,6 +77,7 @@
- [**State**](./docs/State.md)
- [`createMemo`](./docs/createMemo.md) — factory of memoized hooks.
+ - [`useAdopt`](./docs/useAdopt.md) — extract value from multiple render-prop (or FaCC) components.
- [`useCallbag`](./docs/useCallbag.md) — tracks latest value of a callbag.
- [`useGetSet`](./docs/useGetSet.md) — returns state getter `get()` instead of raw state.
- [`useGetSetState`](./docs/useGetSetState.md) — as if [`useGetSet`](./docs/useGetSet.md) and [`useSetState`](./docs/useSetState.md) had a baby.
diff --git a/docs/useAdopt.md b/docs/useAdopt.md
new file mode 100644
index 00000000..986ded6f
--- /dev/null
+++ b/docs/useAdopt.md
@@ -0,0 +1,35 @@
+# `useAdopt`
+
+Extracts a values from multiple render-prop or FaCC components.
+This hook is similar to [`useRenderProp`](./useRenderProp.md), but
+it allows to specify a named map of multiple render-prop elements
+from which to extract values.
+
+
+## Usage
+
+```jsx
+import {useAdopt} from 'react-use';
+
+const FaCC = ({children}) => {
+ return children('VALUE-FaCC');
+};
+const RenderProp = ({render}) => {
+ return render('VALUE-RenderProp');
+};
+
+const Demo = () => {
+ const [fragment, result] = useAdopt({
+ facc: ,
+ renderProp: ,
+ });
+
+ return (
+ <>
+ {fragment}
+
FaCC: {result.facc[0]}
+ Render prop: {result.renderProp[0]}
+ >
+ );
+};
+```
diff --git a/src/__stories__/useAdopt.story.tsx b/src/__stories__/useAdopt.story.tsx
new file mode 100644
index 00000000..5fe91eaf
--- /dev/null
+++ b/src/__stories__/useAdopt.story.tsx
@@ -0,0 +1,32 @@
+import {storiesOf} from '@storybook/react';
+import * as React from 'react';
+import {useAdopt} from '..';
+import ShowDocs from '../util/ShowDocs';
+
+const FaCC = ({children}) => {
+ return children('VALUE-FaCC');
+};
+const RenderProp = ({render}) => {
+ return render('VALUE-RenderProp');
+};
+
+const Demo = () => {
+ const [fragment, result] = useAdopt({
+ facc: ,
+ renderProp: ,
+ });
+
+ return (
+ <>
+ {fragment}
+ FaCC: {result.facc[0]}
+ Render prop: {result.renderProp[0]}
+ >
+ );
+};
+
+storiesOf('useAdopt', module)
+ .add('Docs', () => )
+ .add('Demo', () =>
+
+ )
diff --git a/src/index.ts b/src/index.ts
index 6cbb5f6a..96c1f297 100644
--- a/src/index.ts
+++ b/src/index.ts
@@ -1,4 +1,5 @@
import createMemo from './createMemo';
+import useAdopt from './useAdopt';
import useAsync from './useAsync';
import useAudio from './useAudio';
import useBattery from './useBattery';
@@ -44,6 +45,7 @@ import useWindowSize from './useWindowSize';
export {
createMemo,
+ useAdopt,
useAsync,
useAudio,
useBattery,
diff --git a/src/useAdopt.ts b/src/useAdopt.ts
new file mode 100644
index 00000000..175c8c5c
--- /dev/null
+++ b/src/useAdopt.ts
@@ -0,0 +1,19 @@
+import * as React from 'react';
+import useRenderProp from './useRenderProp';
+
+const useAdopt = (map: {[key in keyof T]: React.ReactElement}): [React.ReactElement, T] => {
+ const keys = Object.keys(map);
+ const fragments: React.ReactElement[] = [];
+ const result: T = {} as T;
+
+ keys.sort();
+ for (const key of keys) {
+ const [fragment, value] = useRenderProp(map[key]);
+ fragments.push(React.cloneElement(fragment, {key}));
+ result[key] = value;
+ }
+
+ return [React.createElement(React.Fragment, null, ...fragments), result];
+};
+
+export default useAdopt;