React公式ドキュメントを読む17 if文でレンダリングし分ける

前回からの続きですが、このページだけ読んでも分かる内容になっています。 今回読むReact公式ドキュメントは「条件付きレンダー」ページの前半です。

Reactで条件によってレンダリング内容を変えたい場合、if文を使った分岐が一般的かもしれません。このページでは、if文による分岐でレンダリングし分ける場合のコード書き方を紹介します。

if文で条件分岐する

ユーザーがログインしているかどうかで表示し分ける

ユーザーがログインしているかどうかで表示し分ける場合を考えてみましょう。ログインしていれば「おかえりなさい!」、ログインしていなければ「ログインしてください。」と表示するものとします。

以下のコードは、isLoggedInの値が true か false かによって表示を切り替えるプログラムになっています。

function UserGreeting(props) {
  return <h1>おかえりなさい!</h1>;
}

function GuestGreeting(props) {
  return <h1>ログインしてください。</h1>;
}

function Greeting(props) {
  const isLoggedIn = props.isLoggedIn;
  if (isLoggedIn) {
    return <UserGreeting />;
  }
  return <GuestGreeting />;
}

ReactDOM.render(
  // trueに変更すると表示が切り替わります
  <Greeting isLoggedIn={false} />,
  document.getElementById('root')
);

上記のサンプルソースをHTMLファイルにしたものが以下です。

https://programming-world.net/sample/react_doc/conditional-rendering1-1.html

上記のコードでは、UserGreetingとGuestGreetingの2つのコンポーネントを用意しておいて、isLoggedInの内容次第で呼び出すコンポーネントを振り分けています。

上記のコードは完成形ではないので、必ず「ログインしてください。」が表示されます。コードをisLoggedIn = {true}に変更すると「おかえりなさい!」に表示が 切り替わります。

ログインボタンとログアウトボタンを設置する

次に、ログインボタンとログアウトボタンを設置してみましょう。

class LoginControl extends React.Component {
  // コンストラクタ
  constructor(props) {
	super(props);

  // メソッドをバインド
	this.handleLoginClick = this.handleLoginClick.bind(this);
	this.handleLogoutClick = this.handleLogoutClick.bind(this);

  // isLoggedIn の値を false にして初期化
	this.state = {isLoggedIn: false};
  }

  // クラスメソッド
  handleLoginClick() {
	this.setState({isLoggedIn: true});
  }

  // クラスメソッド
  handleLogoutClick() {
	this.setState({isLoggedIn: false});
  }

  // レンダリング
  render() {
    // 変数 isLoggedIn を宣言して state を代入
    const isLoggedIn = this.state.isLoggedIn;

    // 変数 button を宣言
    let button;

    // isLoggedIn が true か false かで代入する要素を振り分ける
    if (isLoggedIn) {
      button = <LogoutButton onClick={this.handleLogoutClick} />;
    } else {
      button = <LoginButton onClick={this.handleLoginClick} />;
    }

    /*
    以下の <Greeting isLoggedIn={isLoggedIn} /> の部分は、
    Greeting コンポーネントにisLoggedInを渡すことで、
    Greeting コンポーネントのif文で分岐した値が返ります。
    つまり、<UserGreeting /> か <GuestGreeting /> の一方を表示します。

    その下の {button} の部分は、
    変数 button に代入されている内容を表示します。
    つまり、<LoginButton /> か <LogoutButton /> の一方を表示します。
    */
    return (
      <div>
        <Greeting isLoggedIn={isLoggedIn} />
        {button}
      </div>
    );
  }
}

function UserGreeting(props) {
  return <h1>おかえりなさい!</h1>;
}

function GuestGreeting(props) {
  return <h1>ログインしてください。</h1>;
}

// isLoggedIn が true か false かで返す値を振り分ける
function Greeting(props) {
  const isLoggedIn = props.isLoggedIn;
  if (isLoggedIn) {
	return <UserGreeting />;
  }
  return <GuestGreeting />;
}


function LoginButton(props) {
  return (
	<button onClick={props.onClick}>
	  ログイン
	</button>
  );
}

function LogoutButton(props) {
  return (
	<button onClick={props.onClick}>
	  ログアウト
	</button>
  );
}

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

上記のサンプルソースをHTMLファイルにしたものが以下です。

https://programming-world.net/sample/react_doc/conditional-rendering1-2.html

上記コードでは、LoginControlというコンポーネントを作成して、そのなかでisLoggedInという state によって、ログインしているかどうかを管理しています。

Reactでは変数に要素を代入できるので、button という変数に要素を代入して扱いやすくしています。 [ログイン] [ログアウト]ボタンは、現在の state をもとに <LoginButton /> または <LogoutButton /> の一方を呼び出すことで表示し分けています。

また、「おかえりなさい!」「ログインしてください。」という挨拶メッセージは、Greetingコンポーネントのなかのif文で分岐して、<UserGreeting />または<GuestGreeting />の一方を呼び出すことで表示し分けています。

次回へ続きます。