Search code examples
jquerycolorbox

JQuery Colorbox Doesn't Close on Content Click


Please Help!!! I think I need to add an onComplete callback?

My boss wants the color box to close when the HTML "button download" class is clicked. The way it's currently coded the color box stays up until a user clicks escape, or clicks off the color box (boss doesn't like that.) He wants it to close after a user clicks the "Click Here to Start Download" link in the colorbox.

RELEVANT HTML

<div style='display:none'>
    <div id='inline_content'>
        <img class="arrow" src="img/arrow-down.png" alt="arrow"/>
        <div class="title">Start Download</div>
        <div class="download-container">
            <div class="download-title">Your download is ready!</div>
            <a class="button download" href="http://example.com/download/">Click Here to Start Download</a>
        </div>
        <div class="text">This is a 100% FREE download and is 100% Safe. Millions of users
            are already using this app. Don’t wait any longer. Get it now!</div>
    </div>
</div>

/*! SYSTEM.JS file - this file sets up a 5 second timer, then opens the colorbox */

$(document).ready(function(){

setTimeout(function() {
    $.colorbox({width:"450px",height:"260px", inline:true, href:"#inline_content",close:"X"});
}, 5000);

/*! jquery.colorbox.js file - this file has the colorbox properties */

/*! Colorbox v1.5.13 - 2014-08-04 jQuery lightbox and modal window plugin (c) 2014 Jack Moore */ (function ($, document, window) { var // Default settings object. // See http://jacklmoore.com/colorbox for details. defaults = { // data sources html: false, photo: false, iframe: false, inline: false,

    // behavior and appearance
    transition: "elastic",
    speed: 300,
    fadeOut: 300,
    width: false,
    initialWidth: "600",
    innerWidth: false,
    maxWidth: false,
    height: false,
    initialHeight: "450",
    innerHeight: false,
    maxHeight: false,
    scalePhotos: true,
    scrolling: true,
    opacity: 0.9,
    preloading: true,
    className: false,
    overlayClose: true,
    escKey: true,
    arrowKey: true,
    top: false,
    bottom: false,
    left: false,
    right: false,
    fixed: false,
    data: undefined,
    closeButton: true,
    fastIframe: true,
    open: false,
    reposition: true,
    loop: true,
    slideshow: false,
    slideshowAuto: true,
    slideshowSpeed: 2500,
    slideshowStart: "start slideshow",
    slideshowStop: "stop slideshow",
    photoRegex: /\.(gif|png|jp(e|g|eg)|bmp|ico|webp|jxr|svg)((#|\?).*)?$/i,


    rel: function() {
        return this.rel;
    },
    href: function() {
        // using this.href would give the absolute url, when the href may have been inteded as a selector (e.g. '#container')
        return $(this).attr('href');
    },
    title: function() {
        return this.title;
    }
},

// Cached jQuery Object Variables
$overlay,
$box,
$wrap,
$content,
$topBorder,
$leftBorder,
$rightBorder,
$bottomBorder,
$related,
$window,
$loaded,
$loadingBay,
$loadingOverlay,
$title,
$current,
$slideshow,
$next,
$prev,
$close,
$groupControls,
$events = $('<a/>'), // $({}) would be prefered, but there is an issue with jQuery 1.4.2


// ****************
// HELPER FUNCTIONS
// ****************

// Convenience function for creating new jQuery objects

function launch(element) {
    var options;
    if (!closing) {
        options = $(element).data(colorbox);
        settings = new Settings(element, options);  
        getRelated(settings.get('rel'));
        if (!open) {
            open = active = true; // Prevents the page-change action from queuing up if the visitor holds down the left or right keys.

            setClass(settings.get('className'));

            // Show colorbox so the sizes can be calculated in older versions of jQuery
            $box.css({visibility:'hidden', display:'block', opacity:''});

            $loaded = $tag(div, 'LoadedContent', 'width:0; height:0; overflow:hidden; visibility:hidden');
            $content.css({width:'', height:''}).append($loaded);

            // Cache values needed for size calculations
            interfaceHeight = $topBorder.height() + $bottomBorder.height() + $content.outerHeight(true) - $content.height();
            interfaceWidth = $leftBorder.width() + $rightBorder.width() + $content.outerWidth(true) - $content.width();
            loadedHeight = $loaded.outerHeight(true);
            loadedWidth = $loaded.outerWidth(true);

            // Opens inital empty Colorbox prior to content being loaded.
            var initialWidth = setSize(settings.get('initialWidth'), 'x');
            var initialHeight = setSize(settings.get('initialHeight'), 'y');
            var maxWidth = settings.get('maxWidth');
            var maxHeight = settings.get('maxHeight');

            settings.w = (maxWidth !== false ? Math.min(initialWidth, setSize(maxWidth, 'x')) : initialWidth) - loadedWidth - interfaceWidth;
            settings.h = (maxHeight !== false ? Math.min(initialHeight, setSize(maxHeight, 'y')) : initialHeight) - loadedHeight - interfaceHeight;

            $loaded.css({width:'', height:settings.h});
            publicMethod.position();

            trigger(event_open);
            settings.get('onOpen');

            $groupControls.add($title).hide();

            $box.focus();

            if (settings.get('trapFocus')) {
                // Confine focus to the modal
                // Uses event capturing that is not supported in IE8-
                if (document.addEventListener) {

                    document.addEventListener('focus', trapFocus, true);

                    $events.one(event_closed, function () {
                        document.removeEventListener('focus', trapFocus, true);
                    });
                }
            }

            // Return focus on closing
            if (settings.get('returnFocus')) {
                $events.one(event_closed, function () {
                    $(settings.el).focus();
                });
            }
        }

        var opacity = parseFloat(settings.get('opacity'));
        $overlay.css({
            opacity: opacity === opacity ? opacity : '',
            cursor: settings.get('overlayClose') ? 'pointer' : '',
            visibility: 'visible'
        }).show();

        if (settings.get('closeButton')) {
            $close.html(settings.get('close')).appendTo($content);
        } else {
            $close.appendTo('<div/>'); // replace with .detach() when dropping jQuery < 1.4
        }

        load();
    }
}

// Add Colorbox's event bindings
function addBindings() {
    function clickHandler(e) {
        // ignore non-left-mouse-clicks and clicks modified with ctrl / command, shift, or alt.
        // See: http://jacklmoore.com/notes/click-events/
        if (!(e.which > 1 || e.shiftKey || e.altKey || e.metaKey || e.ctrlKey)) {
            e.preventDefault();
            launch(this);
        }
    }

    if ($box) {
        if (!init) {
            init = true;

            // Anonymous functions here keep the public method from being cached, thereby allowing them to be redefined on the fly.
            $next.click(function () {
                publicMethod.next();
            });
            $prev.click(function () {
                publicMethod.prev();
            });
            $close.click(function () {
                publicMethod.close();
            });
            $overlay.click(function () {
                if (settings.get('overlayClose')) {
                    publicMethod.close();
                }
            });

            // Key Bindings
            $(document).bind('keydown.' + prefix, function (e) {
                var key = e.keyCode;
                if (open && settings.get('escKey') && key === 27) {
                    e.preventDefault();
                    publicMethod.close();
                }
                if (open && settings.get('arrowKey') && $related[1] && !e.altKey) {
                    if (key === 37) {
                        e.preventDefault();
                        $prev.click();
                    } else if (key === 39) {
                        e.preventDefault();
                        $next.click();
                    }
                }
            });

            if ($.isFunction($.fn.on)) {
                // For jQuery 1.7+
                $(document).on('click.'+prefix, '.'+boxElement, clickHandler);
            } else {
                // For jQuery 1.3.x -> 1.6.x
                // This code is never reached in jQuery 1.9, so do not contact me about 'live' being removed.
                // This is not here for jQuery 1.9, it's here for legacy users.
                $('.'+boxElement).live('click.'+prefix, clickHandler);
            }
        }
        return true;
    }
    return false;
}

// Don't do anything if Colorbox already exists.
if ($[colorbox]) {
    return;
}


publicMethod.position = function (speed, loadedCallback) {
    var
    css,
    top = 0,
    left = 0,
    offset = $box.offset(),
    scrollTop,
    scrollLeft;

    $window.unbind('resize.' + prefix);

    // remove the modal so that it doesn't influence the document width/height
    $box.css({top: -9e4, left: -9e4});

    scrollTop = $window.scrollTop();
    scrollLeft = $window.scrollLeft();

    if (settings.get('fixed')) {
        offset.top -= scrollTop;
        offset.left -= scrollLeft;
        $box.css({position: 'fixed'});
    } else {
        top = scrollTop;
        left = scrollLeft;
        $box.css({position: 'absolute'});
    }

    // keeps the top and left positions within the browser's viewport.
    if (settings.get('right') !== false) {
        left += Math.max($window.width() - settings.w - loadedWidth - interfaceWidth - setSize(settings.get('right'), 'x'), 0);
    } else if (settings.get('left') !== false) {
        left += setSize(settings.get('left'), 'x');
    } else {
        left += Math.round(Math.max($window.width() - settings.w - loadedWidth - interfaceWidth, 0) / 2);
    }

    if (settings.get('bottom') !== false) {
        top += Math.max(winheight() - settings.h - loadedHeight - interfaceHeight - setSize(settings.get('bottom'), 'y'), 0);
    } else if (settings.get('top') !== false) {
        top += setSize(settings.get('top'), 'y');
    } else {
        top += Math.round(Math.max(winheight() - settings.h - loadedHeight - interfaceHeight, 0) / 2);
    }

    $box.css({top: offset.top, left: offset.left, visibility:'visible'});

    // this gives the wrapper plenty of breathing room so it's floated contents can move around smoothly,
    // but it has to be shrank down around the size of div#colorbox when it's done.  If not,
    // it can invoke an obscure IE bug when using iframes.
    $wrap[0].style.width = $wrap[0].style.height = "9999px";

    function modalDimensions() {
        $topBorder[0].style.width = $bottomBorder[0].style.width = $content[0].style.width = (parseInt($box[0].style.width,10) - interfaceWidth)+'px';
        $content[0].style.height = $leftBorder[0].style.height = $rightBorder[0].style.height = (parseInt($box[0].style.height,10) - interfaceHeight)+'px';
    }

    css = {width: settings.w + loadedWidth + interfaceWidth, height: settings.h + loadedHeight + interfaceHeight, top: top, left: left};

    // setting the speed to 0 if the content hasn't changed size or position
    if (speed) {
        var tempSpeed = 0;
        $.each(css, function(i){
            if (css[i] !== previousCSS[i]) {
                tempSpeed = speed;
                return;
            }
        });
        speed = tempSpeed;
    }

    previousCSS = css;

    if (!speed) {
        $box.css(css);
    }

    $box.dequeue().animate(css, {
        duration: speed || 0,
        complete: function () {
            modalDimensions();

            active = false;

            // shrink the wrapper down to exactly the size of colorbox to avoid a bug in IE's iframe implementation.
            $wrap[0].style.width = (settings.w + loadedWidth + interfaceWidth) + "px";
            $wrap[0].style.height = (settings.h + loadedHeight + interfaceHeight) + "px";

            if (settings.get('reposition')) {
                setTimeout(function () {  // small delay before binding onresize due to an IE8 bug.
                    $window.bind('resize.' + prefix, publicMethod.position);
                }, 1);
            }

            if ($.isFunction(loadedCallback)) {
                loadedCallback();
            }
        },
        step: modalDimensions
    });
};

publicMethod.resize = function (options) {
    var scrolltop;

    if (open) {
        options = options || {};

        if (options.width) {
            settings.w = setSize(options.width, 'x') - loadedWidth - interfaceWidth;
        }

        if (options.innerWidth) {
            settings.w = setSize(options.innerWidth, 'x');
        }

        $loaded.css({width: settings.w});

        if (options.height) {
            settings.h = setSize(options.height, 'y') - loadedHeight - interfaceHeight;
        }

        if (options.innerHeight) {
            settings.h = setSize(options.innerHeight, 'y');
        }

        if (!options.innerHeight && !options.height) {
            scrolltop = $loaded.scrollTop();
            $loaded.css({height: "auto"});
            settings.h = $loaded.height();
        }

        $loaded.css({height: settings.h});

        if(scrolltop) {
            $loaded.scrollTop(scrolltop);
        }

        publicMethod.position(settings.get('transition') === "none" ? 0 : settings.get('speed'));
    }
};

publicMethod.prep = function (object) {
    if (!open) {
        return;
    }

    var callback, speed = settings.get('transition') === "none" ? 0 : settings.get('speed');

    $loaded.remove();

    $loaded = $tag(div, 'LoadedContent').append(object);

    function getWidth() {
        settings.w = settings.w || $loaded.width();
        settings.w = settings.mw && settings.mw < settings.w ? settings.mw : settings.w;
        return settings.w;
    }
    function getHeight() {
        settings.h = settings.h || $loaded.height();
        settings.h = settings.mh && settings.mh < settings.h ? settings.mh : settings.h;
        return settings.h;
    }

    $loaded.hide()
    .appendTo($loadingBay.show())// content has to be appended to the DOM for accurate size calculations.
    .css({width: getWidth(), overflow: settings.get('scrolling') ? 'auto' : 'hidden'})
    .css({height: getHeight()})// sets the height independently from the width in case the new width influences the value of height.
    .prependTo($content);

    $loadingBay.hide();

    // floating the IMG removes the bottom line-height and fixed a problem where IE miscalculates the width of the parent element as 100% of the document width.

    $(photo).css({'float': 'none'});

    setClass(settings.get('className'));

    callback = function () {
        var total = $related.length,
            iframe,
            complete;

        if (!open) {
            return;
        }

        function removeFilter() { // Needed for IE8 in versions of jQuery prior to 1.7.2
            if ($.support.opacity === false) {
                $box[0].style.removeAttribute('filter');
            }
        }

        complete = function () {
            clearTimeout(loadingTimer);
            $loadingOverlay.hide();
            trigger(event_complete);
            settings.get('onComplete');
        };


        $title.html(settings.get('title')).show();
        $loaded.show();

        if (total > 1) { // handle grouping
            if (typeof settings.get('current') === "string") {
                $current.html(settings.get('current').replace('{current}', index + 1).replace('{total}', total)).show();
            }

            $next[(settings.get('loop') || index < total - 1) ? "show" : "hide"]().html(settings.get('next'));
            $prev[(settings.get('loop') || index) ? "show" : "hide"]().html(settings.get('previous'));

            slideshow();

            // Preloads images within a rel group
            if (settings.get('preloading')) {
                $.each([getIndex(-1), getIndex(1)], function(){
                    var img,
                        i = $related[this],
                        settings = new Settings(i, $.data(i, colorbox)),
                        src = settings.get('href');

                    if (src && isImage(settings, src)) {
                        src = retinaUrl(settings, src);
                        img = document.createElement('img');
                        img.src = src;
                    }
                });
            }
        } else {
            $groupControls.hide();
        }

        if (settings.get('iframe')) {
            iframe = document.createElement('iframe');

            if ('frameBorder' in iframe) {
                iframe.frameBorder = 0;
            }

            if ('allowTransparency' in iframe) {
                iframe.allowTransparency = "true";
            }

            if (!settings.get('scrolling')) {
                iframe.scrolling = "no";
            }

            $(iframe)
                .attr({
                    src: settings.get('href'),
                    name: (new Date()).getTime(), // give the iframe a unique name to prevent caching
                    'class': prefix + 'Iframe',
                    allowFullScreen : true // allow HTML5 video to go fullscreen
                })
                .one('load', complete)
                .appendTo($loaded);

            $events.one(event_purge, function () {
                iframe.src = "//about:blank";
            });

            if (settings.get('fastIframe')) {
                $(iframe).trigger('load');
            }
        } else {
            complete();
        }

        if (settings.get('transition') === 'fade') {
            $box.fadeTo(speed, 1, removeFilter);
        } else {
            removeFilter();
        }
    };

    if (settings.get('transition') === 'fade') {
        $box.fadeTo(speed, 0, function () {
            publicMethod.position(0, callback);
        });
    } else {
        publicMethod.position(speed, callback);
    }
};

Solution

  • Try something like this:

    $("a.button.download").on("click",function(){ 
        $.fn.colorbox.close();
    });
    

    I didn't see a spot where it was called above, but if a click event is bound to that element somewhere else, you'll want to make sure you bind it there instead of by itself.