UNPKG

@csedl/stimulus-dropdown

Version:

Dropdown and Tooltip with stimulus and floating-ui

63 lines (54 loc) 2.3 kB
import {Controller} from "@hotwired/stimulus" import {positionPanelByButton} from "./floating-ui-functions.js"; import {debugLog, onPanelOpen} from "./utils.js"; export default class extends Controller { opening_timer_id = null connect() { const panel_id = this.element.getAttribute('data-panel-id') if (!panel_id) { console.error(`Attribute data-panel-id missing`, this.element) } const delay_sec = parseFloat(this.element.getAttribute('data-delay')) if (!delay_sec) { console.error('missing required attribute: data-delay', this.element) } this.element.addEventListener('mouseenter', (e) => this.start_opening(e, panel_id, delay_sec * 1000)) this.element.addEventListener('mouseleave', (e) => this.close(e, panel_id)) if (window.StimulusDropdown.persistTooltipOnClick) { this.element.addEventListener('click', (e) => this.toggleByClick(e, panel_id)) } } start_opening(e, panel_id, delay_ms) { if (this.element.hasAttribute('data-tooltip-click')) { return; } this.opening_timer_id = setTimeout(() => this.open(e, panel_id), delay_ms) } toggleByClick(e, panel_id) { const stat = this.element.getAttribute('data-tooltip-click') if (stat === 'open') { debugLog('closing by click') this.element.removeAttribute('data-tooltip-click') this.close(e, panel_id) } else { debugLog('opening by click') this.open(e, panel_id) this.element.setAttribute('data-tooltip-click', 'open') } } open(e, panel_id) { this.element.classList.add('tooltip-is-visible') onPanelOpen(e, this.element) this.opening_timer_id = null let panel = document.getElementById(panel_id) panel.style.display = 'block'; positionPanelByButton(this.element) } close(e, panel_id) { if (this.element.hasAttribute('data-tooltip-click')) { return; } this.element.classList.remove('tooltip-is-visible') if (this.opening_timer_id) { clearTimeout(this.opening_timer_id) } let panel = document.getElementById(panel_id) panel.style.display = 'none'; } }