2021-08-23
A while ago, I wrote a short post showing a minimal 33 line React. A lot of the comments focused on the Mithril-like syntax for the virtual DOM. So that we can ignore that aspect, here is a 96 line React with a JSX compiler.
We're going to make this noughts and crosses game:
Now let's look at the code, you can also just view the page source if you want.
let currentPlayer = "o"
let winner = null
const g = [
["", "", ""],
["", "", ""],
["", "", ""],
]
const move = (value, i, j) => {
// ... game logic goes here
renderNoughts()
}
const Cell = ({ value, i, j }) => (
<button class="cell" onclick={() => move(value, i, j)}>
{value}
</button>
)
const Noughts = () => (
<div>
{winner ? <marquee>winner: {winner}</marquee> : <h3>current player: {currentPlayer}</h3>}
<table>
{g.map((row, i) => (
<tr>
{row.map((value, j) => (
<td class={value}>
<Cell value={value} i={i} j={j} />
</td>
))}
</tr>
))}
</table>
</div>
)
const renderNoughts = () => m.render(document.getElementById("noughts"), { children: [Noughts()] })
renderNoughts()
You can read the bread-and-butter of how it works in the original post, the only difference is, rather than use the simpler hyperscript syntax, we compile any <script type="text/jsx">
scripts to plain ol' Javascript with m.parseJsx(source)
.
So for example:
const Cell = ({ value, i, j }) => (
<button class="cell" onclick={() => move(value, i, j)}>
{value}
</button>
)
Gets compiled to:
const Cell = ({ value, i, j }) => (
m("button", {"class": "cell", "onclick": () => move(value, i, j), }, " ", value, " ")
)
<
not followed by an equals sign or a space. I'm not sure what proper JSX compilers do.