UNPKG

@components-1812/offcanvas

Version:

A web component for custom offcanvas, lateral panel

349 lines (304 loc) 10.7 kB
/** * package: @components-1812/offcanvas * version: 0.0.3 */ :host { --offcanvas-position: absolute; --offcanvas-z-index: 8010; width: 100%; height: 100%; position: var(--offcanvas-position); top: 0; left: 0; z-index: var(--offcanvas-z-index); pointer-events: none; /* Panel */ --offcanvas-panel-width: 300px; --offcanvas-panel-height: 100%; --offcanvas-panel-padding: 5px; --offcanvas-panel-transition: margin 0.3s ease-in-out; --offcanvas-panel-header-padding: 5px; --offcanvas-panel-body-padding: 5px; --offcanvas-panel-footer-padding: 5px; --offcanvas-panel-bg: #222; --offcanvas-panel-color: #fff; --offcanvas-panel-header-bg: var(--offcanvas-panel-bg); --offcanvas-panel-header-color: var(--offcanvas-panel-color); --offcanvas-panel-footer-bg: var(--offcanvas-panel-bg); --offcanvas-panel-footer-color: var(--offcanvas-panel-color); --offcanvas-panel-border: 1px solid #ccc; --offcanvas-panel-border-radius: 0px; --offcanvas-panel-shadow: 0 1px 3px 0 #3c40434d, 0 4px 8px 3px #3c404326; /* Backdrop */ --offcanvas-backdrop-bg: #00000080; --offcanvas-backdrop-color: #fff; --offcanvas-backdrop-transition: background-color 0.3s ease-in-out; /* Close button */ --offcanvas-close-button-width: 40px; --offcanvas-close-button-height: 40px; --offcanvas-close-button-padding: 10px; --offcanvas-close-button-bg: transparent; --offcanvas-close-button-color: #fff; --offcanvas-close-button-border: none; --offcanvas-close-button-font-size: 1.5rem; --offcanvas-close-button-cursor: pointer; /* Handle button */ --offcanvas-handle-button-width: 50px; --offcanvas-handle-button-height: 100px; --offcanvas-handle-button-padding: 5px; --offcanvas-handle-button-bg: #444; --offcanvas-handle-button-color: #fff; --offcanvas-handle-button-border: none; --offcanvas-handle-button-border-radius: 10px; --offcanvas-handle-button-cursor: pointer; --offcanvas-handle-button-font-size: 1rem; --offcanvas-handle-button-shadow: var(--offcanvas-panel-shadow); } :host([variant~="top"]), :host([variant~="bottom"]) { --offcanvas-panel-width: 100%; --offcanvas-panel-height: 300px; --offcanvas-handle-button-width: 100px; --offcanvas-handle-button-height: 50px; --offcanvas-panel-shadow: 1px 0 3px 0 #3c40434d, 4px 0 8px 3px #3c404326; } :host([variant~="global"]) { --offcanvas-position: fixed; } :host([variant~="local"]) { --offcanvas-position: absolute; } :host .offcanvas { width: 100%; height: 100%; background-color: transparent; transition: var(--offcanvas-backdrop-transition); pointer-events: none; display: flex; &[open]:not([variant~="backdrop-transparent"]) { background-color: var(--offcanvas-backdrop-bg); } &[variant~="left"], & { flex-direction: row; } &[variant~="right"] { flex-direction: row-reverse; } &[variant~="top"] { flex-direction: column; } &[variant~="bottom"] { flex-direction: column-reverse; } } /*MARK: Panel*/ :host .offcanvas { .panel { width: var(--offcanvas-panel-width); height: var(--offcanvas-panel-height); padding: var(--offcanvas-panel-padding); position: relative; box-sizing: border-box; pointer-events: initial; background: var(--offcanvas-panel-bg); color: var(--offcanvas-panel-color); overflow: hidden; transition: var(--offcanvas-panel-transition); .panel-content { position: relative; width: 100%; height: 100%; display: flex; flex-direction: column; overflow: hidden; } .panel-header { position: relative; padding: var(--offcanvas-panel-header-padding); background: var(--offcanvas-panel-header-bg); color: var(--offcanvas-panel-header-color); } .panel-body { position: relative; flex: 1 1 auto; padding: var(--offcanvas-panel-body-padding); } .panel-footer { position: relative; padding: var(--offcanvas-panel-footer-padding); background: var(--offcanvas-panel-footer-bg); color: var(--offcanvas-panel-footer-color); } } &[variant~="scroll-full"] .panel-content { overflow: auto; } &[variant~="scroll-inner"] .panel-content { overflow: auto; .panel-header { position: sticky; inset: 0 auto auto 0; z-index: 10; } } &[variant~="scroll-body"] .panel { .panel-body { overflow: auto; } } &[variant~="left"] .panel, .panel { border-top: none; border-left: none; border-bottom: none; border-right: var(--offcanvas-panel-border); border-radius: 0 var(--offcanvas-panel-border-radius) var(--offcanvas-panel-border-radius) 0; margin: 0 0 0 calc(-1 * var(--offcanvas-panel-width)); } &[variant~="right"] .panel { border-top: none; border-left: var(--offcanvas-panel-border);; border-bottom: none; border-right: none; border-radius: var(--offcanvas-panel-border-radius) 0 0 var(--offcanvas-panel-border-radius); margin: 0 calc(-1 * var(--offcanvas-panel-width)) 0 0; } &[variant~="top"] .panel { border-top: none; border-left: none; border-bottom: var(--offcanvas-panel-border); border-right: none; border-radius: 0 0 var(--offcanvas-panel-border-radius) var(--offcanvas-panel-border-radius); margin: calc(-1 * var(--offcanvas-panel-height)) 0 0 0; } &[variant~="bottom"] .panel { border-top: var(--offcanvas-panel-border); border-left: none; border-bottom: none; border-right: none; border-radius: var(--offcanvas-panel-border-radius) var(--offcanvas-panel-border-radius) 0 0; margin: 0 0 calc(-1 * var(--offcanvas-panel-height)) 0; } &[open] .panel { box-shadow: var(--offcanvas-panel-shadow); margin: 0; } } /*MARK: Backdrop */ :host .offcanvas { .offcanvas-backdrop { pointer-events: none; flex: 1 1 auto; position: relative; color: var(--offcanvas-backdrop-color); ::slotted(*) { pointer-events: initial; } ::slotted([data-hide-when-closed]){ display: none; } } &[open] .offcanvas-backdrop { pointer-events: initial; ::slotted([data-hide-when-closed]){ display: unset; } ::slotted([data-hide-when-opened]){ display: none; } } &[open][variant~="backdrop-static"] .offcanvas-backdrop { pointer-events: none; } } /*MARK: Close button*/ :host .offcanvas { .close-button { pointer-events: initial; position: absolute; inset: 0 0 auto auto; width: var(--offcanvas-close-button-width); height: var(--offcanvas-close-button-height); padding: var(--offcanvas-close-button-padding); background: var(--offcanvas-close-button-bg); color: var(--offcanvas-close-button-color); border: var(--offcanvas-close-button-border); font-size: var(--offcanvas-close-button-font-size); cursor: var(--offcanvas-close-button-cursor); display: flex; align-items: center; justify-content: center; } } /*MARK: Handle button*/ :host .offcanvas { .handle-button { pointer-events: initial; position: absolute; box-sizing: border-box; width: var(--offcanvas-handle-button-width); height: var(--offcanvas-handle-button-height); padding: var(--offcanvas-handle-button-padding); background: var(--offcanvas-handle-button-bg); color: var(--offcanvas-handle-button-color); box-shadow: var(--offcanvas-handle-button-shadow); border: var(--offcanvas-handle-button-border); font-size: var(--offcanvas-handle-button-font-size); cursor: var(--offcanvas-handle-button-cursor); margin: auto; } &[variant~="left"], & { .handle-button { inset: 0 auto 0 0; border-radius: 0 var(--offcanvas-handle-button-border-radius) var(--offcanvas-handle-button-border-radius) 0; ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: 0deg; } } &[open] .handle-button { ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: 180deg; } } } &[variant~="right"] { .handle-button { inset: 0 0 0 auto; border-radius: var(--offcanvas-handle-button-border-radius) 0 0 var(--offcanvas-handle-button-border-radius); ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: 180deg; } } &[open] .handle-button { ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: 0deg; } } } &[variant~="top"] { .handle-button { inset: 0 0 auto 0; border-radius: 0 0 var(--offcanvas-handle-button-border-radius) var(--offcanvas-handle-button-border-radius); ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: 90deg; } } &[open] .handle-button { ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: -90deg; } } } &[variant~="bottom"] { .handle-button { inset: auto 0 0 0; border-radius: var(--offcanvas-handle-button-border-radius) var(--offcanvas-handle-button-border-radius) 0 0; ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: -90deg; } } &[open] .handle-button { ::slotted([data-rotate-icon]), svg[data-rotate-icon]{ rotate: 90deg; } } } }