summaryrefslogtreecommitdiff
path: root/elm3/VNEdit/General.elm
blob: f98bf5c27eaf204fd64455272dda3cd09c64f661 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
module VNEdit.General exposing (..)

import Html exposing (..)
import Html.Attributes exposing (..)
import Html.Events exposing (..)
import File exposing (File)
import Json.Decode as JD
import Lib.Html exposing (..)
import Lib.Gen exposing (..)
import Lib.Util exposing (..)
import Lib.Api as Api


type alias Model =
  { desc            : String
  , image           : Int
  , imgState        : Api.State
  , img_nsfw        : Bool
  , length          : Int
  , l_renai         : String
  , l_wp            : String
  , anime           : String
  , animeList       : List { aid : Int }
  , animeDuplicates : Bool
  }


init : VNEdit -> Model
init d =
  { desc            = d.desc
  , image           = d.image
  , imgState        = Api.Normal
  , img_nsfw        = d.img_nsfw
  , length          = d.length
  , l_renai         = d.l_renai
  , l_wp            = d.l_wp
  , anime           = String.join " " (List.map (.aid >> String.fromInt) d.anime)
  , animeList       = d.anime
  , animeDuplicates = False
  }


new : Model
new =
  { desc            = ""
  , image           = 0
  , imgState        = Api.Normal
  , img_nsfw        = False
  , length          = 0
  , l_renai         = ""
  , l_wp            = ""
  , anime           = ""
  , animeList       = []
  , animeDuplicates = False
  }


type Msg
  = Desc String
  | Image String
  | ImgNSFW Bool
  | Length String
  | LWP String
  | LRenai String
  | Anime String
  | ImgUpload (List File)
  | ImgDone Api.Response


update : Msg -> Model -> (Model, Cmd Msg)
update msg model =
  case msg of
    Desc s     -> ({ model | desc = s }, Cmd.none)
    Image s    -> ({ model | image = if s == "" then 0 else Maybe.withDefault model.image (String.toInt s) }, Cmd.none)
    ImgNSFW b  -> ({ model | img_nsfw = b }, Cmd.none)
    Length s   -> ({ model | length = Maybe.withDefault 0 (String.toInt s) }, Cmd.none)
    LWP s      -> ({ model | l_wp = s }, Cmd.none)
    LRenai s   -> ({ model | l_renai = s }, Cmd.none)

    Anime s ->
      let lst = List.map (\e -> { aid = Maybe.withDefault 0 (String.toInt e) }) (String.words s)
      in ({ model | anime = s, animeList = lst, animeDuplicates = hasDuplicates <| List.map .aid lst }, Cmd.none)

    ImgUpload [i] -> ({ model | imgState = Api.Loading }, Api.postImage Api.Cv i ImgDone)
    ImgUpload _   -> (model, Cmd.none)

    ImgDone (Api.Image id _ _) -> ({ model | image = id, imgState = Api.Normal  }, Cmd.none)
    ImgDone r                  -> ({ model | image =  0, imgState = Api.Error r }, Cmd.none)


view : Model -> (Msg -> a) -> List (Html a) -> Html a
view model wrap titles = card "general" "General info" [] <|
  titles ++ List.map (Html.map wrap)
  [ cardRow "Description" (Just "English please!") <| formGroup
    [ inputTextArea "desc" model.desc Desc [rows 8]
    , div [class "form-group__help"]
      [ text "Short description of the main story. Please do not include untagged spoilers,"
      , text " and don't forget to list the source in case you didn't write the description yourself."
      , text " Formatting codes are allowed."
      ]
    ]
  , cardRow "Image" Nothing
    [ div [class "row"]
      [ div [class "col-md col-md--1"]
        [ div [style "max-width" "200px", style "margin-bottom" "8px"]
          [ dbImg "cv" (if model.imgState == Api.Loading then -1 else model.image) [] Nothing ]
        ]
      , div [class "col-md col-md--2"] <| formGroups
        [ [ label [for "img"] [ text "Upload new image" ]
          , input [type_ "file", class "text", name "img", id "img", Api.onFileChange ImgUpload, disabled (model.imgState == Api.Loading) ] []
          , case model.imgState of
              Api.Error r -> div [class "invalid-feedback"] [text <| Api.showResponse r]
              _ -> text ""
          , div [class "form-group__help"]
            [ text "Preferably the cover of the CD/DVD/package. Image must be in JPEG or PNG format and at most 5MB. Images larger than 256x400 will automatically be resized." ]
          ]
        , [ label [for "img_id"] [ text "Image ID" ]
          , inputText "img_id" (String.fromInt model.image) Image [pattern "^[0-9]+$", disabled (model.imgState == Api.Loading)]
          , div [class "form-group__help"]
            [ text "Use a VN image that is already on the server. Set to '0' to remove the current image." ]
          ]
        , [ label [for "img_nsfw"] [ text "NSFW" ]
          , label [class "checkbox"]
            [ inputCheck "img_nsfw" model.img_nsfw ImgNSFW
            , text " Not safe for work" ]
          , div [class "form-group__help"]
            [ text "Please check this option if the image contains nudity, gore, or is otherwise not safe in a work-friendly environment." ]
          ]
        ]
      ]
    ]
  , cardRow "Properties" Nothing <| formGroups
    [ [ label [for "length"] [ text "Length" ]
      , inputSelect [id "length", name "length", onInput Length]
          (String.fromInt model.length)
          (List.map (\(a,b) -> (String.fromInt a, b)) vnLengths)
      ]
    , [ label [] [ text "External links" ]
      , p [] [ text "http://en.wikipedia.org/wiki/", inputText "l_wp" model.l_wp LWP [class "form-control--inline", maxlength 100] ]
      , p [] [ text "http://renai.us/game/", inputText "l_renai" model.l_renai LRenai [class "form-control--inline", maxlength 100], text ".shtml" ]
      ]
      -- TODO: Nicer list-editing and search suggestions for anime
    , [ label [ for "anime" ] [ text "Anime" ]
      , inputText "anime" model.anime Anime [pattern "^[ 0-9]*$"]
      , if model.animeDuplicates
        then div [class "invalid-feedback"] [ text "There are duplicate anime." ]
        else text ""
      , div [class "form-group__help"]
        [ text "Whitespace separated list of AniDB anime IDs. E.g. \"1015 3348\" will add Shingetsutan Tsukihime and Fate/stay night as related anime."
        , br [] []
        , text "Note: It can take a few minutes for the anime titles to appear on the VN page."
        ]
      ]
    ]
  ]