google-handwriting-api-elm/src/Api.elm

130 lines
3.7 KiB
Elm

module Api exposing (Msg(..), update)
import Http exposing (expectJson)
import List exposing (map)
import Json.Decode as D exposing (Value)
import Json.Encode as E
import DrawingBoard exposing (Stroke)
api : String
api = "https://inputtools.google.com/request?itc=ja-t-i0-handwrit&app=translate"
type alias APIRequest = {
app_version : Float
, api_level : String
, device : String
, input_type : Int
, options : String
, requests : List Request
}
apiRequestEncoder : APIRequest -> Value
apiRequestEncoder request =
E.object
[ ("app_version", E.float request.app_version)
, ("api_level", E.string request.api_level)
, ("device", E.string request.device)
, ("input_type", E.int request.input_type)
, ("options", E.string request.options)
, ("requests", E.list requestEncoder request.requests)
]
type alias Request = {
writing_guide: WritingGuide
, pre_context: String
, max_num_results: Int
, max_completions: Int
, language: String
, ink: List RealStroke
}
strokeEncoder : RealStroke -> Value
strokeEncoder = E.list(E.list(E.float))
requestEncoder : Request -> Value
requestEncoder request =
E.object
[ ("writing_guide", writingGuideEncoder request.writing_guide)
, ("pre_context", E.string request.pre_context)
, ("max_num_results", E.int request.max_num_results)
, ("max_completions", E.int request.max_completions)
, ("language", E.string request.language)
, ("ink", E.list strokeEncoder request.ink)
]
type alias WritingGuide = {
writing_area_width: Int
, writing_area_height: Int
}
writingGuideEncoder : WritingGuide -> Value
writingGuideEncoder writingGuide=
E.object
[ ("writing_area_width", E.int writingGuide.writing_area_width)
, ("writing_area_height", E.int writingGuide.writing_area_height)
]
type Msg = SendRequest
| GotResponse (Result Http.Error (List String))
update : Msg -> List Stroke -> String -> (List String, Cmd Msg)
update msg strokes userAgent =
case msg of
SendRequest -> ([], sendKanjiRequest strokes userAgent)
GotResponse result ->
case result of
Ok kanji -> Debug.log "OK: " (kanji, Cmd.none)
Err e -> Tuple.second (Debug.log "ERR: " e, ([], Cmd.none))
kanjiDecoder : D.Decoder (List String)
kanjiDecoder = D.index 1
<| D.index 0
<| D.index 1
<| D.list
<| D.oneOf [D.string]
sendKanjiRequest : List Stroke -> String -> Cmd Msg
sendKanjiRequest strokes userAgent = Http.post
{ body = generateRequestData strokes userAgent
|> apiRequestEncoder
|> Http.jsonBody
, expect = expectJson GotResponse kanjiDecoder
, url = api
}
type alias RealStroke = List (List Float)
convertStrokeToRealStroke : Stroke -> RealStroke
convertStrokeToRealStroke stroke = [ stroke.xs
, stroke.ys
, (map (\t -> t - stroke.startTime) stroke.times)
]
mockWritingGuide : WritingGuide
mockWritingGuide =
{ writing_area_width = 500
, writing_area_height = 500
}
max_results : Int
max_results = 10
generateRequestData : List Stroke -> String -> APIRequest
generateRequestData strokes userAgent =
{ app_version = 0.4
, api_level = "537.36"
, device = userAgent
, input_type = 0
, options = "enable_pre_space"
, requests =
[
{ writing_guide = mockWritingGuide
, pre_context = ""
, max_num_results = max_results
, max_completions = 0
, language = "ja"
, ink = (map convertStrokeToRealStroke strokes)
}
]
}