Helpers for DOM nodes as part of an Interface
.
These are primitives used for svg and html
(filling the same role as elm/virtual-dom
)
Plain text or an Element
. Create using text
and element
text : String -> Node future_
Plain text DOM Node
RecordWithoutConstructorFunction { header : Web.DomElementHeader future
, subs : List (Node future)
}
A tagged DOM node that can itself contain child nodes
element : String -> List (Modifier future) -> List (Node future) -> Node future
Create a DOM element with a given tag, Modifier
s and sub-nodes.
For example to get <p>flying</p>
Web.Dom.element "p"
[]
[ Web.Dom.text "flying" ]
To create SVG elements, use Web.Svg.element
elementNamespaced : String -> String -> List (Modifier future) -> List (Node future) -> Node future
Create a DOM element with a given namespace, tag, Modifier
s and sub-nodes.
For example, Web.Svg
defines its elements using
element : String -> List (Modifier future) -> List (DomNode future) -> DomNode future
element tag modifiers subs =
Web.Dom.elementNamespaced "http://www.w3.org/2000/svg" tag modifiers subs
futureMap : (future -> mappedFuture) -> Node future -> Node mappedFuture
Wire events from this Web.Dom.Node
to a specific event, for example
buttonUi "start"
|> Web.Dom.futureMap (\Clicked -> StartButtonClicked)
with
buttonUi : String -> Web.Dom.Node ButtonEvent
buttonUi label =
Web.Dom.element "button"
[ Web.Dom.listenTo "click"
|> Web.Dom.modifierFutureMap (\_ -> Clicked)
]
[ Web.Dom.text label ]
type ButtonEvent
= Clicked
render : Node future -> Web.Interface future
An Interface
for displaying a given Web.Dom.Node
Rope (ModifierSingle future)
Setting of a Web.Dom.Element
.
To create one, use attribute
, style
, listenTo
etc.
To combine multiple, use Web.Dom.modifierBatch
and Web.Dom.modifierNone
For example to get <a href="https://elm-lang.org">elm</a>
Web.Dom.element "a"
[ Web.Dom.attribute "href" "https://elm-lang.org" ]
[ Web.Dom.text "elm" ]
Btw: If you can think of a nicer name for this like "customization", "characteristic" or "aspect", please open an issue.
class
in <div class="greeting"></div>
className
in div.className = "greeting"
But don't be surprised: There are cases where
For example, trying to reset the text inside a a text input with
Web.Dom.attribute "value" "user input"
-- then later replace it with
Web.Dom.attribute "value" ""
will only provide a default value and has no effect on the currently written text, so you'll have to use
Web.Dom.stringProperty "value" ""
Similarly for checkboxes:
Web.Dom.boolProperty "checked" False
Maybe a rule of thumb is: Use properties to set anything related to interactivity and attributes for everything else.
If you have some opinions or better explanations, please open an issue.
modifierFutureMap : (future -> mappedFuture) -> Modifier future -> Modifier mappedFuture
Wire events from this Modifier
to a specific event.
Web.Dom.listen "click" |> Web.Dom.modifierFutureMap (\_ -> ButtonClicked)
modifierBatch : List (Modifier future) -> Modifier future
Combine multiple Modifier
s into one.
modifierNone : Modifier future_
Doing nothing as a Modifier
. These two examples are equivalent:
Web.Dom.modifierBatch
[ a, Web.Dom.modifierNone, b ]
and
Web.Dom.modifierBatch
(List.filterMap identity
[ a |> Just, Nothing, b |> Just ]
)
attribute : String -> String -> Modifier future_
A key-value attribute Modifier
attributeNamespaced : String -> String -> String -> Modifier future_
A namespaced key-value attribute Modifier
.
For example, you could define an SVG xlink href attribute as
attributeXlinkHref : String -> Modifier msg
attributeXlinkHref value =
Web.Dom.attributeNamespaced "http://www.w3.org/1999/xlink" "xlink:href" value
style : String -> String -> Modifier future_
A key-value style Modifier
boolProperty : String -> Basics.Bool -> Modifier future_
A key-bool value DOM property Modifier
stringProperty : String -> String -> Modifier future_
A key-string value DOM property Modifier
listenTo : String -> Modifier Json.Decode.Value
Listen for a specific DOM event on the Web.Dom.Element
.
Use modifierFutureMap
to wire this to a specific event.
If you want to override the browser's default behavior for that event,
use listenToPreventingDefaultAction
listenToPreventingDefaultAction : String -> Modifier Json.Decode.Value
Like listenTo
but preventing the browser's default action.
That's for example how elm's Browser.Events.onSubmit
prevents the form from changing the page’s location:
submitListen : Web.Dom.Modifier ()
submitListen =
Web.Dom.listenToPreventingDefaultAction "submit"
|> Web.Dom.modifierFutureMap (\_ -> ())
scrollToShow : { x : Web.DomElementVisibilityAlignment, y : Web.DomElementVisibilityAlignment } -> Modifier future_
Ensure a given initial DomElementVisibilityAlignment
in both directions.
Unlike style
s,
this is just an initial configuration
which can be changed by user actions.
So adding e.g. scrollToShow { y = Web.DomElementStart, x = Web.DomElementStart }
will scroll to the top left once the next render happens
but will not prevent users from scrolling away.
Note: Uses Element.scrollIntoView
scrollPositionRequest : Modifier { fromLeft : Basics.Float, fromTop : Basics.Float }
Getting the current scroll position from the left and top.
Use in combination with scrollToPosition
to implement saving and restoring scroll position even when users had navigated off a URL.
scrollToPosition : { fromLeft : Basics.Float, fromTop : Basics.Float } -> Modifier future_
Ensure a given initial scroll position in both directions.
To move to the edge in a direction, use scrollToShow
instead.
Unlike style
s,
this is just an initial configuration
which can be changed by user actions.
So adding e.g. scrollToPosition ...
will scroll once the next render happens
but will not prevent users from scrolling away.
Exposed so can for example simulate it more easily in tests, add a debugger etc.
An individual Modifier
.
Create using attribute
, style
, listenTo
etc.