noredink-ui/styleguide-app/Examples/RadioButton.elm

251 lines
7.8 KiB
Elm
Raw Normal View History

2020-07-30 21:12:30 +03:00
module Examples.RadioButton exposing
( example
, State, Msg
)
{-|
@docs example
@docs State, Msg
-}
import Category exposing (Category(..))
import Css exposing (..)
import Debug.Control as Control exposing (Control)
2020-07-30 21:12:30 +03:00
import Dict exposing (Dict)
import Example exposing (Example)
import Html.Styled as Html exposing (..)
2020-07-30 21:12:30 +03:00
import Html.Styled.Attributes exposing (css)
import KeyboardSupport exposing (Direction(..), Key(..))
2020-07-30 21:39:16 +03:00
import Nri.Ui.Button.V10 as Button
import Nri.Ui.Data.PremiumLevel as PremiumLevel exposing (PremiumLevel)
2020-07-30 21:12:30 +03:00
import Nri.Ui.Heading.V2 as Heading
import Nri.Ui.Modal.V10 as Modal
2020-11-07 02:57:10 +03:00
import Nri.Ui.RadioButton.V2 as RadioButton
2020-07-30 21:39:16 +03:00
import Nri.Ui.Text.V5 as Text
2020-07-30 21:12:30 +03:00
{-| -}
example : Example State Msg
example =
2020-09-09 21:43:10 +03:00
{ name = "RadioButton"
2020-11-07 02:57:10 +03:00
, version = 2
2020-07-30 21:12:30 +03:00
, state = init
, update = update
2020-07-30 21:39:16 +03:00
, subscriptions = subscriptions
2020-07-30 21:12:30 +03:00
, view = view
2021-09-04 18:47:56 +03:00
, categories = [ Inputs ]
2020-07-30 21:47:32 +03:00
, keyboardSupport =
2020-11-20 21:42:26 +03:00
[ { keys = [ Arrow Left ]
2020-11-07 02:57:10 +03:00
, result = "Move the focus & select the radio button to the left"
}
2020-11-20 21:42:26 +03:00
, { keys = [ Arrow Right ]
2020-11-07 02:57:10 +03:00
, result = "Move the focus & select the radio button to the right"
}
2020-11-20 21:42:26 +03:00
, { keys = [ Space ]
2020-11-07 02:57:10 +03:00
, result = "Select the current radio button"
}
]
2020-07-30 21:12:30 +03:00
}
{-| -}
view : State -> List (Html Msg)
view model =
[ Heading.h3 [] [ Html.text "RadioButton" ]
, Heading.h4 [] [ Html.text "view" ]
, viewVanilla model
, Heading.h4 [] [ Html.text "premium" ]
, viewPremium model
2020-07-30 21:39:16 +03:00
, Modal.info
{ title = "Go Premium!"
2020-07-30 21:39:16 +03:00
, wrapMsg = ModalMsg
, focusManager =
Modal.MultipleFocusableElements
(\{ firstFocusableElement, autofocusElement, lastFocusableElement, closeButton } ->
{ content =
[ Text.mediumBody [] [ text "Often, we'll launch a modal showing the benefits of premium when a locked radio button is clicked." ]
, closeButton (autofocusElement :: firstFocusableElement)
]
, footer =
[ Button.button "Okay"
[ Button.large
, Button.onClick (ModalMsg Modal.close)
, Button.custom lastFocusableElement
]
]
}
)
}
[]
2020-07-30 21:39:16 +03:00
model.modal
2020-07-30 21:12:30 +03:00
]
viewVanilla : State -> Html Msg
viewVanilla state =
2021-09-04 18:49:10 +03:00
div []
[ RadioButton.view
{ label = "Cats"
, value = "Cats"
, name = "radio-button-examples"
, selectedValue = state.selectedValue
, onSelect = Select
, valueToString = identity
}
, RadioButton.view
{ label = "Dogs"
, value = "Dogs"
, name = "radio-button-examples"
, selectedValue = state.selectedValue
, onSelect = Select
, valueToString = identity
}
]
viewPremium : State -> Html Msg
viewPremium state =
let
premiumConfig =
Control.currentValue state.premiumControl
in
2021-09-09 17:51:44 +03:00
div []
[ Heading.h4 [] [ Html.text "Premium Radio Buttons" ]
, Html.div [ css [ Css.margin (Css.px 8) ] ]
[ Control.view SetPremiumControl state.premiumControl
|> Html.fromUnstyled
]
, RadioButton.premium
{ label = "Hedgehog (Free)"
, value = "Hedgehogs"
, name = "radio-button-examples"
, selectedValue = state.selectedValue
, teacherPremiumLevel = premiumConfig.teacherPremiumLevel
, contentPremiumLevel = PremiumLevel.Free
, onSelect = Select
2020-07-30 21:47:32 +03:00
-- TODO:
-- the next version of the RadioComponent will handle focus correctly,
-- including re-capturing the focus when the modal closes.
-- While we could change premiumMsg to be String -> msg now,
-- and use the correct id, there's not much point in doing
-- so yet since the radio doesn't handle focus correctly.
, premiumMsg = ModalMsg (Modal.open "fake-id")
, valueToString = identity
, showPennant = premiumConfig.showPennant
, isDisabled = False
}
, RadioButton.premium
{ label = "Hedgehodge (Premium)"
, value = "Hedgehodges"
, name = "radio-button-examples"
, selectedValue = state.selectedValue
, teacherPremiumLevel = premiumConfig.teacherPremiumLevel
, contentPremiumLevel = PremiumLevel.PremiumWithWriting
, onSelect = Select
2020-07-30 21:47:32 +03:00
-- TODO:
-- the next version of the RadioComponent will handle focus correctly,
-- including re-capturing the focus when the modal closes.
-- While we could change premiumMsg to be String -> msg now,
-- and use the correct id, there's not much point in doing
-- so yet since the radio doesn't handle focus correctly.
, premiumMsg = ModalMsg (Modal.open "fake-id")
, valueToString = identity
, showPennant = premiumConfig.showPennant
, isDisabled = False
}
, RadioButton.premium
{ label = "Disabled"
, value = "Disabled"
, name = "radio-button-examples"
, selectedValue = state.selectedValue
, teacherPremiumLevel = premiumConfig.teacherPremiumLevel
, contentPremiumLevel = PremiumLevel.PremiumWithWriting
, onSelect = Select
2020-07-30 21:47:32 +03:00
-- TODO:
-- the next version of the RadioComponent will handle focus correctly,
-- including re-capturing the focus when the modal closes.
-- While we could change premiumMsg to be String -> msg now,
-- and use the correct id, there's not much point in doing
-- so yet since the radio doesn't handle focus correctly.
, premiumMsg = ModalMsg (Modal.open "fake-id")
, valueToString = identity
, showPennant = premiumConfig.showPennant
, isDisabled = True
}
]
{-| -}
type alias State =
{ selectedValue : Maybe String
2020-07-30 21:39:16 +03:00
, modal : Modal.Model
, premiumControl : Control PremiumConfig
}
2020-07-30 21:12:30 +03:00
{-| -}
init : State
init =
{ selectedValue = Nothing
2020-07-30 21:39:16 +03:00
, modal = Modal.init
, premiumControl = initPremiumControls
}
2020-07-30 21:12:30 +03:00
type alias PremiumConfig =
{ teacherPremiumLevel : PremiumLevel
, showPennant : Bool
}
initPremiumControls : Control PremiumConfig
initPremiumControls =
Control.record PremiumConfig
|> Control.field "teacherPremiumLevel"
(Control.choice
[ ( "Free", Control.value PremiumLevel.Free )
, ( "Premium", Control.value PremiumLevel.PremiumWithWriting )
]
)
|> Control.field "showPennant" (Control.bool False)
type Msg
2020-07-30 21:39:16 +03:00
= ModalMsg Modal.Msg
| Select String
| SetPremiumControl (Control PremiumConfig)
| NoOp
2020-07-30 21:12:30 +03:00
{-| -}
update : Msg -> State -> ( State, Cmd Msg )
update msg model =
case msg of
2020-07-30 21:39:16 +03:00
ModalMsg modalMsg ->
let
( modal, cmd ) =
Modal.update { dismissOnEscAndOverlayClick = True }
modalMsg
model.modal
in
( { model | modal = modal }, Cmd.map ModalMsg cmd )
Select value ->
( { model | selectedValue = Just value }, Cmd.none )
SetPremiumControl premiumControl ->
( { model | premiumControl = premiumControl }, Cmd.none )
NoOp ->
( model, Cmd.none )
2020-07-30 21:39:16 +03:00
subscriptions : State -> Sub Msg
subscriptions { modal } =
Sub.map ModalMsg (Modal.subscriptions modal)