fix(ui): overlay fixes (responsive backdrop/select-rich/tooltip)

This commit is contained in:
Thijs Louisse 2022-12-16 01:46:05 +01:00 committed by Thomas Allmer
parent ab906fc13b
commit 7ac0a42224
6 changed files with 54 additions and 13 deletions

View file

@ -0,0 +1,5 @@
---
'@lion/ui': patch
---
[overlays] fixes (responsive backdrop/select-rich/tooltip)

View file

@ -1,4 +1,3 @@
import { EventTargetShim } from '@lion/ui/core.js';
import { adoptStyles } from 'lit';
import { overlays } from './singleton.js';
import { containFocus } from './utils/contain-focus.js';
@ -129,7 +128,7 @@ const supportsCSSTypedObject = window.CSS?.number && document.body.attributeStyl
* bottom/top/left/right sheets etc.
*
*/
export class OverlayController extends EventTargetShim {
export class OverlayController extends EventTarget {
/**
* @constructor
* @param {OverlayConfig} config initial config. Will be remembered as shared config
@ -973,22 +972,24 @@ export class OverlayController extends EventTargetShim {
if (this.inheritsReferenceWidth) {
this._handleInheritsReferenceWidth();
}
if (this.visibilityTriggerFunction) {
this._handleUserInteraction({ phase });
this._handleVisibilityTriggers({ phase });
}
}
/**
* @param {{ phase: OverlayPhase }} config
*/
_handleUserInteraction({ phase }) {
_handleVisibilityTriggers({ phase }) {
if (typeof this.visibilityTriggerFunction === 'function') {
if (phase === 'init') {
this.__userInteractionHandler = this.visibilityTriggerFunction({ phase, controller: this });
this.__visibilityTriggerHandler = this.visibilityTriggerFunction({
phase,
controller: this,
});
}
if (this.__userInteractionHandler[phase]) {
this.__userInteractionHandler[phase]();
if (this.__visibilityTriggerHandler[phase]) {
this.__visibilityTriggerHandler[phase]();
}
}
}
@ -1053,10 +1054,14 @@ export class OverlayController extends EventTargetShim {
break;
}
case 'show':
if (this.config.hasBackdrop) {
this.backdropNode.classList.add(`overlays__backdrop--visible`);
}
this.__hasActiveBackdrop = true;
break;
case 'hide':
case 'teardown':
this.backdropNode.classList.remove(`overlays__backdrop--visible`);
this.__hasActiveBackdrop = false;
break;
}

View file

@ -1515,6 +1515,22 @@ describe('OverlayController', () => {
expect(ctrl.contentWrapperNode.classList.contains('overlays__overlay-container--top-right'));
expect(ctrl.isShown).to.be.true;
});
it('disables backdrop when switching to hasBackrop "false"', async () => {
const ctrl = new OverlayController({
...withLocalTestConfig(),
contentNode: /** @type {HTMLElement} */ (await fixture(html`<div>content1</div>`)),
hasBackdrop: true,
});
await ctrl.show(); // Popper adds inline styles
expect(ctrl.backdropNode).not.to.be.undefined;
expect(Array.from(ctrl.backdropNode.classList)).to.include('overlays__backdrop--visible');
ctrl.updateConfig({
hasBackdrop: false,
});
expect(Array.from(ctrl.backdropNode.classList)).to.not.include('overlays__backdrop--visible');
});
});
describe('Accessibility', () => {

View file

@ -336,6 +336,8 @@ export class LionSelectRich extends SlotMixin(ScopedElementsMixin(OverlayMixin(L
_defineOverlayConfig() {
return {
...withDropdownConfig(),
// Needs more advanced behavior (see `__invokerOnClick`)
visibilityTriggerFunction: undefined,
};
}

View file

@ -32,6 +32,10 @@ export class LionTooltip extends ArrowMixin(OverlayMixin(LitElement)) {
:host([hidden]) {
display: none;
}
::slotted([slot='content']) {
width: max-content;
}
`,
];
}
@ -54,9 +58,19 @@ export class LionTooltip extends ArrowMixin(OverlayMixin(LitElement)) {
/** @protected */
// eslint-disable-next-line class-methods-use-this
_defineOverlayConfig() {
const superCfg = super._defineOverlayConfig();
const tooltipCfg = withTooltipConfig({ invokerRelation: this.invokerRelation });
return /** @type {OverlayConfig} */ ({
...super._defineOverlayConfig(),
...withTooltipConfig({ invokerRelation: this.invokerRelation }),
...superCfg,
...tooltipCfg,
popperConfig: {
...(superCfg.popperConfig || {}),
...(tooltipCfg.popperConfig || {}),
modifiers: [
...(superCfg.popperConfig?.modifiers || []),
...(tooltipCfg.popperConfig?.modifiers || []),
],
},
});
}
}

View file

@ -227,8 +227,7 @@ describe('lion-tooltip', () => {
expect(el._arrowNode).to.be.displayed;
});
// TODO: promise for dynamic import popper does not resolve?
it.skip('makes sure positioning of the arrow is correct', async () => {
it('makes sure positioning of the arrow is correct', async () => {
const el = /** @type {LionTooltip} */ (
await fixture(html`
<lion-tooltip