Skip to content

Commit c97f284

Browse files
jvliwanagmaddie927
authored andcommitted
Add support for React Context (#101)
* Add support for React Context * See https://reactjs.org/docs/context.html * Change ReactContext to be foreign data type
1 parent 9501881 commit c97f284

File tree

2 files changed

+67
-0
lines changed

2 files changed

+67
-0
lines changed

Diff for: src/React/Basic.js

+14
Original file line numberDiff line numberDiff line change
@@ -218,3 +218,17 @@ exports.toReactComponent = function(_unionDict) {
218218
};
219219
};
220220
};
221+
222+
exports.createContext = function(defaultValue) {
223+
return function () {
224+
return React.createContext(defaultValue);
225+
};
226+
};
227+
228+
exports.contextProvider = function(context) {
229+
return context.Provider;
230+
};
231+
232+
exports.contextConsumer = function(context) {
233+
return context.Consumer;
234+
};

Diff for: src/React/Basic.purs

+53
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,12 @@ module React.Basic
2121
, ReactComponentInstance
2222
, toReactComponent
2323
, Ref
24+
, ReactContext
25+
, createContext
26+
, contextConsumer
27+
, contextProvider
28+
, provider
29+
, consumer
2430
) where
2531

2632
import Prelude
@@ -369,6 +375,53 @@ foreign import toReactComponent
369375
-> { render :: Self props state -> JSX | spec }
370376
-> ReactComponent { | jsProps }
371377

378+
foreign import data ReactContext :: Type -> Type
379+
380+
-- | Create a `ReactContext` given a default value. Use `provider` and `consumer`
381+
-- | to provide and consume context values. Alternatively, use `contextProvider`
382+
-- | and `contextConsumer` directly if a `ReactComponent` is required for interop.
383+
-- |
384+
-- | ```purs
385+
-- | render self =
386+
-- | R.div_
387+
-- | [ R.button
388+
-- | { onClick: capture_ $ self.setState \s -> s { counter = s.counter + 1 }
389+
-- | , children: [ R.text "Tick!" ]
390+
-- | }
391+
-- | , provider countContext self.state.counter
392+
-- | [ consumer countContext \counter ->
393+
-- | [ R.text $ "Ticks: " <> (show counter)
394+
-- | ]
395+
-- | ]
396+
-- | ]
397+
-- | ```
398+
-- |
399+
-- | __*See also:* `provider`, `consumer`, React's documentation regarding Context__
400+
foreign import createContext :: forall a. a -> Effect (ReactContext a)
401+
402+
foreign import contextProvider
403+
:: forall a
404+
. ReactContext a
405+
-> ReactComponent { value :: a, children :: Array JSX }
406+
407+
foreign import contextConsumer
408+
:: forall a
409+
. ReactContext a
410+
-> ReactComponent { children :: a -> Array JSX }
411+
412+
-- | Create a provider `JSX` given a context value and children.
413+
-- |
414+
-- | __*See also:* `createContext`, `consumer`__
415+
provider :: forall a. ReactContext a -> a -> Array JSX -> JSX
416+
provider context value children =
417+
element (contextProvider context) { value, children }
418+
419+
-- | Create a consumer `JSX` from a context value to children.
420+
-- |
421+
-- | __*See also:* `createContext`, `producer`__
422+
consumer :: forall a. ReactContext a -> (a -> Array JSX) -> JSX
423+
consumer context children =
424+
element (contextConsumer context) { children }
372425

373426
-- |
374427
-- | Internal utility or FFI functions

0 commit comments

Comments
 (0)