Display an Auto-Dismiss message

Is it possible in Five to show a message that goes away after a specified time? This seems like a common requirement, and I believe JavaScript may support this.

Thanks…

Hi Ron,

You should be able to achieve it using JavaScript via a client-side event.

Regards,
Elton S

Thanks Elton.

I was able to attain this effect by creating a MessageBox library which creates an experience almost exactly like five.showMessage, but it has a timeout parameter. I appreciate your help.

Let me know if you want a copy of this library code.

Hi Ron,

It is good to know you got a solution.

Please, feel free to share your code sample here (in case you want to make it public) or you can share via my email elton@five.co.

Regards,
Elton S

Thanks. I created a library called MessageBox, which closely mimics five.showMessage. It allows a configurable timeout which if not 0, dismisses the dialog in that many milliseconds. 0 or missing keeps the message until you click OK.

It is called like this:
MessageBox(five, {Message: xxx, Title: xxx, Timeout: ##})

Message is required, but others are optional. Also, it’s written so if it is called like MessageBox(five, myMessageText), it will still work (without the title and timeout).

function MessageBox(five, opts) {

    // Emulates five.showMessage, but adds configurable timeout for auto-dismissing
    
    // opts is a JSON object with parameters
    // { Message: xxx, Title: xxx, Timeout: ## }
    
    // handle if user only supplied the message instead of parameters
    if (typeof opts === 'string') {
        opts = { Message: opts };
    }
    if (!opts) opts = {};

    var title = opts.Title || 'Five';
    var message = opts.Message || 'No Message Supplied';
    var timeoutMs = opts.Timeout;
    if (timeoutMs === undefined || timeoutMs === null) timeoutMs = 0;

    // Overlay (blocks UI)
    var overlay = document.createElement('div');
    Object.assign(overlay.style, {
        position: 'fixed',
        top: '0',
        left: '0',
        right: '0',
        bottom: '0',
        background: 'rgba(0,0,0,0.35)',
        zIndex: 999999,
        display: 'flex',
        alignItems: 'center',
        justifyContent: 'center',
        padding: '20px'
    });

    // Dialog box
    var box = document.createElement('div');
    Object.assign(box.style, {
        background: '#fff',
        borderRadius: '10px',
        padding: '18px 20px',
        minWidth: '280px',
        maxWidth: '520px',
        boxShadow: '0 10px 30px rgba(0,0,0,0.25)',
        fontSize: '14px',
        color: '#111',

        // Keep the dialog from getting too tall
        maxHeight: '80vh',

        // Layout so message area can scroll but title/buttons stay visible
        display: 'flex',
        flexDirection: 'column',
        gap: '12px'
    });

    // Title
    var titleEl = document.createElement('div');
    titleEl.textContent = title;
    Object.assign(titleEl.style, {
        fontSize: '18px',
        fontWeight: 'bold',
        flex: '0 0 auto'
    });

    // Message (scrollable when needed + selectable)
    var msgEl = document.createElement('div');
    msgEl.textContent = message;
    Object.assign(msgEl.style, {
        whiteSpace: 'pre-wrap',
        lineHeight: '1.4',

        // This is what makes it scroll when long
        overflowY: 'auto',

        // Allow it to take remaining height inside the box
        flex: '1 1 auto',

        // Make sure text is selectable/copyable
        userSelect: 'text'
    });

    // Button row
    var btnRow = document.createElement('div');
    Object.assign(btnRow.style, {
        display: 'flex',
        justifyContent: 'flex-end',
        marginTop: '6px',
        flex: '0 0 auto'
    });

    // OK button
    var btn = document.createElement('button');
    btn.type = 'button';
    btn.textContent = 'OK';

    Object.assign(btn.style, {
        cursor: 'pointer',
        border: 'none',
        borderRadius: '8px',
        padding: '7px 16px',
        background: '#1677ff',
        color: '#fff',
        fontSize: '14px',
        fontWeight: '500'
    });

    function close() {
        document.removeEventListener('keydown', onKeyDown);
        if (overlay.parentNode) overlay.parentNode.removeChild(overlay);
    }

    function onKeyDown(e) {
        var k = e && (e.key || e.keyCode);
        if (k === 'Enter' || k === 13 || k === 'Escape' || k === 27) {
            close();
        }
    }

    btn.onclick = close;

    overlay.onclick = function (e) {
        if (e.target === overlay) {
            close();
        }
    };

    // Build DOM
    overlay.appendChild(box);
    box.appendChild(titleEl);
    box.appendChild(msgEl);
    btnRow.appendChild(btn);
    box.appendChild(btnRow);

    document.body.appendChild(overlay);
    document.addEventListener('keydown', onKeyDown);

    try { btn.focus(); } catch (e) {}

    if (timeoutMs > 0) {
        setTimeout(close, timeoutMs);
    }
}

Hi Ron,

Thank you so much for sharing your solution.

Regards,
Elton S