I looked for a split-pane for Elm and found things that don't seem straightforward to use.
doodledood/elm-split-pane is not compatible with Elm 0.19.1, so I guess I would either have to switch to Elm 0.18, or convert this to Elm 0.19.1 to use it. Also it is defined in terms of Elm HTML, not Elm UI.
I also found https://github.com/ellie-app/ellie/blob/master/assets/src/Ellie/Ui/SplitPane.elm. That involves a bunch of custom JavaScript, and it's not obvious to me how tightly coupled it is with the rest of the app.
I'm using a split pane in my elm project with elm-ui. I took this SplitPane elm-html-based package https://github.com/doodledood/elm-split-pane, copied it's source into my project and converted its internals to return Element msg from its view function by wrapping the content and the attributes.
Here is the source code of the converted functions:
view : ViewConfig msg -> Element msg -> Element msg -> State -> Element msg
view (ViewConfig viewConfig) firstView secondView (State state) =
let
splitter =
getConcreteSplitter viewConfig state.orientation state.dragState
in
case state.orientation of
Horizontal ->
row
(paneContainerStyle state.orientation
++ [ width fill ]
)
[ el (firstChildViewStyle (State state)) firstView
, splitter
, el (secondChildViewStyle (State state)) secondView
]
Vertical ->
column (paneContainerStyle state.orientation)
[ el (firstChildViewStyle (State state)) firstView
, splitter
, el (secondChildViewStyle (State state)) secondView
]
viewReversed : ViewConfig msg -> Element msg -> Element msg -> State -> Element msg
viewReversed (ViewConfig viewConfig) firstView secondView (State state) =
let
splitter =
getConcreteSplitter viewConfig state.orientation state.dragState
in
case state.orientation of
Horizontal ->
row
(paneContainerStyle state.orientation
++ [ width fill ]
)
[ el (secondChildViewStyle (State state)) secondView
, splitter
, el (firstChildViewStyle (State state)) firstView
]
Vertical ->
column (paneContainerStyle state.orientation)
[ el (secondChildViewStyle (State state)) firstView
, splitter
, el (firstChildViewStyle (State state)) firstView
]
getConcreteSplitter :
{ toMsg : Msg -> msg
, splitter : Maybe (CustomSplitter msg)
}
-> Orientation
-> DragState
-> Element msg
getConcreteSplitter viewConfig orientation4 dragState =
case viewConfig.splitter of
Just (CustomSplitter splitter) ->
splitter
Nothing ->
case createCustomSplitter viewConfig.toMsg <| createDefaultSplitterDetails orientation4 dragState of
CustomSplitter defaultSplitter ->
defaultSplitter
Here are the styles functions:
paneContainerStyle : Orientation -> List (Attribute msg)
paneContainerStyle orientation5 =
[ style "overflow" "hidden"
, style "display" "flex"
, style "flexDirection"
(case orientation5 of
Horizontal ->
"row"
Vertical ->
"column"
)
, style "justifyContent" "center"
, style "alignItems" "center"
, style "width" "100%"
, style "height" "100%"
, style "boxSizing" "border-box"
]
|> List.map Element.htmlAttribute
firstChildViewStyle : State -> List (Attribute msg)
firstChildViewStyle (State state) =
case state.splitterPosition of
Px px2 ->
let
v =
(String.fromFloat <| toFloat (getValue px2)) ++ "px"
in
case state.orientation of
Horizontal ->
[ style "display" "flex"
, style "width" v
, style "height" "100%"
, style "overflow" "hidden"
, style "boxSizing" "border-box"
, style "position" "relative"
]
|> List.map Element.htmlAttribute
Vertical ->
[ style "display" "flex"
, style "width" "100%"
, style "height" v
, style "overflow" "hidden"
, style "boxSizing" "border-box"
, style "position" "relative"
]
|> List.map Element.htmlAttribute
Percentage p ->
let
v =
String.fromFloat <| getValue p
in
[ style "display" "flex"
, style "flex" v
, style "width" "100%"
, style "height" "100%" -- pz edit
, style "overflow" "hidden"
, style "boxSizing" "border-box"
, style "position" "relative"
]
|> List.map Element.htmlAttribute
secondChildViewStyle : State -> List (Attribute msg)
secondChildViewStyle (State state) =
case state.splitterPosition of
Px _ ->
[ style "display" "flex"
, style "flex" "1"
, style "width" "100%"
, style "height" "100%"
, style "overflow" "hidden"
, style "boxSizing" "border-box"
, style "position" "relative"
]
|> List.map Element.htmlAttribute
Percentage p ->
let
v =
String.fromFloat <| 1 - getValue p
in
[ style "display" "flex"
, style "flex" v
, style "width" "100%"
, style "height" "100%"
, style "overflow" "hidden"
, style "boxSizing" "border-box"
, style "position" "relative"
]
|> List.map Element.htmlAttribute
Uri