/*!
 * Custom elements for Nanopore-Digital Web applications
 */
'use strict';

const debounceEvent = (event, wait) => {
    const original = event._original || event;
    return {
        _original: event,
        emit: debounce(original.emit.bind(original), wait),
    };
};
/**
 * debounce ensures that one function call is made for an event that fires multiple times.
 * @param callback to perform after waiting
 * @param wait how to long to wait before calling the function
 * @returns a debounced function to call as often as required
 */
const debounce = (callback, wait = 0) => {
    let timer;
    return (...args) => {
        clearTimeout(timer);
        timer = setTimeout(callback, wait, ...args);
    };
};
/**
 * throttle delays executing a function - reducing the function calls of an event that fires multiple times.
 * @param callback to perform after a delay
 * @param delay how long to delay before calling the function
 * @returns a throttled function to call as often as required
 */
const throttle = (callback, delay) => {
    // Previously called time of the function
    let prev = 0;
    return (...args) => {
        // Current called time of the function
        const now = new Date().getTime();
        // If difference is greater than delay call
        // the function again.
        if (now - prev > delay) {
            prev = now;
            // "..." is the spread operator here
            // returning the function with the
            // array of arguments
            return callback(...args);
        }
    };
};

exports.debounce = debounce;
exports.debounceEvent = debounceEvent;
exports.throttle = throttle;
