Skip to content

Different Map for Selected Item #2

@cjduncana

Description

@cjduncana

I propose to add a new function to NonEmptyArray to map different functions depending on if an item in the list is selected or not. You can find the function definition below.

I am currently creating an interface inspired by Gmail's tablet interface: a list view on the left, and a detail view on the right. The user would select an item from the list, and the app would display its details in the view to the right. The design asks for the selected item to be visually distinct from the rest of the items.

Whenever I want to select or modify one element in a list without knowing beforehand its position in the list, I reach for Array and its get and set functions. Other users solve this problem using List and its indexedMap and foldl functions by checking if the index matches the one given. I avoid this since these functions traverse the whole list, which is always going to be slower compared to Array especially as the list grows longer. NonEmptyArray benefits the app since I know that there is always going to be at least an item, so I can use getSelected without dealing with Maybe.

I created two functions Int -> Item -> Html Msg, one for when the item is selected and the other for the other items. I also created a function that maps the items with these two functions:

indexedMapSelected : { selected : Int -> a -> b, other : Int -> a -> b } -> NonEmptyArray a -> NonEmptyArray b
indexedMapSelected { selected, other } array =
    let
        choose index =
            if index == NonEmptyArray.selectedIndex array then
                selected index
            else
                other index
    in
    NonEmptyArray.indexedMap choose array

Yesterday, I mentioned to this package owner the List.Selection.mapSelected function as inspiration for the function I created, but that was before I realize I need the index in the Array to pass in a Msg.

mapSelected : { selected : a -> b, other : a -> b } -> NonEmptyArray a -> NonEmptyArray b
mapSelected { selected, other } array =
    let
        choose index =
            if index == NonEmptyArray.selectedIndex array then
                selected
            else
                other
    in
    NonEmptyArray.indexedMap choose array

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions