サーバを使わず、htmlファイルをダブルクリックして、Material UIの画面を表示をやってみました。
参考)
https://qiita.com/murasuke/items/e0600497a8900ca8401b
上記サイトでReact+TypeScriptでカウントアップするデモを引用させていただきます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
<!DOCTYPE html> <head> <meta charset="utf-8"> <title>React tsx-esm-standalone</title> <script src="https://unpkg.com/@babel/standalone/babel.min.js"></script> <script> Babel.registerPreset('tsx', { presets: [ [Babel.availablePresets['typescript'], {allExtensions: true, isTSX: true} ]], }, ); </script> <script type="text/babel" data-type="module" data-presets="tsx,react"> import React, { useState } from "https://cdn.skypack.dev/react@17"; import ReactDOM from "https://cdn.skypack.dev/react-dom@17"; const Counter: React.Component = () => { const [count, setCount] = React.useState<number>(0); const handleClick = () => setCount(n => n + 1); return ( <div> <div>Count: {count}</div> <button onClick={handleClick}>Increment</button> </div> ); } ReactDOM.render(<Counter />, document.getElementById('app')); </script> </head> <body> <div id="app"></div> </body> </html> |
よくあるカウントアップの動作確認ができました。
次に、Material UIを使おうとしましたが、 skypackではうまくいきませんでした。(多分私のやり方がまずい)
そこでMUIがうまく表示できる例を見つけました。引用させていただきます。
参考)
https://github.com/skypackjs/skypack-cdn/issues/233
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
<!doctype html> <html> <head> <meta charset="utf-8"> <script src="https://unpkg.com/react@17.0.2/umd/react.development.js"></script> <script src="https://unpkg.com/react-dom@17.0.2/umd/react-dom.development.js"></script> <script src="https://unpkg.com/@mui/material@5.0.6/umd/material-ui.development.js"></script> <script type="module"> const { Button, TextField } = MaterialUI; const e = React.createElement; ReactDOM.render( e(Button, {variant: 'contained', color: 'primary'}, 'Button'), // e(TextField), document.getElementById('root') ); </script> </head> <body> <div id="root"></div> </body> </html> |
コード
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
<script src="https://unpkg.com/react@18/umd/react.development.js"></script> <script src="https://unpkg.com/react-dom@18/umd/react-dom.development.js"></script> <script src="https://unpkg.com/babel-standalone@6/babel.min.js"></script> <script src="https://unpkg.com/@mui/material@5.0.6/umd/material-ui.development.js"></script> <div id="root"></div> <script type="text/babel"> const {useState, useCallback} = React; const {Button, TextField} = MaterialUI; function MyApp() { const [count, setCount] = useState(0) const increment = useCallback(() => setCount((n) => n + 1), [setCount] ) const decrement = () => { let n = count setCount(n-1) } return (<div> <h3>Hello! {count}</h3> <Button variant='contained' color='primary' onClick={increment} >Increment</Button> <Button variant='contained' color='primary' onClick={decrement} >Decrement</Button> </div>) } const container = document.getElementById('root'); const root = ReactDOM.createRoot(container); root.render(<MyApp />); </script> |
increment/decrement はあえてロジックを変えてみました。
ここからもう一つユーザファイルをCORS制約で読むことはできないため、サーバが必要です。
scriptタグで読み込むreactはnode module形式でimportできないためESModule版を使うということ、npmパッケージをESModuleにしてくれるサービスhttps://cdn.skeypack.dev があること、勉強になりました。