This is an alternative site for discovering Elm packages. You may be looking for the official Elm package site instead.
We were not able to find the expected elm-package.json file at this tag.
Tag 8.0.1
Committed At 2019-05-15 16:03:37 UTC

Modules

    README

      🌲           🌲                             🌲          
     🌲🌲   🌲🌲 🌲      🌲   🌲  🌲   🌲     🌲  🌲      🌲🌲             🌲    
    🌲🌲🌲  🌲🌲🌲 🌲  🌲🌲🌲 🌲🌲  🌲  🌲🌲🌲 🌲🌲🌲   🌲 🌲🌲        🌲🌲      🌲   
    

    elm-arborist

    Drag-and-drop interface to edit, dissect and-rearrange tree structures, with nodes holding any data type you wish. Here is a demo, and here some docs.

    Getting started

    TLDR: simple app example (run with cd examples && elm reactor, then open http://localhost:8000/Simple.elm)

    First things first, we need to specify what kind of data structure our tree's nodes will hold. For this demo, it will be a record with a question and an answer.

    type alias MyNode =
        { question : String
        , answer : String
        }
    
    exampleNode = MyNode "How are you?" "Fine thanks"
    

    We can then use the Arborist.Tree module to recursively construct a tree structure:

    import Arborist.Tree as Tree
    
    tree : Tree.Tree MyNode
    tree =
      Tree.Node (MyNode "Q1" "A1")
        [ Tree.Node (MyNode "Q2" "A2") []
        , Tree.Node (MyNode "Q3" "A3")
            [ Tree.Node ( "Q4", "A4" )
            ]
        ]
    

    Now, we can now define a model for your app:

    import Arborist
    import Arborist.Tree as Tree
    
    type alias Model =
      { tree : Tree.Tree MyNode
      , arborist : Arborist.State
      }
    

    Next, we configure the editor:

    arboristSettings : List (Arborist.Setting MyNode)
    arboristSettings =
        [ Settings.keyboardNavigation True
        , Settings.defaultNode (MyNode "A" "Q")
        , Settings.nodeWidth 100
        , Settings.level 80
        , Settings.gutter 20
        ]
    

    Rendering the editor will look like this:

    view : Model -> Html Msg
    view model =
        Arborist.view
            []
            { state = model.arborist
            , tree = model.tree
            , settings = arboristSettings
            -- We get to these two in a second
            , nodeView = nodeView
            , toMsg = Arborist
            }
    

    Now let's look at the two bits we left out: nodeView and toMsg.

    nodeView

    This function specifies how a node should be displayed within its bounding box, and looks like this:

    -- Don't worry about `context` for now
    nodeView : Arborist.NodeView MyNode Msg
    nodeView context maybeNode =
        case maybeNode of
            Just node ->
                text node.question
    
            Nothing ->
                text "+ add node"
    

    toMsg

    Arborist uses the teach-me-how-to-message pattern, passing an Arborist.Updater to your app's update function. The updater is a function that works out the new tree and new state based on the previous tree and previous state.

    type Msg
        -- This is the message constructor that goes into the `toMsg` field above
        = Arborist (Arborist.Updater MyNode)
    
    update : Msg -> Model -> ( Model, Cmd Msg )
    update msg model =
        case msg of
            Arborist updater ->
                let
                    ( newState, newTree ) =
                        updater model.arborist model.tree
                in
                ( { model
                    | arborist = newState
                    , tree = newTree
                  }
                , Cmd.none
                )
    

    Arborist cannot give new values straight away because mouse events are fired so quickly that they can undo each others' changes in the runtime, hence the complexity in the update logic above.

    And that's it - your very own tree editor is ready.

    Going further

    Context

    The context object exposed in the nodeView function above provides, as its name suggests, contextual information to the node when it is rendered, including their parent node and list of siblings. You may for instance want to signal to the user that a child can't be older than their parent in the family tree as they edit it, but traversing the tree to find that information is tedious and inefficient - so Arborist gives you access to it directly.

    This should work for a large number of tree editing cases. If you need a broader context, you will need to traverse the tree yourself.

    UX goodies

    In the settings module, you will find setup instructions for advanced features like node clustering and keyboard navigation. For a real-world example, have a look at the elm-arborist landing page.

    Contributing

    Contributions welcome - please feel free to go ahead with issues and PR's, or reach out to me on Elm Slack at @peterszerzo.

    License

    MIT.

    🌲🌲🌲  🌲🌲🌲 🌲  🌲🌲🌲 🌲🌲  🌲  🌲🌲🌲 🌲🌲🌲   🌲 🌲🌲        🌲🌲      🌲   
     🌲🌲   🌲🌲 🌲      🌲   🌲  🌲   🌲     🌲  🌲      🌲🌲             🌲    
      🌲           🌲                             🌲