Skip to content

GoIlluminate/elm-fancy-daterangepicker

Repository files navigation

elm-fancy-daterangepicker

elm install goilluminate/elm-fancy-daterangepicker

A reusable daterange picker in Elm.

DateRangePicker

Usage

Initializing

The DateRangePicker.init function initialises the DateRangePicker's state.

init : Model
init =
    { ...
        dateRangePicker = DateRangePicker.init
      ...
    }

View

The DateRangePicker can be displayed in the view using the DateRangePicker.view function. It returns its own message type so you should wrap it in one of your own messages using Html.map. You will need to have fetched the currentTime and localZone beforehand using Time.now and Time.here

type Msg
    = ...
    | DatePickerMsgs DateRangePicker.Msg
    | ...

view : Model -> Html Msg
view model =
    ...
    div []
        [ DateRangePicker.view 
            model.currentTime
            model.localZone
            model.dateRangePicker |> Html.map DatePickerMsgs
        ]

There is a helper method for opening the daterangepicker, which puts an onClick with the appropriate message onto the html element.

button [ DateRangePicker.open "datepicker-button", Html.Attribute.id "datepicker-button" ] [ text "Open Picker" ]

Update

To handle Msg in your update function, you should unwrap the DateRangePicker.Msg and pass it down to the DateRangePicker.update function. The DateRangePicker.update function returns:

  • the new model
  • any command
    DatePickerMsgs msg_ ->
        let
            ( newDateRangePicker, dateRangePickerCmd ) =
                DateRangePicker.update msg_ model.dateRangePicker
        in
        ( { model | dateRangePicker = newDateRangePicker }, Cmd.map DatePickerMsgs dateRangePickerCmd )

Subscriptions

You will need to hook up subscriptions for the daterangepicker to fully function. It will also need the current time and local zone.

subscriptions : Model -> Sub Msg
subscriptions model =
    let
        pickerSubscriptions =
            case ( model.currentTime, model.localZone ) of
                ( Just currentTime, Just localZone ) ->
                    DateRangePicker.subscriptions model.datePicker currentTime localZone

                _ ->
                    Sub.none
    in
    Sub.map DatePickerMsgs pickerSubscriptions

Settings

The DateRangePicker has several settings which can be changed as wanted. You can set these at init time with initWithOptions. If you don't want to change all the options you can combine with this defaultConfig like so:

init : Model
init =
    { ...
        dateRangePicker = DateRangePicker.initWithOptions
                              { defaultConfig
                                  | calendarType = TwoMonths
                                  , dateSelectionType = DateSelection
                              }
      ...
    }

There is also a concept of Presets which can allow a user to quickly select a date or dateRange which is commonly used. There are a couple premade presets that you can use as well.

The CustomPresets are set relative to the current date. All of them can be set at init time.

init : Model
init =
    { ...
        dateRangePicker = DateRangePicker.initWithOptions
                              { defaultConfig
                                  | presets =
                                      [ DateRangePicker.Today
                                      , DateRangePicker.Yesterday
                                      , DateRangePicker.Custom <|
                                          { intervalStart = DateRangePicker.Days
                                          , intervalStartValue = -3
                                          , intervalEnd = DateRangePicker.Days
                                          , intervalEndValue = -1
                                          , display = "Past Three Days"
                                          }
                                      , DateRangePicker.PastWeek
                                      , DateRangePicker.PastMonth
                                      ]
                              }
      ...
    }

CSS

The CSS for the date pickers are distributed separately. You can grab the compiled CSS from here or you can grab the SCSS source from here. There is both a light and dark theme available. You will need to have a parent element which sets the appropriate color class.

div [Attributes.class "theme-light"] [DateRangePicker.view ...]

or

div [Attributes.class "theme-dark"] [DateRangePicker.view ...]

Map.! compiler error

If you run into the compiler error Map.!: given key is not an element in the map, try moving "justinmimbs/date" into your direct dependencies. It may fix the error.

Development

Prerequisites

  • Ruby
  • Rake gem install rake

Running the example

To run the example run rake. This will: - install all node modules - install all elm packages - run the webpack dev server with hmr on localhost:8080

Tests

To run the tests run rake test. This will: - install all elm packages in the tests folder - run elm-test

Note you need to have elm-test installed globally

npm install elm-test -g