Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 29 additions & 11 deletions pages/docs/manual/v11.0.0/jsx.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -353,6 +353,8 @@ Below is a full list of everything you need in a generic JSX transform module, i

> You can easily copy-paste-and-adapt this to your needs if you're creating bindings to a JSX framework. Most often, all you'll need to change is what the `@module("") external` points to, so the runtime calls point to the correct JS module.

<CodeTab labels={["ReScript"]}>

```rescript
// Preact.res
/* Below is a number of aliases to the common `Jsx` module */
Expand All @@ -362,16 +364,16 @@ type component<'props> = Jsx.component<'props>

type componentLike<'props, 'return> = Jsx.componentLike<'props, 'return>

@module("preact")
@module("preact/jsx-runtime")
external jsx: (component<'props>, 'props) => element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxKeyed: (component<'props>, 'props, ~key: string=?, @ignore unit) => element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxs: (component<'props>, 'props) => element = "jsxs"

@module("preact")
@module("preact/jsx-runtime")
external jsxsKeyed: (component<'props>, 'props, ~key: string=?, @ignore unit) => element = "jsxs"

/* These identity functions and static values below are optional, but lets
Expand All @@ -383,37 +385,53 @@ external array: array<element> => element = "%identity"
external float: float => element = "%identity"
external int: int => element = "%identity"
external string: string => element = "%identity"
external promise: promise<element> => element = "%identity"

/* These are needed for Fragment (<> </>) support */
type fragmentProps = {children?: element}

@module("preact") external jsxFragment: component<fragmentProps> = "Fragment"
@module("preact/jsx-runtime") external jsxFragment: component<fragmentProps> = "Fragment"

/* The Elements module is the equivalent to the ReactDOM module in React. This holds things relevant to _lowercase_ JSX elements. */
/* The Elements module is the equivalent to the ReactDOM module in Preact. This holds things relevant to _lowercase_ JSX elements. */
module Elements = {
/* Here you can control what props lowercase JSX elements should have.
A base that the React JSX transform uses is provided via JsxDOM.domProps,
but you can make this anything. The editor tooling will support
autocompletion etc for your specific type. */
type props = JsxDOM.domProps

@module("preact")
@module("preact/jsx-runtime")
external jsx: (string, props) => Jsx.element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external div: (string, props) => Jsx.element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxKeyed: (string, props, ~key: string=?, @ignore unit) => Jsx.element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxs: (string, props) => Jsx.element = "jsxs"

@module("preact")
@module("preact/jsx-runtime")
external jsxsKeyed: (string, props, ~key: string=?, @ignore unit) => Jsx.element = "jsxs"

external someElement: element => option<element> = "%identity"
}
```

</CodeTab>

As you can see, most of the things you'll want to implement will be copy paste from the above. But do note that **everything needs to be there unless explicitly noted** or the transform will fail at compile time.

To enable this, you need to configure the `jsx` `module` in your `rescript.json`:

```json
{
"jsx": {
"version": 4,
"module": "Preact"
}
}
```

_value "Preact" is the name of the module that implements the generic JSX transform._
40 changes: 29 additions & 11 deletions pages/docs/manual/v12.0.0/jsx.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -353,6 +353,8 @@ Below is a full list of everything you need in a generic JSX transform module, i

> You can easily copy-paste-and-adapt this to your needs if you're creating bindings to a JSX framework. Most often, all you'll need to change is what the `@module("") external` points to, so the runtime calls point to the correct JS module.

<CodeTab labels={["ReScript"]}>

```rescript
// Preact.res
/* Below is a number of aliases to the common `Jsx` module */
Expand All @@ -362,16 +364,16 @@ type component<'props> = Jsx.component<'props>

type componentLike<'props, 'return> = Jsx.componentLike<'props, 'return>

@module("preact")
@module("preact/jsx-runtime")
external jsx: (component<'props>, 'props) => element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxKeyed: (component<'props>, 'props, ~key: string=?, @ignore unit) => element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxs: (component<'props>, 'props) => element = "jsxs"

@module("preact")
@module("preact/jsx-runtime")
external jsxsKeyed: (component<'props>, 'props, ~key: string=?, @ignore unit) => element = "jsxs"

/* These identity functions and static values below are optional, but lets
Expand All @@ -383,37 +385,53 @@ external array: array<element> => element = "%identity"
external float: float => element = "%identity"
external int: int => element = "%identity"
external string: string => element = "%identity"
external promise: promise<element> => element = "%identity"

/* These are needed for Fragment (<> </>) support */
type fragmentProps = {children?: element}

@module("preact") external jsxFragment: component<fragmentProps> = "Fragment"
@module("preact/jsx-runtime") external jsxFragment: component<fragmentProps> = "Fragment"

/* The Elements module is the equivalent to the ReactDOM module in React. This holds things relevant to _lowercase_ JSX elements. */
/* The Elements module is the equivalent to the ReactDOM module in Preact. This holds things relevant to _lowercase_ JSX elements. */
module Elements = {
/* Here you can control what props lowercase JSX elements should have.
A base that the React JSX transform uses is provided via JsxDOM.domProps,
but you can make this anything. The editor tooling will support
autocompletion etc for your specific type. */
type props = JsxDOM.domProps

@module("preact")
@module("preact/jsx-runtime")
external jsx: (string, props) => Jsx.element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external div: (string, props) => Jsx.element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxKeyed: (string, props, ~key: string=?, @ignore unit) => Jsx.element = "jsx"

@module("preact")
@module("preact/jsx-runtime")
external jsxs: (string, props) => Jsx.element = "jsxs"

@module("preact")
@module("preact/jsx-runtime")
external jsxsKeyed: (string, props, ~key: string=?, @ignore unit) => Jsx.element = "jsxs"

external someElement: element => option<element> = "%identity"
}
```

</CodeTab>

As you can see, most of the things you'll want to implement will be copy paste from the above. But do note that **everything needs to be there unless explicitly noted** or the transform will fail at compile time.

To enable this, you need to configure the `jsx` `module` in your `rescript.json`:

```json
{
"jsx": {
"version": 4,
"module": "Preact"
}
}
```

_value "Preact" is the name of the module that implements the generic JSX transform._
30 changes: 28 additions & 2 deletions src/components/CodeExample.res
Original file line number Diff line number Diff line change
Expand Up @@ -104,24 +104,49 @@ module CopyButton = {
}

@react.component
let make = (~highlightedLines=[], ~code: string, ~showLabel=true, ~lang="text") => {
let make = (
~highlightedLines=[],
~code: string,
~showLabel=true,
~lang="text",
~showCopyButton=false,
) => {
let children = HighlightJs.renderHLJS(~highlightedLines, ~code, ~lang, ())

let label = if showLabel {
let label = langShortname(lang)
let rightPosition = if showCopyButton {
"right-8" // Move label left when copy button is present
} else {
"right-1"
}
let topPosition = if showCopyButton {
"top-1"
} else {
"top-0"
}
<div
className="absolute right-1 top-0 p-1 font-sans text-12 font-bold text-gray-30 pointer-events-none">
className={`absolute ${rightPosition} ${topPosition} p-1 font-sans text-12 font-bold text-gray-30 pointer-events-none`}>
{//RES or JS Label
String.toUpperCase(label)->React.string}
</div>
} else {
React.null
}

let copyButton = if showCopyButton {
<div className="absolute right-1 top-0 p-1">
<CopyButton code />
</div>
} else {
React.null
}

<div
//normal code-text without tabs
className="relative w-full flex-col rounded xs:rounded border border-gray-20 bg-gray-10 pt-2 text-gray-80">
label
copyButton
<div className="px-5 text-14 pt-4 pb-4 overflow-x-auto whitespace-pre"> children </div>
</div>
}
Expand All @@ -145,6 +170,7 @@ module Toggle = {
code: tab.code,
lang: ?tab.lang,
showLabel: true,
showCopyButton: true,
})
| multiple =>
let numberOfItems = Array.length(multiple)
Expand Down
1 change: 1 addition & 0 deletions src/components/CodeExample.resi
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ let make: (
~code: string,
~showLabel: bool=?,
~lang: string=?,
~showCopyButton: bool=?,
) => React.element

module Toggle: {
Expand Down