LoginSignup
0
0

More than 3 years have passed since last update.

Azureみたいなウィザードっぽい入力フォームを作りたい Phase2 確認画面実装編(knockout.js使いこなせない)

Posted at

前の記事の続き。

フォームに入力した内容を、最後に確認画面で出すための実装に挑戦した。

↓こんな感じで入力すると
image.png
こうなる。名前はいま食べてるお菓子からそのまま流用した。
image.png

入力内容の連携にはknockout.jsを使った。data-bindってやつ。
knockout.jsはダウンロードして、フォルダ構成が以下になるように配置。

index.html(本記事のソースをコピペしただけのHTMLファイル)
AdminLTE-3.0.2(フォルダ)
css
img
js
plugins
knockout-3.5.1(フォルダ)
knockout-3.5.1.js

ソースは以下。(クリックするとソースが表示されます)
<!DOCTYPE html>
<html>

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <meta http-equiv="x-ua-compatible" content="ie=edge">

    <title>テストページ</title>

    <!-- Font Awesome Icons -->
    <link rel="stylesheet" href="AdminLTE-3.0.2/plugins/fontawesome-free/css/all.min.css">
    <!-- Theme style -->
    <link rel="stylesheet" href="AdminLTE-3.0.2/css/adminlte.min.css">
    <!-- Google Font: Source Sans Pro -->
    <link href="https://fonts.googleapis.com/css?family=Source+Sans+Pro:300,400,400i,700" rel="stylesheet">
</head>

<body>
<div class="split-input-form container-fluid">
    <div class="Title">分割入力フォーム</div>

    <div class="docking">
        <div class="docking-body p-3">
            <ul class="nav nav-tabs">
                <li class="nav-item">
                    <a href="#tab1-content" class="nav-link" data-toggle="tab">基本</a>
                </li>
                <li class="nav-item">
                    <a href="#tab2-content" class="nav-link" data-toggle="tab">住所</a>
                </li>
                <li class="nav-item">
                    <a href="#tab3-content" class="nav-link" data-toggle="tab">連絡先</a>
                </li>
                <li class="nav-item">
                    <a href="#tab4-content" class="nav-link" data-toggle="tab">確認</a>
                </li>
            </ul>
            <div class="tab-content">
                <div id="tab1-content" class="tab-pane active">
                    <div>
                        <span>基本の情報を入力します。</span>
                    </div>
                    <br />
                    <div class="font-weight-bold" style="margin: 10px 0px;">基本情報</div>
                    <div>
                        <span>あなたの名前と年齢を入力します。</span>
                    </div>
                    <br />
                    <div class="row form-group">
                        <label class="col-xl-1 d-flex align-items-center">
                            名前
                        </label>
                        <input type="text" data-bind="value: inputName, valueUpdate: 'input'" class="col-xl-11 form-control" id="InputName" placeholder="名前を入力" />
                    </div>
                    <br />
                    <div class="row form-group">
                        <label class="col-xl-1 d-flex align-items-center">
                            年齢
                        </label>
                        <input type="text" data-bind="value: inputAge, valueUpdate: 'input'" class="col-xl-11 form-control" id="InputAge" placeholder="年齢を入力" />
                    </div>
                </div>
                <div id="tab2-content" class="tab-pane">
                    <div>
                        <span>あなたの住所を入力します。</span>
                    </div>
                    <br />
                    <!-- general form elements -->
                    <div class="row form-group">
                        <label for="selectPrefectureLabel" class="col-xl-1 d-flex align-items-center">
                            都道府県
                        </label>
                        <select class="form-control" data-bind="options: prefItems, value: selectedPref" id="selectPrefecture"></select>
                    </div>
                    <br />
                    <div class="form-group">
                        <label for="selectAreaLabel" class="col-xl-1 d-flex align-items-center">
                            地域
                        </label>
                        <div class="custom-control custom-radio">
                            <input class="custom-control-input" data-bind="checked: inputArea" type="radio" id="AreaRadioWest" name="AreaRadio" checked="" value="どちらかというと西">
                            <label for="AreaRadioWest" class="custom-control-label">
                                どちらかというと西
                            </label>
                        </div>
                        <div class="custom-control custom-radio">
                            <input class="custom-control-input" data-bind="checked: inputArea" type="radio" id="AreaRadioEast" name="AreaRadio" value="どちらかというと東">
                            <label for="AreaRadioEast" class="custom-control-label">
                                どちらかというと東
                            </label>
                        </div>
                    </div>
                </div>
                <div id="tab3-content" class="tab-pane">
                    <div>
                        <span>希望する連絡手段を選んでください。(複数選択可能)</span>
                    </div>
                    <br />
                    <div class="form-group">
                        <div class="custom-control custom-checkbox">
                            <input class="custom-control-input" data-bind="checked: inputContact" type="checkbox" id="customboxMobile" value="携帯電話" />
                            <label for="customboxMobile" class="custom-control-label">
                                携帯電話
                            </label>
                        </div>
                        <div class="custom-control custom-checkbox">
                            <input class="custom-control-input" data-bind="checked: inputContact" type="checkbox" id="customboxPhone" value="固定電話" />
                            <label for="customboxPhone" class="custom-control-label">
                                固定電話
                            </label>
                        </div>
                        <div class="custom-control custom-checkbox">
                            <input class="custom-control-input" data-bind="checked: inputContact" type="checkbox" id="customboxFax" value="FAX" />
                            <label for="customboxFax" class="custom-control-label">
                                FAX
                            </label>
                        </div>
                    </div>
                </div>
                <div id="tab4-content" class="tab-pane">
                    <div>
                        <span>入力した内容を確認します。以下でよろしいですか?</span>
                    </div>
                    <br />
                    <div class="form-group">
                        <div class="row">
                            <label class="col-xl-1 d-flex align-items-center">
                                名前
                            </label>
                            <p class="col-xl-11" id="InputNameResult" data-bind="text: inputName" />
                        </div>
                        <br />
                        <div class="row">
                            <label class="col-xl-1 d-flex align-items-center">
                                年齢
                            </label>
                            <p class="col-xl-11" id="InputAgeResult" data-bind="text: inputAge" />
                        </div>
                        <br />
                        <div class="row">
                            <label class="col-xl-1 d-flex align-items-center">
                                都道府県
                            </label>
                            <p class="col-xl-11" id="InputPrefResult" data-bind="text: selectedPref" />
                        </div>
                        <br />
                        <div class="row">
                            <label class="col-xl-1 d-flex align-items-center">
                                地域
                            </label>
                            <p class="col-xl-11" id="InputAreaResult" data-bind="text: inputArea" />
                        </div>
                        <br />
                        <div class="row">
                            <label class="col-xl-1 d-flex align-items-center">
                                連絡先
                            </label>
                            <p class="col-xl-11" id="InputContactResult" data-bind="text: inputContact" />
                        </div>
                    </div>
                </div>
            </div>
        </div>
    </div>
</div>

<!-- jQuery -->
<script src="AdminLTE-3.0.2/plugins/jquery/jquery.min.js"></script>
<!-- Bootstrap 4 -->
<script src="AdminLTE-3.0.2/plugins/bootstrap/js/bootstrap.bundle.min.js"></script>
<!-- AdminLTE App -->
<script src="AdminLTE-3.0.2/js/adminlte.min.js"></script>
<!-- knockout.js  -->
<script src="knockout-3.5.1/knockout-3.5.1.js"></script>

<script>
    $(function () {
        var viewModel = {
            //
            // 初期値は空文字
            //
            inputName: ko.observable(''),
            inputAge: ko.observable(''),
            prefItems : ['北海道', '本州', '四国', '九州'],
            selectedPref: ko.observable('北海道'),
            inputArea: ko.observable(''),
            inputContact: ko.observableArray()
        };
        ko.applyBindings(viewModel);
    });
</script>

</body>
</html>

knockout.js、まだよくわかってないけどいい感じ。
今は入力フォームを監視して、入力された値を確認画面にそのまま反映してるだけで、まだ氷山の一角って感じ。
例えば、「基本」タブの「名前」を「姓」「名」って分ける修正をするときに、ViewModelだけ更新すればUIも動的に変わってくれるって使い方ができそう。
ていうか、それが主目的のライブラリなんだっけか・・・・?

もうちょい勉強して、拡張しやすいコードに更新したいですね。
でも、今は先に進むことを考えよう・・・・

次は、画面最下部にあるボタンの実装をやろう。
下の画面の「確認および作成」「<前へ」「次:ディスク」 のとこね・・・
image.png

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0