PopOver

A floating container for any content, such as navigation menus, help texts, etc.

Basic Example

A PopOver is generated by the factory function popOver.

By clicking on the building block created by popOverButton or Space with focused popOverButton, the floating container created by popOverPanel is shown as well.

Esc or a click outside the visible container closes the popOverPanel.

data class Solution(val name: String, val description: String, val icon: String)

val solutions = listOf(
Solution("fritz2", "Cool web framework for building modern SPAs", fritz2),
Solution("Headless", "Create fully functional and customized components", HeroIcons.academic_cap),
Solution("Tailwind", "Nice CSS framework for styling your application", HeroIcons.color_swatch)
)

popOver {
popOverButton {
span { +"Open Popover" }
}

popOverPanel {
solutions.forEach { item ->
a {
div {
svg { content(item.icon) }
}
div {
p { +item.name }
p { +item.description }
}
}
}
}
}

Open State

PopOver is an OpenClose component. There are different Flows and Handler like opened in its scope available to control the open state of a popover panel on state changes.

The opening state of the PopOver can be bound to an external store via data binding, e.g. to always display the popover panel.

popOverButton {
className(opened.map { if (it) "" else "text-opacity-90" })
opened.map { if (it) "Close Popover" else "Open Popover" }.renderText()
}

Transitions

Showing and hiding the popover panel can be easily animated with the help of transition:

popOverPanel {
transition(
opened,
"transition ease-out duration-200",
"opacity-0 translate-y-1",
"opacity-100 translate-y-0",
"transition ease-in duration-150",
"opacity-100 translate-y-0",
"opacity-0 translate-y-1"
)

//...
}

Positioning

popOverPanel is a PopUpPanel and therefore provides in its scope some configuration options, e.g. to control the position or distance of the list box from the popOverButton as a reference element:

popOverPanel {
placement = Placement.Bottom
distance = 20

//...
}

Arrow

An arrow pointing to the popOverButton can easily be added:

popOverPanel {
arrow()

//...
}

By default, the arrow is 8 pixels wide and inherits the background-color from the popOverPanel but it can easily be styled by adding classes:

arrow("h-3 w-3 bg-white")

Focus Management

In order to prevent interaction with the rest of the application via keyboard interaction, the popover uses a so-called focus trap by default. Therefore, the focus will cycle through all the focusable elements using Tab without leaving the modal panel.

For this reason there should always be at least one focusable element in the popover panel.

By default, the first focusable element is always given the focus. In order to focus a specific tag initially, the setInitialFocus function can be called inside a Tag.

Mouse Interaction

A click on the popOverButton toggles the state of the container. A click outside the opened container closes it.

Keyboard Interaction

Command Description
Enter Space when popOverButton is focused Opens container
Esc when container is open Closes container

API

Summary / Sketch

popOver {
// inherited by `OpenClose`
val openState: DatabindingProperty<Boolean>
val opened: Flow<Boolean>
val close: SimpleHandler<Unit>
val open: SimpleHandler<Unit>
val toggle: SimpleHandler<Unit>

popOverButton() { }
popOverPanel() {
// inherited by `PopUpPanel`
var placement: Placement
var strategy: Strategy
var flip: Boolean
var skidding: Int
var distance: int
}
}

popOver

Parameters: classes, id, scope, tag, initialize

Default-Tag: div

Scope property Typ Description
openState DatabindingProperty<Boolean> Mandatory (two-way) data-binding for opening and closing.
opened Flow<Boolean> Data stream that provides Boolean values related to the "open" state. Quite useless within a popover, as it is always true
close SimpleHandler<Unit> Handler to close the popover panel from inside.
open SimpleHandler<Unit> handler to open; does not make sense to use within a popover!
toggle SimpleHandler<Unit> handler for switching between open and closed; does not make sense to use within a popover.

popOverButton

Available in the scope of: popOver

Parameters: classes, scope, tag, initialize

Default-Tag: button

popOverPanel

Available in the scope of: popOver

Parameters: classes, scope, tag, initialize

Default-Tag: div

Scope property Typ Description
placement Placement Defines the position of the building block, e.g. Placement.top, Placement.bottomRight, etc. Default is Placement.auto. The presumably best position is determined automatically based on the available visible space.
strategy Strategy Determines whether the block should be positioned absolute (default) or fixed.
flip Boolean If the block comes too close to the edge of the visible area, the position automatically changes to the other side if more space is available there.
skidding Int Defines the shifting of the panel along the reference element in pixels. The default value is 0.
distance Int Defines the distance of the panel from the reference element in pixels. The default value is 10.