elm

elmでwebアプリ作成15 〜 施設追加画面

前回は、施設情報の編集が保存できたかどうかを画面上に表示する機能を作りました。

今回は、新しい施設を新規追加する機能です。

ここでは、新規追加画面を作ります。登録は次回にします。

このコミットです。

施設一覧ページの右上に、「add new facility」ボタンを作って、そこから新規追加画面へ遷移します。
新規追加画面では、施設名やその他の項目を埋めて、「register」ボタンを押すと施設が登録されます。
今回実装したのは画面までなので、registerボタンを押してもまだ登録はされません。


src/Facilities/AddNewFacility.elmの作成

新規追加画面です。src/View.elmから、このモジュールのviewが呼ばれます。施設の各フィールドについては、リスト表示にしました。インポートする関数は全て列挙するスタイルで来ていますが、Htmlモジュールのインポート関数を列挙するのが面倒になってきたのでimport Html exposing (..)にしてしまおうかと思っています。

module Facilities.AddNewFacility exposing (..)

import Html exposing (Html, button, div, input, table, tbody, td, text, textarea, thead, tr)
import Html.Attributes exposing (class, cols, rows, type_)
import Msgs exposing (Msg)

view : Html Msg
view =
    div [ class "m2" ]
        [ nav
        , addNewFacility
        ]

nav : Html Msg
nav =
    div []
        [ text "add new facility page"
        ]

addNewFacility : Html Msg
addNewFacility =
    div []
        [ fieldList ]

fieldList : Html Msg
fieldList =
    div []
        [ table []
            [ thead [] []
            , tbody []
                [ tr []
                    [ td [] [ text "Facility name" ]
                    , td [] [ input [ type_ "text" ] [] ]
                    ]
                , tr []
                    [ td [] [ text "Opening time" ]
                    , td [] [ input [ type_ "time" ] []
                            , text " - "
                            , input [ type_ "time" ] []
                            ]
                    ]
                , tr []
                    [ td [] [ text "Postal code (Zip code)" ]
                    , td [] [ input [ type_ "text" ] [] ]
                    ]
                , tr []
                    [ td [] [ text "Address" ]
                    , td [] [ input [ type_ "text" ] [] ]
                    ]
                , tr []
                    [ td [] [ text "web_site URL" ]
                    , td [] [ input [ type_ "url" ] [] ]
                    ]
                , tr []
                    [ td [] [ text "description" ]
                    , td [] [ textarea [ rows 10, cols 100 ] [] ]
                    ]
                ]
            ]
        , button [ class "btn btn-primary mb1 bg-blue" ] [ text "register" ]
        ]

src/Facilities/List.elmの編集

施設一覧ページに、新規追加ページへのリンクボタンを置きます。

-- 追加インポート
import Html.Attributes exposing (class, href)
import Routing exposing (facilityPath, newFacilityPath)

view : WebData (List Facility) -> Html Msg
view response =
    div []
    div [ class "m2" ] -- マージンをつけた
        [ nav
        , maybeList response
        ]

-- 新規追加ページへのリンクボタンを表示
nav : Html Msg
nav =
    div []
        [ div [] [ text "施設一覧" ] ]
        [ text "Facility list"
        , span [ class "right" ] [ newFacilityLink ]
        ]

-- 新規追加ページへのリンクボタン
newFacilityLink : Html Msg
newFacilityLink =
    a [ href  newFacilityPath, class "center p1 white bg-blue rounded" ]
        [ text "add new facility"]

こんな感じで右上にボタンが表示されます。


src/Facilities/SingleEdit.elmの編集

これは、ついでにやってしまった変更で、CSSのためにクラスをつけただけなので、関係ありません。こういう「ついでに」をよくやってしまいます。


src/Models.elmの編集

-- 新規追加ページへのルーティング用の型を追加
type Route
    = FacilitiesRoute
    | FacilityRoute FacilityId
    | FacilityEditRoute FacilityId
    | NewFacilityRoute -- 追加
    | NotFoundRoute

src/Routing.elmの編集

ルーティングの定義です。

-- 新規追加ページへのパス
newFacilityPath : String
newFacilityPath =
    "#new-facility"

-- 上記のパスにマッチするようにマッチャー追加
matchers : Parser (Route -> a) a
matchers =
    oneOf
        [ map FacilitiesRoute top
        , map FacilityEditRoute (s "facilities" </> string </> s "edit")
        , map FacilityRoute (s "facilities" </> string)
        , map FacilitiesRoute (s "facilities")
        , map NewFacilityRoute (s "new-facility") -- 追加
        ]

src/View.elmの編集

ルーティングで、NewFacilityRouteにマッチした時に新規追加ページのビューを呼び出します。

-- 追加インポート
import Facilities.AddNewFacility

-- NewFacilityRouteの時に、新規追加ページのビューを呼び出す
page : Model -> Html Msg
page model =
    case model.route of
        Models.FacilitiesRoute ->
            Facilities.List.view model.facilities
        Models.FacilityRoute facilityId ->
            singlePage model facilityId
        Models.FacilityEditRoute facilityId ->
            singleEditPage model facilityId
        Models.NewFacilityRoute ->
            Facilities.AddNewFacility.view -- 追加
        Models.NotFoundRoute ->
            notFoundView "url not found"

これで、新規追加画面はできました。こんな感じです。デザインセンスがあれば、もっとましな見た目にするんですが、とりあえずまず機能を実装するということで。

次は、これをDBに反映させる処理を実装します。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です