Tooltip

Display contextual information on hover, focus, or click with smart positioning and auto-adjustment

Overview

Tooltips display contextual information when users hover over, focus on, or click an element. They're perfect for providing hints, definitions, or additional context without cluttering the interface.

Key Features

  • Multiple Triggers - Hover, click, or focus activation
  • Positioning - Top, bottom, left, or right placement
  • Show Delay - Configurable delay before display
  • Animations - Smooth fade-in transitions
  • Dynamic Content - Update tooltip text on the fly
  • Auto-positioning - Smart placement to avoid viewport edges

Basic Usage

const tooltip = Domma.elements.tooltip('#my-button', {
    content: 'Helpful information here',
    position: 'top',
    trigger: 'hover',
    delay: 200
});

Getting Started

Add tooltips to your elements in three simple steps

Step 1: Add HTML Element

Create any HTML element that will trigger the tooltip:

<button id="my-button" class="btn btn-primary">Hover Me</button>
<span id="help-icon">?</span>
<a id="info-link" href="#">Learn more</a>

Step 2: Include Domma

Add Domma CSS and JavaScript to your page:

<!-- CSS -->
<link rel="stylesheet" href="dist/domma.css">
<link rel="stylesheet" href="dist/elements.css">

<!-- JavaScript -->
<script src="dist/domma.min.js"></script>

Step 3: Initialize the Tooltip

Call Domma.elements.tooltip() to attach a tooltip:

// Hover tooltip
Domma.elements.tooltip('#my-button', {
    content: 'Helpful information appears here',
    position: 'top',       // 'top', 'bottom', 'left', 'right'
    trigger: 'hover',      // 'hover', 'click', 'focus'
    delay: 200             // Delay before showing (ms)
});

// Click tooltip with HTML content
Domma.elements.tooltip('#help-icon', {
    content: '<strong>Tip:</strong> Click to continue',
    trigger: 'click',
    position: 'bottom'
});

Note: The tooltip auto-generates and positions the tooltip popup (no HTML required). Tooltips intelligently adjust position if near viewport edges. Use setContent() to update tooltip text dynamically.

Web Components

Domma Tooltip is now available as a native Web Component! Use modern <domma-tooltip> tags or the traditional wrapper API - both work identically with zero breaking changes.

Direct Web Component Usage

Wrap trigger elements in <domma-tooltip> tags:

Direct Web Component Usage
<domma-tooltip content="Top tooltip" position="top">
    <button type="button" class="btn btn-primary">Top</button>
</domma-tooltip>
<domma-tooltip content="Bottom tooltip" position="bottom">
    <button type="button" class="btn btn-primary">Bottom</button>
</domma-tooltip>
<domma-tooltip content="Left tooltip" position="left">
    <button type="button" class="btn btn-primary">Left</button>
</domma-tooltip>
<domma-tooltip content="Right tooltip" position="right">
    <button type="button" class="btn btn-primary">Right</button>
</domma-tooltip>
<domma-tooltip content="Top tooltip" position="top">
    <button class="btn btn-primary">Top</button>
</domma-tooltip>

<domma-tooltip content="Bottom tooltip" position="bottom">
    <button class="btn btn-primary">Bottom</button>
</domma-tooltip>

Trigger Types

Trigger Types
<domma-tooltip content="Hover trigger (default)" trigger="hover">
    <button type="button" class="btn btn-outline">Hover</button>
</domma-tooltip>
<domma-tooltip content="Click trigger" trigger="click">
    <button type="button" class="btn btn-outline">Click</button>
</domma-tooltip>
<domma-tooltip content="Focus trigger" trigger="focus">
    <input type="text" class="form-input tooltip-input-width-150" placeholder="Focus me">
</domma-tooltip>
<domma-tooltip content="Hover trigger" trigger="hover">
    <button>Hover</button>
</domma-tooltip>

<domma-tooltip content="Click trigger" trigger="click">
    <button>Click</button>
</domma-tooltip>

<domma-tooltip content="Focus trigger" trigger="focus">
    <input type="text" placeholder="Focus me">
</domma-tooltip>

Delay Configuration

Control show and hide delays:

Delay Configuration
<domma-tooltip content="Instant tooltip" delay="0">
    <button type="button" class="btn btn-secondary">No Delay</button>
</domma-tooltip>
<domma-tooltip content="Delayed tooltip" delay="500">
    <button type="button" class="btn btn-secondary">500ms Delay</button>
</domma-tooltip>
<domma-tooltip content="Slow hide" delay="0" hide-delay="1000">
    <button type="button" class="btn btn-secondary">Slow Hide</button>
</domma-tooltip>
<domma-tooltip content="Instant" delay="0">
    <button>No Delay</button>
</domma-tooltip>

<domma-tooltip content="Delayed" delay="500" hide-delay="300">
    <button>With Delays</button>
</domma-tooltip>

Programmatic API

Web Components support dynamic updates:

Programmatic API


<domma-tooltip id="programmable-tooltip" content="Initial content" position="top">
    <button type="button" class="btn btn-info">Hover &amp; Click Button Below</button>
</domma-tooltip>
<br><br>
<button type="button" class="btn btn-sm btn-primary" data-action="1">Update Content</button>
<button type="button" class="btn btn-sm btn-secondary" data-action="2">Change Position</button>
/**
 * Programmatic API - from public/showcase/elements/tooltip.
 */
export function mount(root) {
    const positions = ['top', 'bottom', 'left', 'right'];
    let currentPosIndex = 0;
    const tooltipContents = [
            'Updated content!',
            'New tooltip text!',
            'Changed again!',
            'Back to original'
        ];
    let contentIndex = 0;
    function updateTooltipContent() {
            const tooltip = $(root).find('#programmable-tooltip')[0];
            contentIndex = (contentIndex + 1) % tooltipContents.length;
            tooltip.setContent(tooltipContents[contentIndex]);
        };
    function changeTooltipPosition() {
            const tooltip = $(root).find('#programmable-tooltip')[0];
            currentPosIndex = (currentPosIndex + 1) % positions.length;
            tooltip.setPosition(positions[currentPosIndex]);
        };

    // Handlers the old page had inline (onclick=…), wired here.
    $(root).find('[data-action="1"]').on('click', function (event) {
        updateTooltipContent();
    });
    $(root).find('[data-action="2"]').on('click', function (event) {
        changeTooltipPosition();
    });
}
const tooltip = $('domma-tooltip')[0];

// Update content
tooltip.setContent('New tooltip text!');

// Update position
tooltip.setPosition('bottom');

// Show/hide programmatically
tooltip.show();
tooltip.hide();
tooltip.toggle();

// Check visibility
if (tooltip.isVisible()) {
    console.log('Tooltip is showing');
}

Wrapper API (Backwards Compatible)

Existing code continues to work unchanged! The wrapper API uses Web Components internally:

Wrapper API (Backwards Compatible)
<button type="button" id="wrapper-tooltip-btn" class="btn btn-success">Wrapper Tooltip</button>
/**
 * Wrapper API (Backwards Compatible) - from public/showcase/elements/tooltip.
 */
export function mount(root) {
        // Web Components - Wrapper API demo
    if ($(root).find('#wrapper-tooltip-btn').length) {
                E.tooltip(root.querySelector('#wrapper-tooltip-btn'), {
                    content: 'This uses the wrapper API!',
                    position: 'top',
                    trigger: 'hover'
                });
            }
}
// Traditional approach - still works!
const tooltip = Domma.elements.tooltip('#my-element', {
    content: 'Helpful information here',
    position: 'top',
    trigger: 'hover',
    delay: 200
});

// Same API as before
tooltip.show();
tooltip.hide();
tooltip.setContent('Updated text');
tooltip.destroy();

💡 Benefits of Web Components: Encapsulation - Tooltip styles isolated via Shadow DOM Smart Positioning - Auto-adjusts to avoid viewport edges Standards-based - Native browser API, future-proof Backwards Compatible - Existing code works without changes

Quick Start

Hover Tooltip

Hover Tooltip
<button type="button" id="quick-hover" class="btn btn-primary">Hover Me</button>
/**
 * Hover Tooltip - from public/showcase/elements/tooltip.
 */
export function mount(root) {
            // Original showcase examples
    E.tooltip(root.querySelector('#quick-hover'), {
                content: 'This appears on hover',
                position: 'top'
            });
}
Domma.elements.tooltip('#button', {
    content: 'This appears on hover',
    position: 'top'
});

Tutorial

Build a form with helpful tooltips on input fields.

Tutorial
<div class="form-group mb-3">
    <label>Username <span id="username-help" class="tooltip-cursor-help">ⓘ</span></label>
    <input type="text" class="form-input" placeholder="Enter username">
</div>
<div class="form-group">
    <label>Password <span id="password-help" class="tooltip-cursor-help">ⓘ</span></label>
    <input type="password" class="form-input" placeholder="Enter password">
</div>
/**
 * Tutorial - from public/showcase/elements/tooltip.
 */
export function mount(root) {
    E.tooltip(root.querySelector('#username-help'), {
                content: 'Username must be 3-20 characters',
                position: 'right'
            });
    E.tooltip(root.querySelector('#password-help'), {
                content: 'Password must be at least 8 characters',
                position: 'right'
            });
}
Domma.elements.tooltip('#username-help', {
    content: 'Username must be 3-20 characters',
    position: 'right',
    trigger: 'hover'
});

Domma.elements.tooltip('#password-help', {
    content: 'Password must be at least 8 characters',
    position: 'right',
    trigger: 'hover'
});

Examples

Positioning Options

Positioning Options
<div class="flex justify-center gap-4 tooltip-demo-area-py-4">
    <button type="button" id="pos-top" class="btn btn-outline">Top</button>
    <button type="button" id="pos-bottom" class="btn btn-outline">Bottom</button>
    <button type="button" id="pos-left" class="btn btn-outline">Left</button>
    <button type="button" id="pos-right" class="btn btn-outline">Right</button>
</div>
/**
 * Positioning Options - from public/showcase/elements/tooltip.
 */
export function mount(root) {
    E.tooltip(root.querySelector('#pos-top'), {content: 'Tooltip on top', position: 'top'});
    E.tooltip(root.querySelector('#pos-bottom'), {content: 'Tooltip on bottom', position: 'bottom'});
    E.tooltip(root.querySelector('#pos-left'), {content: 'Tooltip on left', position: 'left'});
    E.tooltip(root.querySelector('#pos-right'), {content: 'Tooltip on right', position: 'right'});
}

Trigger Types

Trigger Types
<div class="flex justify-center gap-4">
    <button type="button" id="trigger-hover" class="btn btn-primary">Hover</button>
    <button type="button" id="trigger-click" class="btn btn-primary">Click</button>
    <input id="trigger-focus" type="text" class="form-input tooltip-input-width-150" placeholder="Focus me">
</div>
/**
 * Trigger Types - from public/showcase/elements/tooltip.
 */
export function mount(root) {
    E.tooltip(root.querySelector('#trigger-hover'), {content: 'Shown on hover', trigger: 'hover'});
    E.tooltip(root.querySelector('#trigger-click'), {content: 'Shown on click', trigger: 'click'});
    E.tooltip(root.querySelector('#trigger-focus'), {content: 'Shown on focus', trigger: 'focus'});
}

Dynamic Content

Dynamic Content

Hover count: 0

<button type="button" id="dynamic-tooltip" class="btn btn-secondary">Hover for count</button>
<p class="text-sm text-muted mt-2">Hover count: <span id="hover-count">0</span></p>
/**
 * Dynamic Content - from public/showcase/elements/tooltip.
 */
export function mount(root) {
    let hoverCount = 0;
    const dynamicTip = E.tooltip(root.querySelector('#dynamic-tooltip'), {
                content: 'Hover count: 0',
                position: 'top'
            });
    $(root).find('#dynamic-tooltip').on('mouseenter', () => {
                hoverCount++;
                $(root).find('#hover-count').text(hoverCount);
                dynamicTip.setContent(`Hover count: ${hoverCount}`);
            });
}

Best Practices

Accessibility

  • Keyboard Access - Use focus trigger for keyboard users
  • ARIA Labels - Add aria-describedby linking to tooltip
  • Don't Hide Critical Info - Essential information shouldn't require tooltip interaction

Performance

  • Reuse Instances - Don't recreate tooltips on every interaction
  • Delay Hover - Use 200ms+ delay to avoid accidental triggers

API Reference

Options

Option Type Default Description
content String '' Tooltip text content
position String 'top' Position: top, bottom, left, right
trigger String 'hover' Trigger: hover, click, focus
delay Number 0 Show delay in milliseconds
animation Boolean true Enable fade animation

Methods

Method Description
show() Show tooltip immediately
hide() Hide tooltip immediately
toggle() Toggle tooltip visibility
setContent(text) Update tooltip text
destroy() Remove tooltip and clean up

Config Engine

$.setup({
    '#help-icon': {
        component: 'tooltip',
        options: {
            content: 'Click for help documentation',
            position: 'right',
            trigger: 'hover'
        }
    }
});

CSS Customisation

Override these CSS variables to customise Tooltip appearance and match your design system.

Variable Default Controls
--dm-slate-900 #0f172a Tooltip background
--dm-radius-md 0.375rem Tooltip corner radius
--dm-font-size-sm 0.875rem Tooltip text size
--dm-text-inverse var(--dm-white) Tooltip text colour

Example Override

/* Light tooltip - override inline or create custom class */
.tooltip-light {
    background: #f9fafb;
    color: #1f2937;
}

Full CSS Customisation Cheat-Sheet →

Related Elements

Related Elements
<div class="grid grid-cols-1 grid-auto-fit-250 gap-4"><a href="/showcase/elements/modal" class="card card-hover no-underline text-inherit">
        <div class="card-body">
            <h3 class="card-title">Modal</h3>
            <p class="card-text">For longer content that needs full focus</p>
        </div>
    </a>
    <a href="/showcase/elements/dropdown" class="card card-hover no-underline text-inherit">
        <div class="card-body">
            <h3 class="card-title">Dropdown</h3>
            <p class="card-text">For interactive menus and options</p>
        </div>
    </a>
</div>