elm-pages-v3-beta/examples/pokedex/src/Page/TailwindForm.elm

2332 lines
97 KiB
Elm
Raw Normal View History

module Page.TailwindForm exposing (Data, Model, Msg, page)
import Css
import Css.Global
import DataSource exposing (DataSource)
2022-01-04 08:17:07 +03:00
import Date exposing (Date)
import Dict exposing (Dict)
import Form exposing (Form)
import Head
import Head.Seo as Seo
2022-01-05 03:20:44 +03:00
import Html as CoreHtml
import Html.Styled as Html exposing (Html)
import Html.Styled.Attributes as Attr exposing (css)
import Icon
import Page exposing (Page, PageWithState, StaticPayload)
import PageServerResponse exposing (PageServerResponse)
import Pages.PageUrl exposing (PageUrl)
import Pages.Url
import Server.Request as Request exposing (Request)
import Shared
import Tailwind.Breakpoints as Bp
import Tailwind.Utilities as Tw
2022-01-04 08:17:07 +03:00
import Time
import View exposing (View)
type alias Model =
{}
type alias Msg =
Never
type alias RouteParams =
{}
type alias User =
{ first : String
, last : String
, username : String
, email : String
2022-01-04 08:17:07 +03:00
, birthDay : Date
, notificationPreferences : NotificationPreferences
}
type alias NotificationPreferences =
{ comments : Bool
, candidates : Bool
, offers : Bool
2022-01-05 04:55:37 +03:00
, pushNotificationsSetting : Maybe PushNotificationsSetting
}
defaultUser : User
defaultUser =
{ first = "Jane"
, last = "Doe"
, username = "janedoe"
, email = "janedoe@example.com"
2022-01-04 08:17:07 +03:00
, birthDay = Date.fromCalendarDate 1969 Time.Jul 20
, notificationPreferences =
{ comments = False
, candidates = False
, offers = False
2022-01-05 04:55:37 +03:00
, pushNotificationsSetting = Nothing
}
}
styleAttrs attrs =
List.map Attr.fromUnstyled attrs
usernameInput { toInput, toLabel, errors } =
Html.div []
[ Html.div
[ css
[ Bp.sm
[ Tw.grid
, Tw.grid_cols_3
, Tw.gap_4
, Tw.items_start
, Tw.border_t
, Tw.border_gray_200
, Tw.pt_5
]
]
]
[ Html.label
(styleAttrs toInput
++ [ Attr.for "username"
, css
[ Tw.block
, Tw.text_sm
, Tw.font_medium
, Tw.text_gray_700
, Bp.sm
[ Tw.mt_px
, Tw.pt_2
]
]
]
)
[ Html.text "Username" ]
, Html.div
[ css
[ Tw.mt_1
, Bp.sm
[ Tw.mt_0
, Tw.col_span_2
]
]
]
[ Html.div
[ css
[ Tw.max_w_lg
, Tw.flex
, Tw.rounded_md
, Tw.shadow_sm
, Tw.relative
]
]
[ Html.span
[ css
[ Tw.inline_flex
, Tw.items_center
, Tw.px_3
, Tw.rounded_l_md
, Tw.border
, Tw.border_r_0
, Tw.border_gray_300
, Tw.bg_gray_50
, Tw.text_gray_500
, Bp.sm
[ Tw.text_sm
]
]
]
[ Html.text "workcation.com/" ]
, Html.input
(styleAttrs toInput
++ [ Attr.type_ "text"
, Attr.name "username"
, Attr.id "username"
, Attr.attribute "autocomplete" "username"
, css
[ Tw.flex_1
, Tw.block
, Tw.w_full
, Tw.min_w_0
, Tw.rounded_none
, Tw.rounded_r_md
, Tw.border_gray_300
, Css.focus
[ Tw.ring_indigo_500
, Tw.border_indigo_500
]
, Bp.sm
[ Tw.text_sm
]
]
]
)
[]
, Html.div
[ css
[ Tw.absolute
, Tw.inset_y_0
, Tw.right_0
, Tw.pr_3
, Tw.flex
, Tw.items_center
, Tw.pointer_events_none
]
]
[ if errors |> List.isEmpty then
Html.text ""
else
Icon.error
]
]
]
]
2022-01-03 22:14:39 +03:00
, Html.p
[ css
[ Tw.mt_2
, Tw.text_sm
, Tw.text_red_600
]
]
2022-01-03 22:14:39 +03:00
[ errors |> String.join "\n" |> Html.text ]
]
form : User -> Form User (Html Never)
form user =
Form.succeed User
|> Form.required
(Form.input
"first"
2022-01-03 22:14:39 +03:00
(textInput "First name")
|> Form.withInitialValue user.first
)
|> Form.required
(Form.input
"last"
2022-01-03 22:14:39 +03:00
(textInput "Last name")
|> Form.withInitialValue user.last
)
|> Form.required
(Form.input "username" usernameInput
|> Form.withInitialValue user.username
|> Form.withServerValidation
(\username ->
if username == "asdf" then
DataSource.succeed [ "username is taken" ]
else
DataSource.succeed []
)
)
|> Form.required
(Form.input
"email"
2022-01-03 22:14:39 +03:00
(textInput "Email address")
|> Form.withInitialValue user.email
)
|> Form.required
(Form.date
"dob"
2022-01-03 22:14:39 +03:00
(textInput "Date of Birth")
2022-01-04 08:17:07 +03:00
|> Form.withInitialValue (user.birthDay |> Date.toIsoString)
|> Form.withMinDate "1900-01-01"
|> Form.withMaxDate "2022-01-01"
2022-01-04 08:17:07 +03:00
|> Form.withServerValidation
(\birthDate ->
let
_ =
2022-01-05 03:20:44 +03:00
birthDate |> Date.toIsoString
2022-01-04 08:17:07 +03:00
in
2022-01-05 03:20:44 +03:00
if birthDate == Date.fromCalendarDate 1969 Time.Jul 20 then
2022-01-04 08:17:07 +03:00
DataSource.succeed [ "No way, that's when the moon landing happened!" ]
else
DataSource.succeed []
)
)
2022-01-04 08:17:07 +03:00
|> Form.wrap wrapSection
|> Form.appendForm (|>)
2022-01-05 03:20:44 +03:00
((Form.succeed NotificationPreferences
|> Form.required
(Form.checkbox
"comments"
--user.checkbox
False
(checkboxInput { name = "Comments", description = "Get notified when someones posts a comment on a posting." })
)
|> Form.required
(Form.checkbox
"candidates"
--user.checkbox
False
(checkboxInput { name = "Candidates", description = "Get notified when a candidate applies for a job." })
)
|> Form.required
(Form.checkbox
"offers"
--user.checkbox
False
(checkboxInput { name = "Offers", description = "Get notified when a candidate accepts or rejects an offer." })
)
2022-01-05 03:20:44 +03:00
|> Form.wrap wrapEmailSection
2022-01-05 04:55:37 +03:00
|> Form.appendForm (|>)
(Form.succeed identity
|> Form.required
(Form.radio
"radio-example"
pushNotificationsSettingToString
pushNotificationsSettingFromString
[ PushAll, PushEmail, PushNone ]
radioInput
wrapPushNotificationsSection
)
2022-01-05 03:20:44 +03:00
)
)
|> Form.wrap wrapNotificationsSections
)
|> Form.append
(Form.submit
(\{ attrs } ->
2022-01-03 22:14:39 +03:00
Html.div
[ css
[ Tw.pt_5
]
]
[ Html.div
[ css
[ Tw.flex
, Tw.justify_end
]
]
2022-01-04 01:26:04 +03:00
[ cancelButton
, saveButton attrs
2022-01-03 22:14:39 +03:00
]
]
)
)
2022-01-05 04:55:37 +03:00
type PushNotificationsSetting
= PushAll
| PushEmail
| PushNone
pushNotificationsSettingToString : PushNotificationsSetting -> String
pushNotificationsSettingToString pushNotificationsSetting =
case pushNotificationsSetting of
PushAll ->
"PushAll"
PushEmail ->
"PushEmail"
PushNone ->
"PushNone"
pushNotificationsSettingFromString : String -> Maybe PushNotificationsSetting
pushNotificationsSettingFromString pushNotificationsSetting =
case pushNotificationsSetting of
"PushAll" ->
Just PushAll
"PushEmail" ->
Just PushEmail
"PushNone" ->
Just PushNone
_ ->
Nothing
2022-01-04 01:26:04 +03:00
saveButton formAttrs =
Html.button
(styleAttrs formAttrs
++ [ css
[ Tw.ml_3
, Tw.inline_flex
, Tw.justify_center
, Tw.py_2
, Tw.px_4
, Tw.border
, Tw.border_transparent
, Tw.shadow_sm
, Tw.text_sm
, Tw.font_medium
, Tw.rounded_md
, Tw.text_white
, Tw.bg_indigo_600
, Css.focus
[ Tw.outline_none
, Tw.ring_2
, Tw.ring_offset_2
, Tw.ring_indigo_500
]
, Css.hover
[ Tw.bg_indigo_700
]
]
]
)
[ Html.text "Save" ]
cancelButton : Html msg
cancelButton =
Html.button
[ Attr.type_ "button"
, css
[ Tw.bg_white
, Tw.py_2
, Tw.px_4
, Tw.border
, Tw.border_gray_300
, Tw.rounded_md
, Tw.shadow_sm
, Tw.text_sm
, Tw.font_medium
, Tw.text_gray_700
, Css.focus
[ Tw.outline_none
, Tw.ring_2
, Tw.ring_offset_2
, Tw.ring_indigo_500
]
, Css.hover
[ Tw.bg_gray_50
]
]
]
[ Html.text "Cancel" ]
page : Page RouteParams Data
page =
Page.serverRender
{ head = head
, data = data
}
|> Page.buildNoState { view = view }
type alias Data =
{ user : Maybe User
2022-01-04 22:47:57 +03:00
, errors : Maybe (Dict String { raw : Maybe String, errors : List String })
}
data : RouteParams -> Request (DataSource (PageServerResponse Data))
data routeParams =
Request.oneOf
[ Form.toRequest2 (form defaultUser)
|> Request.map
(\userOrErrors ->
userOrErrors
|> DataSource.map
(\result ->
(case result of
Ok ( user, errors ) ->
{ user = Just user
, errors = Just errors
}
Err errors ->
{ user = Nothing
, errors = Just errors
}
)
|> PageServerResponse.RenderPage
)
)
, PageServerResponse.RenderPage
{ user = Nothing
, errors = Nothing
}
|> DataSource.succeed
|> Request.succeed
]
head :
StaticPayload Data RouteParams
-> List Head.Tag
head static =
Seo.summary
{ canonicalUrlOverride = Nothing
, siteName = "elm-pages"
, image =
{ url = Pages.Url.external "TODO"
, alt = "elm-pages logo"
, dimensions = Nothing
, mimeType = Nothing
}
, description = "TODO"
, locale = Nothing
, title = "TODO title" -- metadata.title -- TODO
}
|> Seo.website
wrapSection : List (Html msg) -> Html msg
wrapSection children =
2022-01-03 22:55:45 +03:00
Html.div []
[ Html.div []
[ Html.h3
[ css
[ Tw.text_lg
, Tw.leading_6
, Tw.font_medium
, Tw.text_gray_900
]
]
[ Html.text "Profile" ]
, Html.p
[ css
[ Tw.mt_1
, Tw.max_w_2xl
, Tw.text_sm
, Tw.text_gray_500
]
]
[ Html.text "This information will be displayed publicly so be careful what you share." ]
]
, Html.div
[ css
[ Tw.mt_6
, Tw.space_y_6
, Bp.sm
[ Tw.mt_5
, Tw.space_y_5
]
]
]
children
2022-01-03 22:55:45 +03:00
]
view :
Maybe PageUrl
-> Shared.Model
-> StaticPayload Data RouteParams
-> View Msg
view maybeUrl sharedModel static =
let
user : User
user =
static.data.user
|> Maybe.withDefault defaultUser
in
{ title = "Form Example"
, body =
[ Html.div
[]
[ Css.Global.global Tw.globalStyles
, static.data.user
|> Maybe.map
(\user_ ->
Html.p
[ css
[ Css.backgroundColor (Css.rgb 163 251 163)
, Tw.p_4
]
]
[ Html.text <| "Successfully received user " ++ user_.first ++ " " ++ user_.last
]
)
|> Maybe.withDefault (Html.p [] [])
2022-01-03 22:14:39 +03:00
--, Html.h1
-- []
-- [ Html.text <| "Edit profile " ++ user.first ++ " " ++ user.last ]
2022-01-03 22:14:39 +03:00
, Html.div
[ css
[ Tw.flex
, Tw.flex_col
, Tw.items_center
, Tw.mt_8
, Tw.border_gray_700
, Tw.rounded_lg
]
2022-01-03 22:14:39 +03:00
]
[ form user
|> Form.toHtml
(\attrs children -> Html.form (List.map Attr.fromUnstyled attrs) children)
static.data.errors
]
--,
--Html.div [
--css [
-- Tw.flex
-- , Tw.flex_col
-- , Tw.items_center
-- , Tw.mt_8
-- , Tw.border_gray_700
-- , Tw.rounded_lg
--
--
--]
--] [
--fullView
--]
]
|> Html.toUnstyled
]
}
2022-01-03 22:14:39 +03:00
textInput labelText { toInput, toLabel, errors } =
Html.div
[ css
[ Bp.sm
[ Tw.grid
, Tw.grid_cols_3
, Tw.gap_4
, Tw.items_start
, Tw.border_t
, Tw.border_gray_200
, Tw.pt_5
]
]
2022-01-03 22:14:39 +03:00
]
[ Html.label
([ css
[ Tw.block
, Tw.text_sm
, Tw.font_medium
, Tw.text_gray_700
, Bp.sm
[ Tw.mt_px
, Tw.pt_2
]
]
2022-01-03 22:14:39 +03:00
]
++ styleAttrs toLabel
)
[ Html.text labelText ]
, Html.div
[ css
[ Tw.mt_1
, Bp.sm
[ Tw.mt_0
, Tw.col_span_2
]
2022-01-03 22:14:39 +03:00
]
]
[ Html.input
(styleAttrs toInput
++ [ --Attr.attribute "autocomplete" "given-name",
css
[ Tw.max_w_lg
, Tw.block
, Tw.w_full
, Tw.shadow_sm
, Tw.border_gray_300
, Tw.rounded_md
, Css.focus
[ Tw.ring_indigo_500
, Tw.border_indigo_500
]
, Bp.sm
2022-01-03 22:14:39 +03:00
[ Tw.max_w_xs
, Tw.text_sm
]
]
2022-01-03 22:14:39 +03:00
]
)
[]
]
2022-01-04 08:17:07 +03:00
, Html.p
[ css
[ Tw.mt_2
, Tw.text_sm
, Tw.text_red_600
]
]
[ errors |> String.join "\n" |> Html.text ]
2022-01-03 22:14:39 +03:00
]
textInput2 =
Html.div
[ css
[ Bp.sm
[ Tw.grid
, Tw.grid_cols_3
, Tw.gap_4
, Tw.items_start
, Tw.border_t
, Tw.border_gray_200
, Tw.pt_5
]
2022-01-03 22:14:39 +03:00
]
]
[ Html.label
[ Attr.for "first-name"
, css
[ Tw.block
, Tw.text_sm
, Tw.font_medium
, Tw.text_gray_700
, Bp.sm
[ Tw.mt_px
, Tw.pt_2
]
]
2022-01-03 22:14:39 +03:00
]
[ Html.text "First name" ]
, Html.div
[ css
[ Tw.mt_1
, Bp.sm
[ Tw.mt_0
, Tw.col_span_2
]
2022-01-03 22:14:39 +03:00
]
]
[ Html.input
[ Attr.type_ "text"
, Attr.name "first-name"
, Attr.id "first-name"
, Attr.attribute "autocomplete" "given-name"
, css
[ Tw.max_w_lg
, Tw.block
, Tw.w_full
, Tw.shadow_sm
, Tw.border_gray_300
, Tw.rounded_md
, Css.focus
[ Tw.ring_indigo_500
, Tw.border_indigo_500
]
2022-01-03 22:14:39 +03:00
, Bp.sm
[ Tw.max_w_xs
, Tw.text_sm
]
]
]
2022-01-03 22:14:39 +03:00
[]
]
]
checkboxInput { name, description } { toLabel, toInput, errors } =
Html.div
[ css
[ Tw.max_w_lg
, Tw.space_y_4
]
]
[ Html.div
[ css
[ Tw.relative
, Tw.flex
, Tw.items_start
]
]
[ Html.div
[ css
[ Tw.flex
, Tw.items_center
, Tw.h_5
]
]
[ Html.input
(styleAttrs toInput
++ [ css
[ Tw.h_4
, Tw.w_4
, Tw.text_indigo_600
, Tw.border_gray_300
, Tw.rounded
, Css.focus
[ Tw.ring_indigo_500
]
]
]
)
[]
]
, Html.div
[ css
[ Tw.ml_3
, Tw.text_sm
]
]
[ Html.label
(styleAttrs toLabel
++ [ css
[ Tw.font_medium
, Tw.text_gray_700
]
]
)
[ Html.text name ]
, Html.p
[ css
[ Tw.text_gray_500
]
]
[ Html.text description ]
]
]
]
2022-01-03 22:14:39 +03:00
2022-01-05 03:20:44 +03:00
wrapNotificationsSections children =
Html.div
[ css
[ Tw.divide_y
, Tw.divide_gray_200
, Tw.pt_8
, Tw.space_y_6
, Bp.sm
[ Tw.pt_10
, Tw.space_y_5
]
]
]
[ Html.div []
[ Html.h3
[ css
[ Tw.text_lg
, Tw.leading_6
, Tw.font_medium
, Tw.text_gray_900
]
]
[ Html.text "Notifications" ]
, Html.p
[ css
[ Tw.mt_1
, Tw.max_w_2xl
, Tw.text_sm
, Tw.text_gray_500
]
]
[ Html.text "We'll always let you know about important changes, but you pick what else you want to hear about." ]
]
, Html.div
[ css
[ Tw.space_y_6
, Tw.divide_y
, Tw.divide_gray_200
, Bp.sm
[ Tw.space_y_5
]
]
]
children
]
wrapEmailSection children =
Html.div
[ css
[ Tw.pt_6
, Bp.sm
[ Tw.pt_5
]
]
]
[ Html.div
[ Attr.attribute "role" "group"
, Attr.attribute "aria-labelledby" "label-email"
]
[ Html.div
[ css
[ Bp.sm
[ Tw.grid
, Tw.grid_cols_3
, Tw.gap_4
, Tw.items_baseline
]
]
]
[ Html.div []
[ Html.div
[ css
[ Tw.text_base
, Tw.font_medium
, Tw.text_gray_900
, Bp.sm
[ Tw.text_sm
, Tw.text_gray_700
]
]
, Attr.id "label-email"
]
[ Html.text "By Email" ]
]
, Html.div
[ css
[ Tw.mt_4
, Bp.sm
[ Tw.mt_0
, Tw.col_span_2
]
]
]
[ Html.div
[ css
[ Tw.max_w_lg
, Tw.space_y_4
]
]
children
]
]
]
]
2022-01-05 04:55:37 +03:00
radioInput item { toLabel, toInput, errors } =
Html.div
[ css
[ Tw.flex
, Tw.items_center
]
]
[ Html.input
(styleAttrs toInput
++ [ --Attr.id "push-everything"
--, Attr.name "push-notifications"
--, Attr.type_ "radio"
css
[ Tw.h_4
, Tw.w_4
, Tw.text_indigo_600
, Tw.border_gray_300
, Css.focus
[ Tw.ring_indigo_500
]
]
]
)
[]
, Html.label
(styleAttrs toLabel
++ [ --Attr.for "push-everything"
css
[ Tw.ml_3
, Tw.block
, Tw.text_sm
, Tw.font_medium
, Tw.text_gray_700
]
]
)
[ (case item of
PushAll ->
"Everything"
PushEmail ->
"Same as email"
PushNone ->
"No push notifications"
)
|> Html.text
]
]
wrapPushNotificationsSection children =
2022-01-05 03:20:44 +03:00
Html.div
[ css
[ Tw.pt_6
, Bp.sm
[ Tw.pt_5
]
]
]
[ Html.div
[ Attr.attribute "role" "group"
, Attr.attribute "aria-labelledby" "label-notifications"
]
[ Html.div
[ css
[ Bp.sm
[ Tw.grid
, Tw.grid_cols_3
, Tw.gap_4
, Tw.items_baseline
]
]
]
[ Html.div []
[ Html.div
[ css
[ Tw.text_base
, Tw.font_medium
, Tw.text_gray_900
, Bp.sm
[ Tw.text_sm
, Tw.text_gray_700
]
]
, Attr.id "label-notifications"
]
[ Html.text "Push Notifications" ]
]
, Html.div
[ css
[ Bp.sm
[ Tw.col_span_2
]
]
]
[ Html.div
[ css
[ Tw.max_w_lg
]
]
[ Html.p
[ css
[ Tw.text_sm
, Tw.text_gray_500
]
]
[ Html.text "These are delivered via SMS to your mobile phone." ]
, Html.div
[ css
[ Tw.mt_4
, Tw.space_y_4
]
]
2022-01-05 04:55:37 +03:00
children
2022-01-05 03:20:44 +03:00
]
]
]
]
]
2022-01-03 22:14:39 +03:00
--fullView : Html msg
--fullView =
-- Html.form
-- [ css
-- [ Tw.space_y_8
-- , Tw.divide_y
-- , Tw.divide_gray_200
-- , Tw.max_w_2xl
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.space_y_8
-- , Tw.divide_y
-- , Tw.divide_gray_200
-- , Bp.sm
-- [ Tw.space_y_5
-- ]
-- ]
-- ]
-- [ Html.div []
-- [ Html.div []
-- [ Html.h3
-- [ css
-- [ Tw.text_lg
-- , Tw.leading_6
-- , Tw.font_medium
-- , Tw.text_gray_900
-- ]
-- ]
-- [ Html.text "Profile" ]
-- , Html.p
-- [ css
-- [ Tw.mt_1
-- , Tw.max_w_2xl
-- , Tw.text_sm
-- , Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "This information will be displayed publicly so be careful what you share." ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.mt_6
-- , Tw.space_y_6
-- , Bp.sm
-- [ Tw.mt_5
-- , Tw.space_y_5
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "username"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "Username" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.max_w_lg
-- , Tw.flex
-- , Tw.rounded_md
-- , Tw.shadow_sm
-- ]
-- ]
-- [ Html.span
-- [ css
-- [ Tw.inline_flex
-- , Tw.items_center
-- , Tw.px_3
-- , Tw.rounded_l_md
-- , Tw.border
-- , Tw.border_r_0
-- , Tw.border_gray_300
-- , Tw.bg_gray_50
-- , Tw.text_gray_500
-- , Bp.sm
-- [ Tw.text_sm
-- ]
-- ]
-- ]
-- [ Html.text "workcation.com/" ]
-- , Html.input
-- [ Attr.type_ "text"
-- , Attr.name "username"
-- , Attr.id "username"
-- , Attr.attribute "autocomplete" "username"
-- , css
-- [ Tw.flex_1
-- , Tw.block
-- , Tw.w_full
-- , Tw.min_w_0
-- , Tw.rounded_none
-- , Tw.rounded_r_md
-- , Tw.border_gray_300
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "about"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "About" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.textarea
-- [ Attr.id "about"
-- , Attr.name "about"
-- , Attr.rows 3
-- , css
-- [ Tw.max_w_lg
-- , Tw.shadow_sm
-- , Tw.block
-- , Tw.w_full
-- , Tw.border
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- , Html.p
-- [ css
-- [ Tw.mt_2
-- , Tw.text_sm
-- , Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "Write a few sentences about yourself." ]
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_center
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "photo"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "Photo" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- ]
-- ]
-- [ Html.span
-- [ css
-- [ Tw.h_12
-- , Tw.w_12
-- , Tw.rounded_full
-- , Tw.overflow_hidden
-- , Tw.bg_gray_100
-- ]
-- ]
-- [ Icon.icon2
-- ]
-- , Html.button
-- [ Attr.type_ "button"
-- , css
-- [ Tw.ml_5
-- , Tw.bg_white
-- , Tw.py_2
-- , Tw.px_3
-- , Tw.border
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Tw.shadow_sm
-- , Tw.text_sm
-- , Tw.leading_4
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Css.focus
-- [ Tw.outline_none
-- , Tw.ring_2
-- , Tw.ring_offset_2
-- , Tw.ring_indigo_500
-- ]
-- , Css.hover
-- [ Tw.bg_gray_50
-- ]
-- ]
-- ]
-- [ Html.text "Change" ]
-- ]
-- ]
-- ]
--
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.pt_8
-- , Tw.space_y_6
-- , Bp.sm
-- [ Tw.pt_10
-- , Tw.space_y_5
-- ]
-- ]
-- ]
-- [ Html.div []
-- [ Html.h3
-- [ css
-- [ Tw.text_lg
-- , Tw.leading_6
-- , Tw.font_medium
-- , Tw.text_gray_900
-- ]
-- ]
-- [ Html.text "Personal Information" ]
-- , Html.p
-- [ css
-- [ Tw.mt_1
-- , Tw.max_w_2xl
-- , Tw.text_sm
-- , Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "Use a permanent address where you can receive mail." ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.space_y_6
-- , Bp.sm
-- [ Tw.space_y_5
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "first-name"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "First name" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.type_ "text"
-- , Attr.name "first-name"
-- , Attr.id "first-name"
-- , Attr.attribute "autocomplete" "given-name"
-- , css
-- [ Tw.max_w_lg
-- , Tw.block
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.max_w_xs
-- , Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "last-name"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "Last name" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.type_ "text"
-- , Attr.name "last-name"
-- , Attr.id "last-name"
-- , Attr.attribute "autocomplete" "family-name"
-- , css
-- [ Tw.max_w_lg
-- , Tw.block
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.max_w_xs
-- , Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "email"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "Email address" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "email"
-- , Attr.name "email"
-- , Attr.type_ "email"
-- , Attr.attribute "autocomplete" "email"
-- , css
-- [ Tw.block
-- , Tw.max_w_lg
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "country"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "Country" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.select
-- [ Attr.id "country"
-- , Attr.name "country"
-- , Attr.attribute "autocomplete" "country-name"
-- , css
-- [ Tw.max_w_lg
-- , Tw.block
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.max_w_xs
-- , Tw.text_sm
-- ]
-- ]
-- ]
-- [ Html.option []
-- [ Html.text "United States" ]
-- , Html.option []
-- [ Html.text "Canada" ]
-- , Html.option []
-- [ Html.text "Mexico" ]
-- ]
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "street-address"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "Street address" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.type_ "text"
-- , Attr.name "street-address"
-- , Attr.id "street-address"
-- , Attr.attribute "autocomplete" "street-address"
-- , css
-- [ Tw.block
-- , Tw.max_w_lg
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "city"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "City" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.type_ "text"
-- , Attr.name "city"
-- , Attr.id "city"
-- , Attr.attribute "autocomplete" "address-level2"
-- , css
-- [ Tw.max_w_lg
-- , Tw.block
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.max_w_xs
-- , Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "region"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "State / Province" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.type_ "text"
-- , Attr.name "region"
-- , Attr.id "region"
-- , Attr.attribute "autocomplete" "address-level1"
-- , css
-- [ Tw.max_w_lg
-- , Tw.block
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.max_w_xs
-- , Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_start
-- , Tw.border_t
-- , Tw.border_gray_200
-- , Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "postal-code"
-- , css
-- [ Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Bp.sm
-- [ Tw.mt_px
-- , Tw.pt_2
-- ]
-- ]
-- ]
-- [ Html.text "ZIP / Postal code" ]
-- , Html.div
-- [ css
-- [ Tw.mt_1
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.input
-- [ Attr.type_ "text"
-- , Attr.name "postal-code"
-- , Attr.id "postal-code"
-- , Attr.attribute "autocomplete" "postal-code"
-- , css
-- [ Tw.max_w_lg
-- , Tw.block
-- , Tw.w_full
-- , Tw.shadow_sm
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Css.focus
-- [ Tw.ring_indigo_500
-- , Tw.border_indigo_500
-- ]
-- , Bp.sm
-- [ Tw.max_w_xs
-- , Tw.text_sm
-- ]
-- ]
-- ]
-- []
-- ]
-- ]
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.divide_y
-- , Tw.divide_gray_200
-- , Tw.pt_8
-- , Tw.space_y_6
-- , Bp.sm
-- [ Tw.pt_10
-- , Tw.space_y_5
-- ]
-- ]
-- ]
-- [ Html.div []
-- [ Html.h3
-- [ css
-- [ Tw.text_lg
-- , Tw.leading_6
-- , Tw.font_medium
-- , Tw.text_gray_900
-- ]
-- ]
-- [ Html.text "Notifications" ]
-- , Html.p
-- [ css
-- [ Tw.mt_1
-- , Tw.max_w_2xl
-- , Tw.text_sm
-- , Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "We'll always let you know about important changes, but you pick what else you want to hear about." ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.space_y_6
-- , Tw.divide_y
-- , Tw.divide_gray_200
-- , Bp.sm
-- [ Tw.space_y_5
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.pt_6
-- , Bp.sm
-- [ Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.div
-- [ Attr.attribute "role" "group"
-- , Attr.attribute "aria-labelledby" "label-email"
-- ]
-- [ Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_baseline
-- ]
-- ]
-- ]
-- [ Html.div []
-- [ Html.div
-- [ css
-- [ Tw.text_base
-- , Tw.font_medium
-- , Tw.text_gray_900
-- , Bp.sm
-- [ Tw.text_sm
-- , Tw.text_gray_700
-- ]
-- ]
-- , Attr.id "label-email"
-- ]
-- [ Html.text "By Email" ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.mt_4
-- , Bp.sm
-- [ Tw.mt_0
-- , Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.max_w_lg
-- , Tw.space_y_4
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.relative
-- , Tw.flex
-- , Tw.items_start
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- , Tw.h_5
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "comments"
-- , Attr.name "comments"
-- , Attr.type_ "checkbox"
-- , css
-- [ Tw.h_4
-- , Tw.w_4
-- , Tw.text_indigo_600
-- , Tw.border_gray_300
-- , Tw.rounded
-- , Css.focus
-- [ Tw.ring_indigo_500
-- ]
-- ]
-- ]
-- []
-- ]
-- , Html.div
-- [ css
-- [ Tw.ml_3
-- , Tw.text_sm
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "comments"
-- , css
-- [ Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "Comments" ]
-- , Html.p
-- [ css
-- [ Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "Get notified when someones posts a comment on a posting." ]
-- ]
-- ]
-- , Html.div []
-- [ Html.div
-- [ css
-- [ Tw.relative
-- , Tw.flex
-- , Tw.items_start
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- , Tw.h_5
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "candidates"
-- , Attr.name "candidates"
-- , Attr.type_ "checkbox"
-- , css
-- [ Tw.h_4
-- , Tw.w_4
-- , Tw.text_indigo_600
-- , Tw.border_gray_300
-- , Tw.rounded
-- , Css.focus
-- [ Tw.ring_indigo_500
-- ]
-- ]
-- ]
-- []
-- ]
-- , Html.div
-- [ css
-- [ Tw.ml_3
-- , Tw.text_sm
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "candidates"
-- , css
-- [ Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "Candidates" ]
-- , Html.p
-- [ css
-- [ Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "Get notified when a candidate applies for a job." ]
-- ]
-- ]
-- ]
-- , Html.div []
-- [ Html.div
-- [ css
-- [ Tw.relative
-- , Tw.flex
-- , Tw.items_start
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- , Tw.h_5
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "offers"
-- , Attr.name "offers"
-- , Attr.type_ "checkbox"
-- , css
-- [ Tw.h_4
-- , Tw.w_4
-- , Tw.text_indigo_600
-- , Tw.border_gray_300
-- , Tw.rounded
-- , Css.focus
-- [ Tw.ring_indigo_500
-- ]
-- ]
-- ]
-- []
-- ]
-- , Html.div
-- [ css
-- [ Tw.ml_3
-- , Tw.text_sm
-- ]
-- ]
-- [ Html.label
-- [ Attr.for "offers"
-- , css
-- [ Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "Offers" ]
-- , Html.p
-- [ css
-- [ Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "Get notified when a candidate accepts or rejects an offer." ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.pt_6
-- , Bp.sm
-- [ Tw.pt_5
-- ]
-- ]
-- ]
-- [ Html.div
-- [ Attr.attribute "role" "group"
-- , Attr.attribute "aria-labelledby" "label-notifications"
-- ]
-- [ Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.grid
-- , Tw.grid_cols_3
-- , Tw.gap_4
-- , Tw.items_baseline
-- ]
-- ]
-- ]
-- [ Html.div []
-- [ Html.div
-- [ css
-- [ Tw.text_base
-- , Tw.font_medium
-- , Tw.text_gray_900
-- , Bp.sm
-- [ Tw.text_sm
-- , Tw.text_gray_700
-- ]
-- ]
-- , Attr.id "label-notifications"
-- ]
-- [ Html.text "Push Notifications" ]
-- ]
-- , Html.div
-- [ css
-- [ Bp.sm
-- [ Tw.col_span_2
-- ]
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.max_w_lg
-- ]
-- ]
-- [ Html.p
-- [ css
-- [ Tw.text_sm
-- , Tw.text_gray_500
-- ]
-- ]
-- [ Html.text "These are delivered via SMS to your mobile phone." ]
-- , Html.div
-- [ css
-- [ Tw.mt_4
-- , Tw.space_y_4
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "push-everything"
-- , Attr.name "push-notifications"
-- , Attr.type_ "radio"
-- , css
-- [ Tw.h_4
-- , Tw.w_4
-- , Tw.text_indigo_600
-- , Tw.border_gray_300
-- , Css.focus
-- [ Tw.ring_indigo_500
-- ]
-- ]
-- ]
-- []
-- , Html.label
-- [ Attr.for "push-everything"
-- , css
-- [ Tw.ml_3
-- , Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "Everything" ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "push-email"
-- , Attr.name "push-notifications"
-- , Attr.type_ "radio"
-- , css
-- [ Tw.h_4
-- , Tw.w_4
-- , Tw.text_indigo_600
-- , Tw.border_gray_300
-- , Css.focus
-- [ Tw.ring_indigo_500
-- ]
-- ]
-- ]
-- []
-- , Html.label
-- [ Attr.for "push-email"
-- , css
-- [ Tw.ml_3
-- , Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "Same as email" ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.flex
-- , Tw.items_center
-- ]
-- ]
-- [ Html.input
-- [ Attr.id "push-nothing"
-- , Attr.name "push-notifications"
-- , Attr.type_ "radio"
-- , css
-- [ Tw.h_4
-- , Tw.w_4
-- , Tw.text_indigo_600
-- , Tw.border_gray_300
-- , Css.focus
-- [ Tw.ring_indigo_500
-- ]
-- ]
-- ]
-- []
-- , Html.label
-- [ Attr.for "push-nothing"
-- , css
-- [ Tw.ml_3
-- , Tw.block
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- ]
-- ]
-- [ Html.text "No push notifications" ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- ]
-- , Html.div
-- [ css
-- [ Tw.pt_5
-- ]
-- ]
-- [ Html.div
-- [ css
-- [ Tw.flex
-- , Tw.justify_end
-- ]
-- ]
-- [ Html.button
-- [ Attr.type_ "button"
-- , css
-- [ Tw.bg_white
-- , Tw.py_2
-- , Tw.px_4
-- , Tw.border
-- , Tw.border_gray_300
-- , Tw.rounded_md
-- , Tw.shadow_sm
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.text_gray_700
-- , Css.focus
-- [ Tw.outline_none
-- , Tw.ring_2
-- , Tw.ring_offset_2
-- , Tw.ring_indigo_500
-- ]
-- , Css.hover
-- [ Tw.bg_gray_50
-- ]
-- ]
-- ]
-- [ Html.text "Cancel" ]
-- , Html.button
-- [ Attr.type_ "submit"
-- , css
-- [ Tw.ml_3
-- , Tw.inline_flex
-- , Tw.justify_center
-- , Tw.py_2
-- , Tw.px_4
-- , Tw.border
-- , Tw.border_transparent
-- , Tw.shadow_sm
-- , Tw.text_sm
-- , Tw.font_medium
-- , Tw.rounded_md
-- , Tw.text_white
-- , Tw.bg_indigo_600
-- , Css.focus
-- [ Tw.outline_none
-- , Tw.ring_2
-- , Tw.ring_offset_2
-- , Tw.ring_indigo_500
-- ]
-- , Css.hover
-- [ Tw.bg_indigo_700
-- ]
-- ]
-- ]
-- [ Html.text "Save" ]
-- ]
-- ]
-- ]