Elm に手を出しました。
mousemove
のイベントハンドラを使うのに MouseEvent
の JSON をパースする必要があって四苦八苦したので、明日の自分のために JSON のパースの仕方をメモっておきます。
後日イベントハンドラについても書く予定。
パーサを書く
SomethingJson
という雑なモジュールを作成しました。
module SomethingJson exposing ( Something , Somethings , somethingDecoder , parseSomething , parseSomethings , FooBarBaz , parseFooBarBaz ) import Json.Decode exposing ( Decoder , Error , decodeString , at , string , int , map , map3 , list ) -- "something" という文字列の要素を持つレコード型 type alias Something = { something : String } -- Something のリスト型 type alias Somethings = List Something -- "something" という要素を含む JSON のデコーダ somethingDecoder : Decoder String somethingDecoder = at ["something"] string -- JSON 文字列をパースして Something 型の値を返す関数 parseSomething : String -> Result Error Something parseSomething = decodeString (map Something somethingDecoder) -- JSON 文字列をパースして Somethings 型の値を返す関数 parseSomethings : String -> Result Error Somethings parseSomethings = decodeString (list (map Something somethingDecoder)) -- 三つの要素を持つレコード型 type alias FooBarBaz = { foo : String , bar : Int , baz : List Int } -- "foo", "bar", "baz" という要素を含む JSON のデコーダ fooBarBazDecoder : Decoder FooBarBaz fooBarBazDecoder = map3 FooBarBaz (at ["foo"] string) (at ["bar"] int) (at ["baz"] (list int)) -- JSON 文字列をパースして FooBarBaz 型の値を返す関数 parseFooBarBaz : String -> Result Error FooBarBaz parseFooBarBaz = decodeString fooBarBazDecoder
elm init
した時に作成される src/
というディレクトリに SomethingJson.elm
という名前で保存します。
パーサを使う
REPL で動作を確認します。
$ elm repl ---- Elm 0.19.0 ---------------------------------------------------------------- Read <https://elm-lang.org/0.19.0/repl> to learn more: exit, help, imports, etc. -------------------------------------------------------------------------------- >
インポートします。
> import SomethingJson
Something
型を表す JSON をパースします。
> SomethingJson.parseSomething "{\"something\":\"何か\"}" Ok { something = "何か" } : Result Json.Decode.Error SomethingJson.Something
Somethings
型(Something
のリスト型)を表す JSON をパースします。
> SomethingJson.parseSomethings "[{\"something\":\"何か\"},{\"something\":\"どれか\"}]" Ok [{ something = "何か" },{ something = "どれか" }] : Result Json.Decode.Error SomethingJson.Somethings
三種類の型の値を持つ FooBarBaz
型を表す JSON をパースします。
> SomethingJson.parseFooBarBaz "{\"foo\":\"ふー\",\"bar\":123,\"baz\":[1,2,3]}" Ok { bar = 123, baz = [1,2,3], foo = "ふー" } : Result Json.Decode.Error SomethingJson.FooBarBaz
もっと要素の多い JSON のパーサをかく
Json.Decode
には map8
まで用意されていて 8 要素まではパーサを書くことができます。それ以上の場合はドキュメントにも記載されているように他のパッケージなどを利用します。
Note: If you run out of map functions, take a look at elm-json-decode-pipeline which makes it easier to handle large objects, but produces lower quality type errors.
リンクされている elm-json-decode-pipeline を使ってみます。
インストールします。
$ elm install NoRedInk/elm-json-decode-pipeline
HTML の MouseEvent の内容を解釈するパーサを書いてみます。
module MouseEvents exposing (EventData, mouseEventDecoder, parseMouseEvent) import Json.Decode exposing (Decoder, Error, decodeString, int, bool, succeed) import Json.Decode.Pipeline exposing (required) type alias EventData = { altKey : Bool , ctrlKey : Bool , shiftKey : Bool , metaKey : Bool , button : Int , clientX : Int , clientY : Int , movementX : Int , movementY : Int , screenX : Int , screenY : Int } mouseEventDecoder : Decoder EventData mouseEventDecoder = succeed EventData |> required "altKey" bool |> required "ctrlKey" bool |> required "shiftKey" bool |> required "metaKey" bool |> required "button" int |> required "clientX" int |> required "clientY" int |> required "movementX" int |> required "movementY" int |> required "screenX" int |> required "screenY" int parseMouseEvent : String -> Result Error EventData parseMouseEvent = decodeString mouseEventDecoder
MouseEvents.elm
というファイル名で src/
に保存します。
REPL で確認します。
$ elm repl ---- Elm 0.19.0 ---------------------------------------------------------------- Read <https://elm-lang.org/0.19.0/repl> to learn more: exit, help, imports, etc. -------------------------------------------------------------------------------- > import MouseEvents > MouseEvents.parseMouseEvent "{\"screenX\":1,\"screenY\":1,\"movementX\":1,\"movementY\":1,\"clientX\":1,\"clientY\":1,\"button\":0,\"metaKey\":true,\"shiftKey\":true,\"ctrlKey\":true,\"altKey\":true}" Ok { altKey = True, button = 0, clientX = 1, clientY = 1, ctrlKey = True, metaKey = True, movementX = 1, movementY = 1, screenX = 1, screenY = 1, shiftKey = True } : Result Json.Decode.Error MouseEvents.EventData
これで MouseEvent を扱う準備ができました。つづく。
いつか読むはずっと読まない:はじまりの艦隊
The Lost Fleet (彷徨える艦隊)の最新刊、The Genesis Fleet: Vanguard 、の邦訳、ようやく読了。って刊行から一年近く経ってしまっていた。
来月には原著のシリーズ最新刊 The Genesis Fleet: Triumphant がもう刊行される模様。
- 作者: ジャック・キャンベル,寺田克也,月岡小穂
- 出版社/メーカー: 早川書房
- 発売日: 2018/05/02
- メディア: 文庫
- この商品を含むブログ (1件) を見る