x-popup
v1.1.0
Published
Popup Web Component used for tooltips and context menus
Downloads
8
Readme
Popup Web Component used for tooltips and context menus
Examples
/** @jsxImportSource sigl */
import $ from 'sigl'
import { filterMap } from 'everyday-utils'
import { Rect } from 'sigl'
import { SurfaceElement, SurfaceItemElement, SurfaceMoveElement, SurfaceResizeElement } from 'x-surface'
import { PopupElement, PopupScene } from 'x-popup'
interface ItemElement extends $.Element<ItemElement> {}
@$.element()
class ItemElement extends $(SurfaceItemElement) {
SurfaceMove = $.element(SurfaceMoveElement)
SurfaceResize = $.element(SurfaceResizeElement)
@$.attr() label = $.String
mounted($: ItemElement['$']) {
$.render(({ host, surface, SurfaceMove, SurfaceResize }) => (
<>
<style>
{/*css*/ `
:host {
box-sizing: border-box;
border: 2px solid pink;
display: block;
position: absolute;
}
${SurfaceMove} {
background: #067;
width: 100%;
height: 20px;
position: absolute;
}
${SurfaceResize} {
background: #ba2;
position: absolute;
right: 0;
bottom: 0;
width: 20px;
height: 20px;
}
`}
</style>
<SurfaceMove surface={surface} dest={host} />
<SurfaceResize surface={surface} dest={host} />
</>
))
}
}
interface SceneElement extends $.Element<SceneElement> {}
@$.element()
class SceneElement extends HTMLElement {
Surface = $.element(SurfaceElement)
Item = $.element(ItemElement)
Popup = $.element(PopupElement)
surface?: SurfaceElement
popupScene = $(this).reduce(({ surface }) => new PopupScene(surface))
items = new $.RefSet<ItemElement>([
{ rect: new Rect(0, 0, 100, 100), label: 'one' },
{ rect: new Rect(200, 0, 100, 100), label: 'two' },
])
mounted($: SceneElement['$']) {
const Popups = $.part(({ Popup, popupScene, surface, items }) =>
filterMap([x-popup.items], item => item.ref.current)
.map(el => (
<Popup
scene={popupScene}
surface={surface}
// placement="nwr"
dest={el as unknown as SurfaceItemElement}
>
{el.label}
</Popup>
))
)
$.render(({ Surface, Item, items }) => (
<>
<style>
{/*css*/ `
:host {
display: block;
width: 100%;
height: 100%;
position: fixed;
}
[part=popups] {
position: absolute;
z-index: 2;
left: 0;
top: 0;
width: 100%;
}`}
</style>
<Surface ref={$.ref.surface}>
{items.map(item => <Item {x-popup.item} />)}
</Surface>
<div part="popups">
<Popups />
</div>
</>
))
}
}
const Scene = $.element(SceneElement)
$.render(<Scene />, document.body)
API
Credits
- everyday-utils by stagas – Everyday utilities
- sigl by stagas – Web framework
- x-surface by stagas – Infinitely pannable and zoomable HTML surface as a Web Component.
Contributing
All contributions are welcome!
License
MIT © 2022 stagas