### ReasonReact Basic Greeting Component
Source: https://reasonml.github.io/reason-react/docs/en/simple
Demonstrates a simple ReasonReact component that renders a greeting message. It highlights Reason's implicit returns, labeled parameters, and type casting for strings.
```reason
/* Greeting.re */
[@react.component]
let make = (~message) =>
{React.string(message)}
;
```
```reason
/* ... */
/* ... */
```
--------------------------------
### Equivalent JavaScript Usage of ReasonReact Component
Source: https://reasonml.github.io/reason-react/docs/en/intro-example
Illustrates the equivalent way to render the 'Greeting' ReasonReact component in a plain JavaScript index file, demonstrating how ReasonReact components are used in a JavaScript context.
```javascript
/* file: index.js */
let root = document.getElementById("root");
if (root != null) {
ReactDOM.render(, root);
};
```
--------------------------------
### Import ReasonReact Component into JavaScript/TypeScript App
Source: https://reasonml.github.io/reason-react/docs/en/intro-example
Shows how to import a ReasonReact component (transpiled to JavaScript) into an existing JavaScript or TypeScript application. It assumes the component exports a function named 'make'.
```javascript
/* file: App.js */
import { make as Greeting } from "./Greeting.js";
export default function App() {
return (
);
}
```
--------------------------------
### Define ReasonReact Component: Greeting
Source: https://reasonml.github.io/reason-react/docs/en/intro-example
Defines a simple ReasonReact functional component named 'Greeting' that accepts a 'name' prop and renders a button with a personalized greeting. Requires the 'react' binding.
```reason
/* file: Greeting.re */
[@react.component]
let make = (~name) => ;
```
--------------------------------
### ReasonReact Component Rendering a List with Belt
Source: https://reasonml.github.io/reason-react/docs/en/simple
Demonstrates rendering a list of items in ReasonReact using the Belt library for array mapping. It defines a record type for list items and shows how to map and render them as list elements.
```reason
/* We define the type of the item (this is a record) */
type item = {
id: string,
text: string,
};
[@react.component]
let make = (~items) =>
{
items
->Belt.Array.map(item =>
{React.string(item.text)}
)
/* Since everything is typed, the arrays need to be, too! */
->React.array
}
;
```
--------------------------------
### ReasonReact Component with Optional Arguments and Fragments
Source: https://reasonml.github.io/reason-react/docs/en/simple
Illustrates how to create a ReasonReact component with an optional argument and use React.Fragment. It shows conditional rendering based on the presence of the optional argument.
```reason
[@react.component]
let make = (~title, ~description=?)
=>
<>
/* React.Fragment works the same way as in React.js! */
title
/* Handling optional variables where you don't want to render anything */
{
switch (description) {
| Some(description) => {React.string(description)}
/* Since everything is typed, React.null is required */
| None => React.null
}
}
>;
```
--------------------------------
### Use ReasonReact Component in Reason App
Source: https://reasonml.github.io/reason-react/docs/en/intro-example
Renders the 'Greeting' ReasonReact component within a Reason application's index file using ReactDOM.render. It selects the root element by its ID and handles the case where the element is not found.
```reason
/* file: Index.re */
switch (ReactDOM.querySelector("#root")) {
| Some(root) => ReactDOM.render(, root)
| None => ()
}
```
--------------------------------
### ReasonReact Simple Counter Example with useState
Source: https://reasonml.github.io/reason-react/docs/en/usestate-hook
A basic counter component implemented using the `useState` hook in ReasonReact. It demonstrates how to initialize state, display it, and update it using buttons for incrementing, decrementing, and resetting.
```reasonml
[@react.component]
let make = (~initialCount) => {
let (count, setCount) = React.useState(_ => initialCount);
{React.string("Count: " ++ Int.to_string(count))}
;
};
```
--------------------------------
### ReasonReact Form Component
Source: https://reasonml.github.io/reason-react/docs/en/simple
Shows a ReasonReact form component, demonstrating event handling for form submission and input element attributes. It highlights differences like `type_` for reserved words and automatic prop conversion.
```reason
[@react.component]
let make = () => {
/* unused variables are prefixed with an underscore */
let onSubmit = _event => Js.log("Hello this is a log!");
/* onSubmit=onSubmit turns to just onSubmit */
;
};
```
--------------------------------
### ReasonReact cloneElement Usage Example
Source: https://reasonml.github.io/reason-react/docs/en/clone-element
Demonstrates how to use the `ReasonReact.cloneElement` function, mirroring the ReactJS `cloneElement` functionality. It shows creating a new element with modified props and children. Note that the `props` argument is marked as unsafe.
```reasonml
let clonedElement = React.cloneElement(, ~props={"payload": 1}, [||]);
```
--------------------------------
### Handle Optional Data with Belt.Option.mapWithDefault
Source: https://reasonml.github.io/reason-react/docs/en/working-with-optional-data
This example shows how to safely extract a value from an optional type using Belt.Option.mapWithDefault. If the optional value is present, it applies a function to it; otherwise, it returns a default value.
```reasonml
let label = selected->Belt.Option.mapWithDefault("Select a Color", selected => selected##name);
```
--------------------------------
### Apollo Client Integration with ReasonReact and graphql-ppx
Source: https://reasonml.github.io/reason-react/docs/en/graphql-apollo
This example shows how to use Apollo Client's useQuery hook within a ReasonReact component. It combines graphql-ppx for query definition with Apollo Hooks to fetch user data. The component handles different data states (Loading, Data, NoData, Error) using Reason's pattern matching for type-safe rendering.
```reason
/* Username.re */
module UserQuery = [%graphql {|
query UserQuery {
currentUser {
name
}
}
|}];
[@react.component]
let make = () => {
let (currentUserName, _) = ApolloHooks.useQuery(UserQuery.definition);
{
switch(currentUserName) {
| Loading =>
{React.string("Loading...")}
| Data(data) =>
{React.string(data##currentUser##name)}
| NoData
| Error(_) =>
{React.string("Get off my lawn!")}
}
}
}
```
--------------------------------
### Invalid GraphQL Query Example with graphql-ppx
Source: https://reasonml.github.io/reason-react/docs/en/graphql-apollo
Illustrates an intentionally invalid GraphQL query to show how graphql-ppx catches errors at compile time. This example intentionally uses an incorrect field name ('namee') which would result in a compiler error, preventing runtime issues.
```reason
/* Username.re */
module UserQuery = [%graphql {|
query UserQuery {
currentUser {
namee // ERROR: Unknown field on type currentUser
}
}
|}];
```
--------------------------------
### ReasonReact Children Handling Example
Source: https://reasonml.github.io/reason-react/docs/en/jsx
Illustrates how ReasonReact passes multiple children as an array and unwraps a single child for convenience when rendering components.
```reason
```
```reason
```
--------------------------------
### Reason React Component Naming Conventions
Source: https://reasonml.github.io/reason-react/docs/en/components
This example showcases how Reason React automatically names components based on their module and declaration. It illustrates naming for a top-level 'make' function, a 'component' function, and a 'make' function within a nested module. It also shows how to manually set a display name using React.setDisplayName.
```reason
/* File.re */
/* will be named `File` in dev tools */
[@react.component]
let make = ...
/* will be named `File$component` in dev tools */
[@react.component]
let component = ...
module Nested = {
/* will be named `File$Nested` in dev tools */
[@react.component]
let make = ...
};
/* Example of manual naming */
let make = ...;
React.setDisplayName(make, "NameThatShouldBeInDevTools");
```
--------------------------------
### ReasonReact useEffect0: Cleanup Effect
Source: https://reasonml.github.io/reason-react/docs/en/useeffect-hook
Demonstrates how to use React.useEffect0 in ReasonReact to set up an effect that requires cleanup. The cleanup function is returned as an option, ensuring resources like subscriptions are properly released when the component unmounts or the effect re-runs. This is useful for one-time setup and teardown.
```reason
[@react.component]
let make = () => {
React.useEffect0(() => {
let id = subscription.subscribe();
/* clean up the subscription */
Some(() => subscription.unsubscribe(id));
});
}
```
--------------------------------
### ReasonReact Usage of Spread Component
Source: https://reasonml.github.io/reason-react/docs/en/adding-data-props
An example demonstrating how to use the 'Spread' component in ReasonReact. It shows passing a 'data-cy' attribute via the 'props' argument to the Spread component, which then applies it to its child 'div' element.
```reasonml
[@react.component]
let make = () =>
/* This div will now have the `data-cy` attribute in the DOM! */
;
```
--------------------------------
### Bind to External JavaScript Context in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/context
This example shows how to bind to a React context defined in a separate JavaScript file within your ReasonReact application. It uses `[@bs.module]` to import the context and then consumes it using `React.useContext`, demonstrating interoperability between ReasonReact and JavaScript contexts.
```javascript
/** ComponentThatDefinesTheContext.js */
export const ThemeContext = React.createContext("light");
```
```reason
/** ComponentToConsumeTheContext.re */
[@bs.module "ComponentThatDefinesTheContext"]
external themeContext: React.Context.t(string) = "ThemeContext";
[@react.component]
let make = () => {
let theme = React.useContext(themeContext);
theme->React.string
}
```
--------------------------------
### ReasonReact Component with Tailwind CSS Styling
Source: https://reasonml.github.io/reason-react/docs/en/tailwind-css
This example showcases a ReasonReact component utilizing Tailwind CSS classes for styling. It demonstrates how to apply common Tailwind utilities for layout, appearance, and text formatting within a React component structure.
```reason
[@react.component]
let make = () =>
{React.string("Tailwind")}
{React.string("A reason react starter with tailwind")}
;
```
--------------------------------
### ReasonReact useEffect1: Conditional Effect Firing
Source: https://reasonml.github.io/reason-react/docs/en/useeffect-hook
Illustrates using React.useEffect1 in ReasonReact for effects that depend on specific values. The effect will only re-run if the dependencies listed in the array change. This is crucial for performance, preventing unnecessary re-executions of effects. The example shows setting up and cleaning up a subscription based on a 'source' prop.
```reason
[@react.component]
let make = (~source) => {
React.useEffect1(() => {
let id = subscription.subscribe();
/* clean up the subscription */
Some(() => subscription.unsubscribe(id));
}, [|source|]);
}
```
--------------------------------
### Route Matching with Pattern Matching in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/router
Demonstrates how to match different URL paths using Reason's powerful pattern matching capabilities. This allows for flexible handling of various routes and sub-routes within a ReasonReact application.
```reason
let url = ReasonReactRouter.useUrl();
switch (url.path) {
| ["book", id, "edit"] => handleBookEdit(id)
| ["book", id] => getBook(id)
| ["book", id, _] => noSuchBookOperation()
| [] => showMainPage()
| ["shop"] | ["shop", "index"] => showShoppingPage()
| ["shop", ...rest] =>
/* e.g. "shop/cart/10", but let "cart/10" be handled by another function */
nestedMatch(rest)
| _ => showNotFoundPage()
};
```
--------------------------------
### Passing Components as Props in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/component-as-prop
Demonstrates how to pass components as props in ReasonReact by using a callback function. This approach allows the owner to control how the component renders and avoids the need for prop spreading within the child component.
```reasonml
let bannerCallback = (prop1, prop2) => ;
;
```
--------------------------------
### Render and Test ReasonReact Components with ReactDOMTestUtils
Source: https://reasonml.github.io/reason-react/docs/en/testing
This snippet demonstrates how to write a basic test for ReasonReact components using ReactDOMTestUtils and an imaginary TestFramework. It covers setting up a container, rendering a component with `act`, and asserting its presence in the DOM using provided querying utilities.
```reasonml
open ReactDOMTestUtils;
open TestFramework;
// TestFramework isn't a real module, just an imaginary set of bindings
// to a JavaScript testing framework
describe("My basic test", ({test, beforeEach, afterEach}) => {
// Here, we prepare an empty ref that will eventually be
// the root node for our test
let container = ref(None);
// Before each test, creates a new div root
beforeEach(prepareContainer(container));
// After each test, removes the div
afterEach(cleanupContainer(container));
test("can render DOM elements", ({expect}) => {
// The following function gives us the div
let container = getContainer(container);
let root = ReactDOM.Client.createRoot(container);
// Most of the ReactDOMTestUtils API is there
act(() => {
ReactDOM.Client.render(root,
"Hello world!"->React.string
);
});
expect.bool(
container
// We also provide some basic DOM querying utilities
// to ease your tests
->DOM.findBySelectorAndTextContent("div", "Hello world!")
->Option.isSome,
).
toBeTrue();
});
});
```
--------------------------------
### Using ContextProvider in ReasonReact Application
Source: https://reasonml.github.io/reason-react/docs/en/context
This code shows how to use the `ContextProvider` component to wrap a part of your ReasonReact application. Any component rendered within `ContextProvider` will have access to the provided context value. This is a common pattern for managing global state like themes or user authentication.
```reason
/** App.re */
[@react.component]
let make = () =>
```
--------------------------------
### Create React Component with ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/reason-using-js
This snippet demonstrates how to create a React component using ReasonReact. It shows the JavaScript implementation and its corresponding ReasonML definition, enabling interoperability between the two languages.
```javascript
var ReactDOM = require('react-dom');
var React = require('react');
var MyBanner = function(props) {
if (props.show) {
return React.createElement('div', null,
'Here\'s the message from the owner: ' + props.message
);
}
else {
return null;
}
};
module.exports = MyBanner;
```
```reasonml
/* ReactJS used by ReasonReact */
[@react.component] [@bs.module]
external make : (~show: bool, ~message: string) => React.element = "./MyBanner";
```
--------------------------------
### Basic Render Props with ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/render-props
Demonstrates a basic implementation of render props in ReasonReact. The Loader component accepts a `render` function prop to define its content.
```reasonml
[@react.component]
let make = () => {
} />
};
```
```reasonml
/* Loader.re */
[@react.component]
let make = (~render) => {
{render()}
};
```
--------------------------------
### ReasonReact Ternary Shortcut for Conditional Rendering
Source: https://reasonml.github.io/reason-react/docs/en/ternary-shortcut
Demonstrates the recommended way to perform conditional rendering in ReasonReact using the ternary operator. This pattern ensures proper handling of null rendering, unlike the shortcut often used in JavaScript. It contrasts with the ReactJS `&&` pattern.
```reason
showButton ? : React.null
```
--------------------------------
### JavaScript Import of ReasonML Component
Source: https://reasonml.github.io/reason-react/docs/en/js-using-reason
Shows how to import and use a ReasonML component compiled to JavaScript within a JavaScript file. Assumes the ReasonML component is available via a module path.
```javascript
var PageReason = require('path/to/PageReason.js').make;
```
--------------------------------
### Conditional Rendering Based on URL Hash and State in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/router
Illustrates how to use pattern matching on both the URL hash and application state (e.g., `MyAppStatus.isUserLoggedIn`) to conditionally render components or determine application state within a ReasonReact component.
```reason
[@react.component]
let make = () => {
let url = ReasonReactRouter.useUrl();
let nowShowing =
switch (url.hash, MyAppStatus.isUserLoggedIn) {
| ("active", _) => Active
| ("completed", _) => Completed
| ("shared", true) => Shared
| ("shared", false) when isSpecialUser => /* handle this state please */
| ("shared", false) => /* handle this state please */
| _ => All
};
/* ... */
}
```
--------------------------------
### ReasonReact ReactDOM: Basic Rendering
Source: https://reasonml.github.io/reason-react/docs/en/dom
Renders a React element into a DOM element using ReasonReact's ReactDOM module. It first queries for a root element by ID and then uses `ReactDOM.Client.createRoot` and `ReactDOM.Client.render` to mount the component. Handles cases where the root element is not found.
```reason
let element = ReactDOM.querySelector("#root");
switch (element) {
| None => Js.log("#root element not found");
| Some(element) => {
let root = ReactDOM.Client.createRoot(element);
ReactDOM.Client.render(, root);
}
}
```
--------------------------------
### Handle Optional String with Switch or Belt.Option.getWithDefault
Source: https://reasonml.github.io/reason-react/docs/en/working-with-optional-data
This snippet illustrates two methods for handling optional strings in ReasonML. The first uses a 'switch' statement for explicit pattern matching, while the second uses Belt.Option.getWithDefault for a more concise approach to provide a fallback value.
```reasonml
/* create the type for the record, totally ok that it's the same name! */
type person = {
name: option(string)
};
let person = {
name: None
};
let label = switch(person.name) {
| Some(name) => name
| None => "Peter"
}
```
```reasonml
let label = Belt.Option.getWithDefault(person.name, "Peter");
```
--------------------------------
### ReasonReact Component with Children Prop
Source: https://reasonml.github.io/reason-react/docs/en/components
Demonstrates how to define and use a ReasonReact component that accepts and renders children. Children are treated as a regular prop, allowing for flexible composition of UI elements within components.
```reasonml
module ComponentTakesChildren = {
[@react.component]
let make = (~name, ~children) => {
{React.string("Hello, " ++ name)}
children
};
};
/* Usage Example */
{React.string("Effectively the child.")}
```
--------------------------------
### Import Basic Reason File into JavaScript
Source: https://reasonml.github.io/reason-react/docs/en/importing-reason-into-js
This snippet demonstrates how to import a basic Reason file (Greeting.re) that defines a React component into a JavaScript file (App.js). It assumes the Reason code is compiled to a named export. The input is a Reason React component, and the output is a JavaScript component that can render it.
```reason
/* Greeting.re */
[@react.component]
let make = (~name) => {React.string("Hey " ++ name)} ;
```
```javascript
/* App.js */
import { make as Greeting } from './Greeting.bs'
export default function App() {
return
}
```
--------------------------------
### Type-Safe GraphQL Query with graphql-ppx
Source: https://reasonml.github.io/reason-react/docs/en/graphql-apollo
This snippet demonstrates defining a type-safe GraphQL query using the %graphql syntax from graphql-ppx. The compiler validates the query against a graphql_schema.json file, preventing runtime errors. It shows a basic query for fetching the current user's name.
```reason
/* Username.re */
module UserQuery = [%graphql {|
query UserQuery {
currentUser {
name
}
}
|}];
```
--------------------------------
### ReasonReact Router API Reference
Source: https://reasonml.github.io/reason-react/docs/en/router
This snippet outlines the core functions provided by the ReasonReact router for managing navigation. It includes functions for pushing and replacing routes, watching URL changes, and accessing the initial URL.
```reason
ReasonReactRouter.push(string);
ReasonReactRouter.replace(string);
ReasonReactRouter.watchUrl(f);
ReasonReactRouter.unwatchUrl(watcherID);
ReasonReactRouter.dangerouslyGetInitialUrl();
ReasonReactRouter.useUrl(~serverUrl);
```
--------------------------------
### ReasonReact useEffect Hook Dependencies
Source: https://reasonml.github.io/reason-react/docs/en/components
Explains how React's `useEffect` hook is adapted in ReasonReact to handle dependencies using tuples for multiple arguments and specific functions like `useEffect2` or `useEffect0`. It highlights the difference for single dependencies requiring an array wrapper (`useEffect1`).
```reasonml
/* React: useEffect(effect, [dep1, dep2]) */
/* ReasonReact */
useEffect2(effect, (dep1, dep2))
/* React: useEffect(effect, []) */
/* ReasonReact */
useEffect0(effect)
/* ReasonReact for single dependency */
useEffect1(effect, [|dep|])
/* ReasonReact for empty or arbitrary length dependencies */
useEffect1(effect, [||])
```
--------------------------------
### Inline Styling with ReactDOM.Style.make
Source: https://reasonml.github.io/reason-react/docs/en/style
This snippet demonstrates how to apply inline styles to a div element using ReasonReact's ReactDOM.Style.make API. It maps labeled arguments to a familiar style object and returns an opaque ReactDOM.style type.
```reasonml
```
--------------------------------
### Create and Provide Context in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/context
This snippet demonstrates how to create a React context and a corresponding provider component in ReasonReact. The context is defined using `React.createContext`, and the provider is created using `React.Context.provider`. This allows you to pass data through the component tree without prop drilling.
```reason
/** as a separate file: ContextProvider.re */
// 1. The context itself
let themeContext = React.createContext("light");
// 2. The provider
include React.Context; // Adds the makeProps external
let make = React.Context.provider(themeContext);
```
```reason
/** or inside any other module */
// 1. The context itself
let themeContext = React.createContext("light");
// 2. The provider component
module ContextProvider = {
include React.Context; // Adds the makeProps external
let make = React.Context.provider(themeContext);
};
```
--------------------------------
### ReasonReact ReactDOMServer: Render to String
Source: https://reasonml.github.io/reason-react/docs/en/dom
Uses ReasonReact's ReactDOMServer module to render a React element into an HTML string. This is useful for server-side rendering, providing a static markup representation of the component.
```reason
ReactDOMServer.renderToString()
```
--------------------------------
### ReasonReact ReactDOMServer: Render to Static Markup
Source: https://reasonml.github.io/reason-react/docs/en/dom
Uses ReasonReact's ReactDOMServer module to render a React element into a static HTML string without extra attributes. This is ideal for server-side rendering when you don't need React's hydration capabilities on the client.
```reason
ReactDOMServer.renderToStaticMarkup()
```
--------------------------------
### Handle Default Props in JavaScript Components for ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/importing-js-into-reason
Explains how to manage default props for JavaScript components when integrating with ReasonReact. This includes scenarios where the JS component already has default props defined or when a default needs to be added in ReasonReact.
```javascript
function Greeting({
name
}) {
return Hey {name}
};
Greeting.defaultProps = {
name: "John"
};
```
```reason
module Greeting = {
[@mel.module "./Greeting.js"] [@react.component]
external make: (~name: string=?) => React.element = "default";
};
```
```reason
module GreetingJs = {
[@mel.module "./Greeting.js"] [@react.component]
external make: (~name: string) => React.element = "default";
};
module Greeting = {
[@react.component]
let make = (~name="Peter") => ;
};
```
--------------------------------
### Conditional Rendering with Optional Data in React
Source: https://reasonml.github.io/reason-react/docs/en/working-with-optional-data
This code demonstrates how to conditionally render a React component based on whether an optional value exists. It uses a 'switch' statement to render a specific component when the value is 'Some' and React.null when it's 'None'.
```reasonml
;
```
--------------------------------
### Pushing a New Route in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/router
Shows how to programmatically navigate to a new URL within a ReasonReact application using `ReasonReactRouter.push`. This function updates the browser's URL without a full page reload, triggering re-renders for components using `useUrl`.
```reason
ReasonReactRouter.push("/books/10/edit#validated");
// If updating URL outside of Router.push:
// window.dispatchEvent(new Event('popState'));
```
--------------------------------
### ReasonML Component for ReactJS
Source: https://reasonml.github.io/reason-react/docs/en/js-using-reason
Defines a ReasonML component 'PageReason' that can be used within a ReactJS application. It takes a 'message' and an optional 'extraGreeting' as props. The component renders a 'MyBannerRe' component with a combined greeting message.
```reasonml
/* ReasonReact used by ReactJS */
[@react.component]
let make = (~message, ~extraGreeting=?)
=> {
let greeting =
switch (extraGreeting) {
| None => "How are you?"
| Some(g) => g
};
;
};
```
--------------------------------
### Children as Render Props with ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/render-props
Illustrates using children as render props in ReasonReact. The Loader component accepts a children function that receives data and renders it.
```reasonml
[@react.component]
let make = (~children) => {
{person =>
{React.string(person.name)}
}
;
};
```
```reasonml
/* Loader.re */
[@react.component]
let make = (~children) => {
let person = {name: "Peter"};
{children(person)}
;
};
```
--------------------------------
### Manual JavaScript Component Import (without @react.component)
Source: https://reasonml.github.io/reason-react/docs/en/components
This snippet illustrates the desugared version of importing a JavaScript component without the [@react.component] annotation. It shows the explicit definition of 'makeProps' for handling labeled arguments and 'make' for the React element, along with module and default export specifications.
```reason
[@mel.obj]
external makeProps: (~name: 'name, ~key: string=?, unit) => {. "name": 'name} = "";
[@mel.module "./path/to/Component.js"]
external make: ({. "name": string}) => React.element = "default";
```
--------------------------------
### Adding Unsafe Style Properties with unsafeAddProp
Source: https://reasonml.github.io/reason-react/docs/en/style
This snippet shows how to use the ReactDOM.Style.unsafeAddProp function to add a style property that might not be recognized by the standard type checker. It takes an existing style, a property name, and its value, returning a new style object.
```reasonml
let myStyle = ReactDOM.Style.make(~color="#444444", ~fontSize="68px", ());
let newStyle = ReactDOM.Style.unsafeAddProp(myStyle, "width", "10px");
```
--------------------------------
### ReasonReact Fragment Transformation
Source: https://reasonml.github.io/reason-react/docs/en/jsx
Explains how ReasonReact transforms the shorthand fragment syntax `<>>` into JavaScript calls using React.jsx with `React.Fragment` and handling children.
```reason
<> child1 child2 >
```
```javascript
React.jsx(
React.jsxFragment,
ReactDOM.domProps(~children=React.array([|child1, child2|]), ()),
)
```
```javascript
React.jsx(React.Fragment, { children: [child1, child2] });
```
--------------------------------
### Import Reason Component as Default Export
Source: https://reasonml.github.io/reason-react/docs/en/importing-reason-into-js
This snippet shows how to import a Reason React component into JavaScript by setting the Reason component as the default export. This allows for a cleaner import statement in the JavaScript file. The input is a Reason React component explicitly set as default, and the output is a JavaScript component leveraging this default export.
```reason
/* Greeting.re */
[@react.component]
let make = (~name) => {React.string("Hey " ++ name)} ;
/* this sets the named export to default */
let default = make;
```
```javascript
/* App.js */
import Greeting from './Greeting.bs'
export default function App() {
return
}
```
--------------------------------
### Access Optional Nested Data with Belt.Array.getBy
Source: https://reasonml.github.io/reason-react/docs/en/working-with-optional-data
This snippet demonstrates how to retrieve an element from an array based on a condition using ReasonML's Belt.Array.getBy. The result is an optional value, which may require further handling.
```reasonml
let selected = colors->Belt.Array.getBy(c => c##id === id);
```
```javascript
const selected = colors.find(c => c.id === id);
```
--------------------------------
### ReasonReact useState Hook Initial Value
Source: https://reasonml.github.io/reason-react/docs/en/components
Illustrates the safe usage of the `React.useState` hook in ReasonReact. Unlike JavaScript React, ReasonReact enforces the use of a function to provide the initial state, ensuring safety across all scenarios.
```reasonml
let (count, setCount) = React.useState(() => 0);
```
--------------------------------
### ReasonReact Component Definition
Source: https://reasonml.github.io/reason-react/docs/en/components
Defines a basic ReasonReact component using function syntax and React Hooks. It includes state management with `React.useState` and renders UI elements with embedded strings and event handlers. This is the primary way to write components in ReasonReact.
```reasonml
[@react.component]
let make = (~name) => {
let (count, setCount) = React.useState(() => 0);
};
```
--------------------------------
### Import Javascript file into ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/importing-js-into-reason
Demonstrates how to import a JavaScript file as a React component into ReasonReact. It requires the use of the [@mel.module] attribute to specify the path to the JavaScript file and [@react.component] to denote it as a React component.
```javascript
/* MyJavascriptFile.js */
export default function Greeting({ name }) {
return Hey {name}
}
```
```reason
/* App.re */
module Greeting = {
[@mel.module "./MyJavascriptFile.js"] [@react.component]
external make: (~name: string) => React.element = "default";
};
let make = () =>
;
```
--------------------------------
### Create DOM Element with Variable Tag in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/i-want-to-create-a-dom-element-without-jsx
Illustrates how to dynamically create DOM elements in ReasonReact by first assigning a string tag, converted to a component using ReactDOM.stringToComponent, to a variable. This variable can then be passed to React.createElement.
```reasonml
let tag = ReactDOM.stringToComponent(multiline ? "textarea" : "input");
React.createElement(tag, /* ... */)
```
--------------------------------
### Export Reason React Component to JavaScript
Source: https://reasonml.github.io/reason-react/docs/en/components
This snippet shows how to use a Reason React component (exported as 'make') within JavaScript code. It assumes the component is available via a CommonJS require.
```javascript
const MyComponent = require('./path/to/Component.js').make;
```
--------------------------------
### Handle Invalid Prop Names in ReasonReact
Source: https://reasonml.github.io/reason-react/docs/en/invalid-prop-name
Reason/OCaml keywords like `type`, `as`, `open`, `begin`, `end`, `in`, and `to` are invalid as prop names. ReasonReact requires appending an underscore (e.g., `type_`, `as_`) for DOM elements. For `aria-*` and `data-*` attributes, specific casing and handling are recommended.
```reason
let example = ;
let anotherExample = ;
```
--------------------------------
### ReasonReact @react.component Decorator Explanation
Source: https://reasonml.github.io/reason-react/docs/en/components
Illustrates how the `[@react.component]` decorator transforms a ReasonReact component definition into a JavaScript-compatible function. It generates a `makeProps` function for handling named arguments as a JavaScript object, which is how React expects props.
```reasonml
/* This is the generated code structure */
[@mel.obj]
external makeProps: (~name: 'name, ~key: string=?, unit) => {. "name": 'name} = "";
let make = (Props) => {
let name = Props##name;
let (count, setCount) = React.useState(() => 0);
};
```
--------------------------------
### ReasonReact ReactDOM: Hydration
Source: https://reasonml.github.io/reason-react/docs/en/dom
Performs hydration, converting a static HTML page into a dynamic React app using ReasonReact's ReactDOM module. It selects a root DOM element and uses `ReactDOM.hydrateRoot` to attach React event listeners to the existing HTML.
```reason
let element = ReactDOM.querySelector("#root");
switch (element) {
| None => Js.log("#root element not found");
| Some(element) => {
/* root is a ReactDOM.Client.root and used to render on top of the existing HTML
with ReactDOM.Client.render or unmount, via ReactDOM.Client.unmount. */
let _root = ReactDOM.hydrateRoot(, element);
();
}
}
```
--------------------------------
### ReasonReact JSX to JavaScript Transformation (Prop-less Capitalized)
Source: https://reasonml.github.io/reason-react/docs/en/jsx
Details the transformation of a prop-less capitalized JSX element, showing how it compiles to a JavaScript call using React.jsx with the component's `make` function.
```reason
```
```javascript
React.jsx(
MyReasonComponent.make,
MyReasonComponent.makeProps(),
)
```
```javascript
React.jsx(MyReasonComponent.make, {})
```
--------------------------------
### Import JavaScript Component into Reason React
Source: https://reasonml.github.io/reason-react/docs/en/components
This demonstrates how to import a default-exported JavaScript component into Reason React using an 'external' declaration. The [@mel.module] attribute specifies the file path, and [@react.component] helps generate the necessary props and component functions.
```reason
[@mel.module "./path/to/Component.js"] [@react.component]
external make: (~name: string) => React.element = "default";
```
--------------------------------
### ReasonReact useState Hook Signature
Source: https://reasonml.github.io/reason-react/docs/en/usestate-hook
The signature for the `useState` hook in ReasonReact. It takes a function that returns the initial state and returns a tuple containing the current state and a function to update it. This differs from React.js by requiring a function for the initial state.
```reasonml
let useState: (unit => 'state) => ('state, 'state => unit);
```
--------------------------------
### ReasonReact JSX to JavaScript Transformation (Capitalized)
Source: https://reasonml.github.io/reason-react/docs/en/jsx
Illustrates the transformation of capitalized JSX elements (custom components) into ReasonReact's JavaScript output. It handles props, children, and the use of `make` and `makeProps` functions.
```reason
{child1} {child2}
```
```javascript
React.jsxs(
MyReasonComponent.make,
MyReasonComponent.makeProps(
~ref=b,
~foo=bar,
~baz=qux,
~children=[|child1, child2|],
()
),
)
```
```javascript
React.jsxs(
MyReasonComponent.make,
{
ref: b,
foo: bar,
baz: qux,
children: [ child1, child2 ],
},
)
```
--------------------------------
### ReasonReact useReducer Hook Implementation
Source: https://reasonml.github.io/reason-react/docs/en/usereducer-hook
This snippet demonstrates the implementation of the `useReducer` hook in ReasonReact. It defines an action type with two cases (Increment and Decrement) and a reducer function to manage state updates. The `make` component utilizes `React.useReducer` to handle state and dispatch actions, rendering the current state and buttons to trigger state changes.
```reasonml
/* we can create anything as the type for action, here we use a variant with 2 cases. */
type action =
| Increment
| Decrement;
/* `state` could also be anything. In this case, we want an int */
let reducer = (state, action) =>
switch (action) {
| Increment => state + 1
| Decrement => state - 1
};
[@react.component]
let make = (~initialValue=0) => {
let (state, dispatch) = React.useReducer(reducer, initialValue);
state->React.int
;
};
```
--------------------------------
### ReasonReact JSX to JavaScript Transformation (Prop-less Uncapitalized)
Source: https://reasonml.github.io/reason-react/docs/en/jsx
Shows the transformation of a prop-less uncapitalized JSX element (``) into JavaScript, using ReactDOM.jsx and compiling to React.createElement.
```reason
```
```javascript
ReactDOM.jsx("div", ReactDOM.domProps());
```
```javascript
React.createElement('div', {})
```
--------------------------------
### ReasonReact Rendering Primitives
Source: https://reasonml.github.io/reason-react/docs/en/components
Shows how to explicitly render different data types like strings, integers, floats, arrays, and null within a ReasonReact component's JSX. Specific functions like `React.string`, `React.int`, `React.float`, and `React.array` are used for type safety.
```reasonml
```
--------------------------------
### Create DOM Element with React.createElement (JavaScript)
Source: https://reasonml.github.io/reason-react/docs/en/i-want-to-create-a-dom-element-without-jsx
Demonstrates the JavaScript approach to creating DOM elements using React.createElement, where a string can represent a DOM tag. This is useful when the tag needs to be determined dynamically.
```javascript
React.createElement(multiline ? "textarea" : "input" /* ... */);
```
--------------------------------
### ReasonReact JSX to JavaScript Transformation (Uncapitalized)
Source: https://reasonml.github.io/reason-react/docs/en/jsx
Demonstrates how ReasonReact's ppx transforms uncapitalized JSX elements into JavaScript calls using ReactDOM.jsxs and ReactDOM.domProps, and its compiled output. It handles nested children and prop transformations.
```reason
{child1} {child2}
```
```javascript
ReactDOM.jsxs(
"div",
ReactDOM.domProps(
~children=React.array([|child1, child2|]),
~foo=bar,
(),
)
)
```
```javascript
React.jsx('div', {foo: bar, children: [ child1, child2 ] })
```
--------------------------------
### React.js Input Change Handler
Source: https://reasonml.github.io/reason-react/docs/en/usestate-hook
A standard React.js component demonstrating how to handle input changes using the `useState` hook. It directly accesses the event target value within the `onChange` handler.
```javascript
/* App.js */
function App() {
const [name, setName] = React.useState("John");
return (
setName(event.target.value)}
/>
);
}
```
--------------------------------
### Correct ReasonReact Input Change Handler with useState
Source: https://reasonml.github.io/reason-react/docs/en/usestate-hook
The corrected ReasonReact implementation for handling input changes. It resolves the bug by extracting the event's value into a local variable *before* calling the state setter function, ensuring the value is available when needed.
```reasonml
/* App.re */
/* CORRECT! This code is bug-free. 👍 */
[@react.component]
let make = () => {
let (name, setName) = React.useState(() => "John");
{
let value = React.Event.Form.target(event)##value;
setName(_ => value)
}
}
/>;
};
```