circuithub / elm-dropdown / Dropdown

Flexible dropdown component which serves as a foundation for custom dropdowns, select–inputs, popovers, and more.

Example

Basic example of usage:

init : Model
init =
    { myDropdownIsOpen = False }

type alias Model =
    { myDropdownIsOpen : Dropdown.State }

type Msg
    = ToggleDropdown Bool

update : Msg -> Model -> Model
update msg model =
    case msg of
        ToggleDropdown newState ->
            { model | myDropdownIsOpen = newState }

view : Model -> Html Msg
view { myDropdownIsOpen } =
    div []
        [ dropdown
            { identifier = "my-dropdown"
            , toggleEvent = Dropdown.OnClick
            , drawerVisibleAttribute = class "visible"
            , onToggle = ToggleDropdown
            , layout =
                \{ toDropdown, toToggle, toDrawer } ->
                    toDropdown div
                        []
                        [ toToggle button [] [ text "Toggle" ]
                        , toDrawer div
                            []
                            [ button [] [ text "Option 1" ]
                            , button [] [ text "Option 2" ]
                            , button [] [ text "Option 3" ]
                            ]
                        ]
            , isToggled = myDropdownIsOpen
            }
        ]

Configuration


type alias State =
Basics.Bool

Indicates wether the dropdown's drawer is visible or not.


type alias Config msg html =
{ identifier : String
, toggleEvent : ToggleEvent
, drawerVisibleAttribute : Html.Attribute msg
, onToggle : State -> msg
, layout : Builder msg -> html
, isToggled : State 
}

Configuration.


type ToggleEvent
    = OnClick
    | OnHover
    | OnFocus

Used to set the event on which the dropdown's drawer should appear or disappear.

Views

dropdown : Config msg html -> html

The convenient way of building a dropdown. Everything can be done with this one function.

Use the Dropdown.Builder that is provided in order to layout the elements of the dropdown however you wish.

Dropdown.dropdown
    { identifier = "my-dropdown"
    , toggleEvent = Dropdown.OnClick
    , drawerVisibleAttribute = class "visible"
    , onToggle = ToggleDropdown
    , layout =
        \{ toDropdown, toToggle, toDrawer } ->
            toDropdown div
                []
                [ toToggle button [] [ text "Toggle" ]
                , toDrawer div
                    []
                    [ button [] [ text "Option 1" ]
                    , button [] [ text "Option 2" ]
                    , button [] [ text "Option 3" ]
                    ]
                ]
    , isToggled = myDropdownState
    }

root : { config | identifier : String, toggleEvent : ToggleEvent, onToggle : State -> msg, isToggled : State } -> (List (Html.Attribute msg) -> List (Html msg) -> Html msg) -> List (Html.Attribute msg) -> List (Html msg) -> Html msg

An alternative way to roll your own dropdown using the given config, isToggled, toggle, and drawer.

type alias SimpleDropdownConfig msg =
    { identifier : String
    , toggleEvent : ToggleEvent
    , drawerVisibleAttribute : Attribute msg
    , onToggle : State -> msg
    , isToggled : State
    , toggleAttrs : List (Attribute msg)
    , toggleLabel : Html msg
    , drawerAttrs : List (Attribute msg)
    , drawerItems : List (Html msg)
    }

simpleDropdown : SimpleDropdownConfig msg -> Html msg
simpleDropdown config =
    root config
        div
        []
        [ toggle config button config.toggleAttrs [ config.toggleLabel ]
        , drawer config div config.drawerAttrs config.drawerItems
        ]

toggle : { config | onToggle : State -> msg, toggleEvent : ToggleEvent, isToggled : State } -> (List (Html.Attribute msg) -> List (Html msg) -> Html msg) -> List (Html.Attribute msg) -> List (Html msg) -> Html msg

Transforms the given HTML-element into a working toggle for your dropdown. See dropdown on how to use in combination with drawer.

Example of use:

toggle
    { onToggle = DropdownToggle, toggleEvent = Dropdown.OnClick, isToggled = myDropdownIsOpen }
    myDropdownState
    button
    [ class "myButton" ]
    [ text "More options" ]

drawer : { config | drawerVisibleAttribute : Html.Attribute msg, isToggled : State } -> (List (Html.Attribute msg) -> List (Html msg) -> Html msg) -> List (Html.Attribute msg) -> List (Html msg) -> Html msg

Transforms the given HTML-element into a working drawer for your dropdown. See dropdown on how to use in combination with toggle.

Example of use:

drawer
    { drawerVisibleAttribute = class "visible", isToggled = myDropdownIsOpen }
    div
    [ class "myDropdownDrawer" ]
    [ button [ onClick NewFile ] [ text "New" ]
    , button [ onClick OpenFile ] [ text "Open..." ]
    , button [ onClick SaveFile ] [ text "Save" ]
    ]