MSBOOKS

プログラミングとか深層学習とか日常の出来事とか

【勉強メモ】Reactのチュートリアルを試してみた その1

はじめに

前回の.net coreに続いて仕事でReact勉強しといて!っていわれたのでreact公式のチュートリアルをやってみます。java scriptとhtmlの知識は当然のように必要だそう…。今回は概要編をやってみます。コードはブラウザでできるものを利用しました→
https://codepen.io/gaearon/pen/oWWQNa?editors=0010

ja.reactjs.org

React とは?

React はユーザインターフェイスを構築するための、宣言型で効率的で柔軟な JavaScript ライブラリだそうで、基本的な文法はjava scriptっぽいです。複雑な UI を、「コンポーネント」と呼ばれる小さく独立した部品から組み立てることができるのが特徴だそう。javaのクラスのUI版ってイメージでしょうか。そのコンポーネントの中のReact.componetから勉強が始まります。

class ShoppingList extends React.Component {
  render() {
    return (
      <div className="shopping-list">
        <h1>Shopping List for {this.props.name}</h1>
        <ul>
          <li>Instagram</li>
          <li>WhatsApp</li>
          <li>Oculus</li>
        </ul>
      </div>
    );
  }
}

// Example usage: <ShoppingList name="Mark" />

コンポーネントは、React に”何を描画したいか”を伝えます。データが変更されると、React はコンポーネントを効率よく更新して再レンダーします。と書いており、つまりデータが更新されたときの再表示が効率よく行えるということでしょうか。

ここで ShoppingList は React コンポーネントクラスです。コンポーネントprops(“properties” の略)と呼ばれるパラメータを受け取りrender メソッドを通じて、表示するビューの階層構造を返します。
render メソッドが返すのはあなたが画面上に表示したいものの説明書きです。React はその説明書きを受け取って画面に描画します。具体的には、render は、描画すべきものの軽量な記述形式である React 要素というものを返します。たいていの React 開発者は、これらの構造を簡単に記述できる “JSX” と呼ばれる構文を使用しています。htmlがreact要素に変換されるイメージですかね。

JSX では JavaScript のすべての能力を使うことができます。どのような JavaScript の式も JSX 内で中括弧に囲んで記入することができます。各 React 要素は、変数に格納したりプログラム内で受け渡ししたりできる、JavaScript のオブジェクトです。
それぞれの React のコンポーネントカプセル化されており独立して動作します。これにより単純なコンポーネントから複雑な UI を作成することができます。

まあいろいろ書いてあってわかりにくいですが、おそらく

スターターコードの中身を確認する

コードを見てみると、3 つの React コンポーネントがあります。HTMLをカプセル化したものが3つあるイメージですかね。

  • Square(正方形のマス目)
  • Board(盤面)
  • Game
class Square extends React.Component {
  render() {
    return (
      <button className="square">
        {/* TODO */}
      </button>
    );
  }
}

class Board extends React.Component {
  renderSquare(i) {
    return <Square />;
  }

  render() {
    const status = 'Next player: X';

    return (
      <div>
        <div className="status">{status}</div>
        <div className="board-row">
          {this.renderSquare(0)}
          {this.renderSquare(1)}
          {this.renderSquare(2)}
        </div>
        <div className="board-row">
          {this.renderSquare(3)}
          {this.renderSquare(4)}
          {this.renderSquare(5)}
        </div>
        <div className="board-row">
          {this.renderSquare(6)}
          {this.renderSquare(7)}
          {this.renderSquare(8)}
        </div>
      </div>
    );
  }
}

class Game extends React.Component {
  render() {
    return (
      <div className="game">
        <div className="game-board">
          <Board />
        </div>
        <div className="game-info">
          <div>{/* status */}</div>
          <ol>{/* TODO */}</ol>
        </div>
      </div>
    );
  }
}

// ========================================

ReactDOM.render(
  <Game />,
  document.getElementById('root')
);

見たところHTMLの要素がコンポーネントに分かれていて、オブジェクト指向HTMLのような見た目をしているよう。
Square(マス目)コンポーネントは 1 つの <button> をレンダーし、Board(盤面)が 9 個のマス目をレンダーしています。Boardクラスのという書き方がそれを示しているそうですね。関数を呼び出すイメージでしょうか。Game コンポーネントは盤面と、後ほど埋めるものらしい。

データを Props 経由で渡す

まずは以下のように変更するそうです。
・Boardコンポーネント

class Board extends React.Component {
  renderSquare(i) {
    return <Square value={i} />;
  }
}

・Squareコンポーネント

class Square extends React.Component {
  render() {
    return (
      <button className="square">
        {this.props.value}
      </button>
    );
  }
}

propsは先ほど引数みたいなイメージって言っていたやつですね。<Square value={i} />でSquareコンポーネントにpropsとしてvalueを渡しています。それをSquareコンポーネントがthis.props.valueでその中身を取り出していますね。これだとまるでSquareクラスにある見えないpublicなフィールドに外部から値を入れているようですね。
実行結果↓
f:id:msteacher:20210810155854p:plain

インタラクティブコンポーネントを作る

次にSquareコンポーネットがクリックされた場合にXが表示されるような変更をするそうです。
・Squareコンポーネント

class Square extends React.Component {
  render() {
    return (
      <button className="square" onClick={function() { alert('click'); }}>
        {this.props.value}
      </button>
    );
  }
}

これはよくあるクリックされたときにonClickが呼ばれてアラートが表示されるやつですね。ちなみにfunctionを省略した↓のような形がよく用いられるそうです。

<button className="square" onClick={() => alert('click')}>

コンポーネントが何かを「覚える」ためには、state というものを使います。javaで言うprivateのフィールドのイメージですね。
・Squareコンポーネント

class Square extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      value: null,
    };
  }

  render() {
    return (
      <button className="square" onClick={() => alert('click')}>
        {this.props.value}
      </button>
    );
  }
}

コンストラクターを使うところ本当にjavaっぽい。propsを受け取っていますが、propsがさっきの例の見えないpublicフィールドだとすれば、stateは見えるprivateフィールドで、オブジェクト指向の考え方であればこのstateを使うのがよさそう。this.stateにはフィールドの値を初期化しています。

・Squareコンポーネント

class Square extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      value: null,
    };
  }

  render() {
    return (
      <button
        className="square"
        onClick={() => this.setState({value: 'X'})}
      >
        {this.state.value}
      </button>
    );
  }
}

この変更では、onclickで呼ばれているものがSquareのフィールドにもつstateのvalueに'X'を代入していますね。先ほどはpropsからvalueを読みだしていましたが、button内の表示はstateのvalueに変更されています。これによってこのボタンを押したらstateの値がnullからXになるので、クリックされたところだけXが表示されるようになるんですね。
setState をコンポーネント内で呼び出すと、React はその内部の子コンポーネントも自動的に更新するそうで、setStateが再レンダー(表示の更新)の合図になっているんですね。実行結果は↓
f:id:msteacher:20210810162400p:plain

おわりに

Reactはhtml,javascirptをオブジェクト指向的な書き方ができるってイメージまでつかむことができるようになりました。複雑なwebページになればなるほど重宝しそうな書き方なので、さらに学んでいきたいと思いました。次回はゲームを完成させる部分をやってみたいと思います。それではまた。