diff --git a/themes/bootstrap3/js/lightbox.js b/themes/bootstrap3/js/lightbox.js index 4037500959fa6ca39dc020e0e9cfe77db9e489b0..b71b23ee9d2232f85909e2dde2c14f4912176dcc 100644 --- a/themes/bootstrap3/js/lightbox.js +++ b/themes/bootstrap3/js/lightbox.js @@ -1,411 +1,411 @@ -/*global checkSaveStatuses, console, deparam, path, Recaptcha, vufindString */ - -var Lightbox = { - /** - * We save the URL and POST data every time we call getByUrl. - * If we don't have a target a form submission, we use these variables - * to replicate empty target behaviour by submitting to the current "page". - */ - lastURL: false, - lastPOST: false, - openingURL: false, - shown: false, // Is the lightbox deployed? - XHR: false, // Used for current in-progress XHR lightbox request - openStack: [], // Array of functions to be called after changeContent or the lightbox event 'shown' - closeStack: [], // Array of functions to be called and cleared after the lightbox event 'hidden' - formHandlers: [], // Full custom handlers for forms; by name - formCallbacks: [], // Custom functions for forms, called after .submit(); by name - - /**********************************/ - /* ====== INTERFACE ====== */ - /**********************************/ - /** - * Register custom open event handlers - * - * Think of this as the $(document).ready() of the Lightbox - * There's actually an alias right below it. - * - * If your template has inline JS, $(document).ready() will not fire in the lightbox - * because it already fired before you opened the lightbox and won't fire again. - * - * You can use $.isReady to determine if ready() has already been called - * so you can trigger your function immediately in the inline JS. - */ - addOpenAction: function(func) { - this.openStack.push(func); - }, - // Alias for addOpenAction - ready: function(func) { - this.openStack.push(func); - }, - /** - * Register custom close event handlers - */ - addCloseAction: function(func) { - this.closeStack.push(func); - }, - /** - * For when you want to handle that form all by yourself - * - * We recommend using the getLightbox action in the AJAX Controller - * to ensure you get a lightbox formatted page. - * - * If your handler doesn't return false, the form will submit the normal way, - * with all normal behavior that goes with: redirection, etc. - */ - addFormHandler: function(formName, func) { - this.formHandlers[formName] = func; - }, - /** - * Register a function to be called when a form submission succeeds - * - * We add error checking by default, you never know when error blocks will strike. - * Passing false to expectsError turns this off. Errors are inserted above *current* content. - */ - addFormCallback: function(formName, func, expectsError) { - if(typeof expectsError === "undefined" || expectsError) { - this.formCallbacks[formName] = function(html) { - Lightbox.checkForError(html, func); - }; - } else { - this.formCallbacks[formName] = func; - } - }, - /** - * We store all the ajax calls in case we need to cancel. - * This function cancels the previous call and creates a new one. - */ - ajax: function(obj) { - if(this.XHR) { - this.XHR.abort(); - } - this.XHR = $.ajax(obj); - }, - /**********************************/ - /* ====== LIGHTBOX ACTIONS ====== */ - /**********************************/ - /** - * Change the content of the lightbox. - * - * Hide the header if it's empty to make more - * room for content and avoid double headers. - */ - titleSet: false, - changeContent: function(html) { - var header = $('#modal .modal-header'); - if(!Lightbox.titleSet) { - var h2 = html.match(/<h2>([^<]*)<\/h2>/); - if(h2) { - header.find('.modal-title').html(h2[1]); - } else { - var pLead = html.match(/<p class="lead[^>]*>([^<]*)<\/p>/); - if(pLead) { - header.find('.modal-title').html(pLead[1]); - } - } - Lightbox.titleSet = false; - } - if(header.find('.modal-title').html().length == 0) { - header.css('border-bottom-width', '0'); - } else { - header.css('border-bottom-width', '1px'); - } - $('#modal .modal-body').html(html).modal({'show':true,'backdrop':false}); - Lightbox.openActions(); - }, - - /** - * This is the function you call to manually close the lightbox - */ - close: function(evt) { - $('#modal').modal('hide'); // This event calls closeActions - }, - /** - * This function is attached to the lightbox close event, - * so it always runs when the lightbox is closed. - */ - closeActions: function() { - Lightbox.shown = false; - Lightbox.openingURL = false; - // Clean out stack - while(Lightbox.closeStack.length > 0) { - var f = Lightbox.closeStack.pop(); - f(); - } - if(this.XHR) { this.XHR.abort(); } - // Reset content so we start fresh when we open a lightbox - $('#modal').removeData('modal'); - $('#modal').find('.modal-title').html(''); - $('#modal').find('.modal-body').html(vufindString.loading + "..."); - }, - /** - * Call all the functions we need for when the modal loads - * - * Called by the 'shown' event and at the end of changeContent - */ - openActions: function() { - for(var i=0;i<Lightbox.openStack.length;i++) { - Lightbox.openStack[i](); - } - }, - /** - * This function changes the content of the lightbox to a message with a close button - */ - confirm: function(message) { - this.changeContent('<div class="alert alert-info">'+message+'</div><button class="btn btn-default" onClick="Lightbox.close()">'+vufindString['close']+'</button>'); - }, - /** - * Regexes a piece of html to find an error alert - * If one is found, display it - * - * If one is not found, return html to a success callback function - */ - checkForError: function(html, success) { - var fi = html.indexOf('<div class="alert alert-danger">'); - if(fi > -1) { - var li = html.indexOf('</div>', fi+31); - Lightbox.displayError(html.substring(fi+31, li).replace(/^[\s<>]+|[\s<>]+$/g, '')); - } else { - success(html); - } - }, - /** - * Insert an error alert element at the top of the lightbox - */ - displayError: function(message) { - var alert = $('#modal .modal-body .alert'); - var html = $.parseHTML($('#modal .modal-body').html()); - // Page with alert already present - if(alert.length > 0 && html.length > 1) { - $(alert).html(message); - // Empty or alert only, change to message with button - } else if($('#modal .modal-body').html() == vufindString.loading+"..." - || (html.length == 1 && $(html).hasClass('alert-danger'))) { - Lightbox.changeContent('<div class="alert alert-danger">'+message+'</div><button class="btn btn-default" onClick="Lightbox.close()">'+vufindString['close']+'</button>'); - // Page without alert - } else { - $('#modal .modal-body').prepend('<div class="alert alert-danger">'+message+'</div>'); - } - $('.fa-spinner').remove(); - if (typeof Recaptcha !== "undefined" && Recaptcha.widget) { - Recaptcha.reload(); - } - }, - - /***********************************/ - /* ====== LIGHTBOX REQUESTS ====== */ - /***********************************/ - /** - * This function creates an XHR request to the URL - * and handles the response according to the callback. - * - * Default callback is changeContent - */ - getByUrl: function(url, post, callback) { - if(typeof callback == "undefined") { - // No custom handler: display return in lightbox - callback = this.changeContent; - } - // If the lightbox isn't visible, fix that - if(this.shown == false) { - $('#modal').modal('show'); - this.shown = true; - } - // Create our AJAX request, store it in case we need to cancel later - this.ajax({ - type:'POST', - url:url, - data:post, - success:function(html) { // Success! - callback(html); - }, - error:function(d,e) { - if (d.status == 200) { - try { - var data = JSON.parse(d.responseText); - Lightbox.changeContent('<p class="alert alert-danger">'+data.data+'</p>'); - } catch(error) { - Lightbox.changeContent('<p class="alert alert-danger">'+d.responseText+'</p>'); - } - } else if(d.status > 0) { - Lightbox.changeContent('<p class="alert alert-danger">'+d.statusText+' ('+d.status+')</p>'); - } - console.log(e,d); // Error reporting - console.log(url,post); - } - }); - // Store current "page" context for empty targets - if(this.openingURL === false) { - this.openingURL = url; - } - this.lastURL = url; - this.lastPOST = post; - //this.openActions(); - return false; - }, - /** - * This is the friendly face to the function above. - * It converts a Controller and Action into a URL through the AJAX handler - * with GET and pushes the data and callback to the getByUrl - */ - get: function(controller, action, get, post, callback) { - // Build URL - var url = path+'/AJAX/JSON?method=getLightbox&submodule='+controller+'&subaction='+action; - if(typeof get !== "undefined" && get !== {}) { - url += '&'+$.param(get); - } - if(typeof post == "undefined") { - post = {}; - } - return this.getByUrl(url, post, callback); - }, - - /**********************************/ - /* ====== FORM SUBMISSIONS ====== */ - /**********************************/ - /** - * Returns all the input values from a form as an associated array - * - * This function takes a jQuery wrapped form - * $(event.target) for example - */ - getFormData: function($form) { - // Gather all the data - var inputs = $form.find('*[name]'); - var data = {}; - for(var i=0;i<inputs.length;i++) { - var currentName = inputs[i].name; - var array = currentName.substring(currentName.length-2) == '[]'; - if(array && !data[currentName.substring(0,currentName.length-2)]) { - data[currentName.substring(0,currentName.length-2)] = []; - } - // Submit buttons - if(inputs[i].type == 'submit') { - if($(inputs[i]).attr('clicked') == 'true') { - data[currentName] = inputs[i].value; - } - // Radio buttons - } else if(inputs[i].type == 'radio') { - if(inputs[i].checked) { - if(array) { - var n = currentName.substring(0,currentName.length-2); - data[n].push(inputs[i].value); - } else { - data[currentName] = inputs[i].value; - } - } - // Checkboxes - } else if($(inputs[i]).attr('type') != 'checkbox' || inputs[i].checked) { - if(array) { - var f = currentName.substring(0,currentName.length-2); - data[f].push(inputs[i].value); - } else { - data[currentName] = inputs[i].value; - } - } - } - return data; - }, - /** - * This function adds submission events to forms loaded inside the lightbox - * - * First, it will check for custom handlers, for those who want to handle everything. - * - * Then, it will check for custom form callbacks. These will be added to an anonymous - * function that will call Lightbox.submit with the form and the callback. - * - * Finally, if nothing custom is setup, it will add the default function which - * calls Lightbox.submit with a callback to close if there are no errors to display. - * - * This is a default open action, so it runs every time changeContent - * is called and the 'shown' lightbox event is triggered - */ - registerForms: function() { - var form = $("#modal").find('form'); - var name = $(form).attr('name'); - // Assign form handler based on name - if(typeof name !== "undefined" && typeof Lightbox.formHandlers[name] !== "undefined") { - $(form).unbind('submit').submit(Lightbox.formHandlers[name]); - // Default action, with custom callback - } else if(typeof Lightbox.formCallbacks[name] !== "undefined") { - $(form).unbind('submit').submit(function(evt){ - Lightbox.submit($(evt.target), Lightbox.formCallbacks[name]); - return false; - }); - // Default - } else { - $(form).unbind('submit').submit(function(evt){ - Lightbox.submit($(evt.target), function(html){ - Lightbox.checkForError(html, Lightbox.close); - }); - return false; - }); - } - }, - /** - * The default, automatic form submission - * - * This function gleans all the information in a form from the function above - * Then it uses the action="" attribute of the form to figure out where to send the data - * and the method="" attribute to send it the proper way - * - * In the wild, forms without an action="" are submitted to the current URL. - * In the case where we have a form with no action in the lightbox, - * we emulate that behaviour by submitting the last URL loaded through - * .getByUrl, stored in lastURL in the Lightbox object. - */ - submit: function($form, callback) { - // Default callback is to close - if(typeof callback == "undefined") { - callback = this.close; - } - var data = this.getFormData($form); - // If we have an action: parse - var POST = $form.attr('method') && $form.attr('method').toUpperCase() == 'POST'; - if($form.attr('action')) { - // Parse action location - var action = $form.attr('action').substring($form.attr('action').indexOf(path)+path.length+1); - var params = action.split('?'); - action = action.split('/'); - var get = params.length > 1 ? deparam(params[1]) : data['id'] ? {id:data['id']} : {}; - if(POST) { - this.get(action[0], action[action.length-1], get, data, callback); - } else { - this.get(action[0], action[action.length-1], data, {}, callback); - } - // If not: fake context by using the previous action - } else if(POST) { - this.getByUrl(this.lastURL, data, callback); - } else { - this.getByUrl(this.lastURL, {}, callback); - } - $(this).find('.modal-body').html(vufindString.loading + "..."); - } -}; - -/** - * This is where you add click events to open the lightbox. - * We do it here so that non-JS users still have a good time. - */ -$(document).ready(function() { - // Add handlers to the forms - Lightbox.addOpenAction(Lightbox.registerForms); - /** - * Hook into the Bootstrap close event - * - * Yes, the secret's out, our beloved Lightbox is a modal - */ - $('#modal').on('hidden.bs.modal', Lightbox.closeActions); - /** - * If a link with the class .modal-link triggers the lightbox, - * look for a title="" to use as our lightbox title. - */ - $('.modal-link,.help-link').click(function() { - var title = $(this).attr('title'); - if(typeof title === "undefined") { - title = $(this).html(); - } - $('#modal .modal-title').html(title); - Lightbox.titleSet = true; - }); +/*global checkSaveStatuses, console, deparam, path, Recaptcha, vufindString */ + +var Lightbox = { + /** + * We save the URL and POST data every time we call getByUrl. + * If we don't have a target a form submission, we use these variables + * to replicate empty target behaviour by submitting to the current "page". + */ + lastURL: false, + lastPOST: false, + openingURL: false, + shown: false, // Is the lightbox deployed? + XHR: false, // Used for current in-progress XHR lightbox request + openStack: [], // Array of functions to be called after changeContent or the lightbox event 'shown' + closeStack: [], // Array of functions to be called and cleared after the lightbox event 'hidden' + formHandlers: [], // Full custom handlers for forms; by name + formCallbacks: [], // Custom functions for forms, called after .submit(); by name + + /**********************************/ + /* ====== INTERFACE ====== */ + /**********************************/ + /** + * Register custom open event handlers + * + * Think of this as the $(document).ready() of the Lightbox + * There's actually an alias right below it. + * + * If your template has inline JS, $(document).ready() will not fire in the lightbox + * because it already fired before you opened the lightbox and won't fire again. + * + * You can use $.isReady to determine if ready() has already been called + * so you can trigger your function immediately in the inline JS. + */ + addOpenAction: function(func) { + this.openStack.push(func); + }, + // Alias for addOpenAction + ready: function(func) { + this.openStack.push(func); + }, + /** + * Register custom close event handlers + */ + addCloseAction: function(func) { + this.closeStack.push(func); + }, + /** + * For when you want to handle that form all by yourself + * + * We recommend using the getLightbox action in the AJAX Controller + * to ensure you get a lightbox formatted page. + * + * If your handler doesn't return false, the form will submit the normal way, + * with all normal behavior that goes with: redirection, etc. + */ + addFormHandler: function(formName, func) { + this.formHandlers[formName] = func; + }, + /** + * Register a function to be called when a form submission succeeds + * + * We add error checking by default, you never know when error blocks will strike. + * Passing false to expectsError turns this off. Errors are inserted above *current* content. + */ + addFormCallback: function(formName, func, expectsError) { + if(typeof expectsError === "undefined" || expectsError) { + this.formCallbacks[formName] = function(html) { + Lightbox.checkForError(html, func); + }; + } else { + this.formCallbacks[formName] = func; + } + }, + /** + * We store all the ajax calls in case we need to cancel. + * This function cancels the previous call and creates a new one. + */ + ajax: function(obj) { + if(this.XHR) { + this.XHR.abort(); + } + this.XHR = $.ajax(obj); + }, + /**********************************/ + /* ====== LIGHTBOX ACTIONS ====== */ + /**********************************/ + /** + * Change the content of the lightbox. + * + * Hide the header if it's empty to make more + * room for content and avoid double headers. + */ + titleSet: false, + changeContent: function(html) { + var header = $('#modal .modal-header'); + if(!Lightbox.titleSet) { + var h2 = html.match(/<h2>([^<]*)<\/h2>/); + if(h2) { + header.find('.modal-title').html(h2[1]); + } else { + var pLead = html.match(/<p class="lead[^>]*>([^<]*)<\/p>/); + if(pLead) { + header.find('.modal-title').html(pLead[1]); + } + } + Lightbox.titleSet = false; + } + if(header.find('.modal-title').html().length == 0) { + header.css('border-bottom-width', '0'); + } else { + header.css('border-bottom-width', '1px'); + } + $('#modal .modal-body').html(html).modal({'show':true,'backdrop':false}); + Lightbox.openActions(); + }, + + /** + * This is the function you call to manually close the lightbox + */ + close: function(evt) { + $('#modal').modal('hide'); // This event calls closeActions + }, + /** + * This function is attached to the lightbox close event, + * so it always runs when the lightbox is closed. + */ + closeActions: function() { + Lightbox.shown = false; + Lightbox.openingURL = false; + // Clean out stack + while(Lightbox.closeStack.length > 0) { + var f = Lightbox.closeStack.pop(); + f(); + } + if(this.XHR) { this.XHR.abort(); } + // Reset content so we start fresh when we open a lightbox + $('#modal').removeData('modal'); + $('#modal').find('.modal-title').html(''); + $('#modal').find('.modal-body').html(vufindString.loading + "..."); + }, + /** + * Call all the functions we need for when the modal loads + * + * Called by the 'shown' event and at the end of changeContent + */ + openActions: function() { + for(var i=0;i<Lightbox.openStack.length;i++) { + Lightbox.openStack[i](); + } + }, + /** + * This function changes the content of the lightbox to a message with a close button + */ + confirm: function(message) { + this.changeContent('<div class="alert alert-info">'+message+'</div><button class="btn btn-default" onClick="Lightbox.close()">'+vufindString['close']+'</button>'); + }, + /** + * Regexes a piece of html to find an error alert + * If one is found, display it + * + * If one is not found, return html to a success callback function + */ + checkForError: function(html, success) { + var fi = html.indexOf('<div class="alert alert-danger">'); + if(fi > -1) { + var li = html.indexOf('</div>', fi+31); + Lightbox.displayError(html.substring(fi+31, li).replace(/^[\s<>]+|[\s<>]+$/g, '')); + } else { + success(html); + } + }, + /** + * Insert an error alert element at the top of the lightbox + */ + displayError: function(message) { + var alert = $('#modal .modal-body .alert'); + var html = $.parseHTML($('#modal .modal-body').html()); + // Page with alert already present + if(alert.length > 0 && html.length > 1) { + $(alert).html(message); + // Empty or alert only, change to message with button + } else if($('#modal .modal-body').html() == vufindString.loading+"..." + || (html.length == 1 && $(html).hasClass('alert-danger'))) { + Lightbox.changeContent('<div class="alert alert-danger" role="alert">'+message+'</div><button class="btn btn-default" onClick="Lightbox.close()">'+vufindString['close']+'</button>'); + // Page without alert + } else { + $('#modal .modal-body').prepend('<div class="alert alert-danger alert-dismissible" role="alert"><button type="button" class="close" data-dismiss="alert"><span aria-hidden="true">×</span><span class="sr-only">Close</span></button>'+message+'</div>'); + } + $('.fa-spinner').remove(); + if (typeof Recaptcha !== "undefined" && Recaptcha.widget) { + Recaptcha.reload(); + } + }, + + /***********************************/ + /* ====== LIGHTBOX REQUESTS ====== */ + /***********************************/ + /** + * This function creates an XHR request to the URL + * and handles the response according to the callback. + * + * Default callback is changeContent + */ + getByUrl: function(url, post, callback) { + if(typeof callback == "undefined") { + // No custom handler: display return in lightbox + callback = this.changeContent; + } + // If the lightbox isn't visible, fix that + if(this.shown == false) { + $('#modal').modal('show'); + this.shown = true; + } + // Create our AJAX request, store it in case we need to cancel later + this.ajax({ + type:'POST', + url:url, + data:post, + success:function(html) { // Success! + callback(html); + }, + error:function(d,e) { + if (d.status == 200) { + try { + var data = JSON.parse(d.responseText); + Lightbox.changeContent('<p class="alert alert-danger">'+data.data+'</p>'); + } catch(error) { + Lightbox.changeContent('<p class="alert alert-danger">'+d.responseText+'</p>'); + } + } else if(d.status > 0) { + Lightbox.changeContent('<p class="alert alert-danger">'+d.statusText+' ('+d.status+')</p>'); + } + console.log(e,d); // Error reporting + console.log(url,post); + } + }); + // Store current "page" context for empty targets + if(this.openingURL === false) { + this.openingURL = url; + } + this.lastURL = url; + this.lastPOST = post; + //this.openActions(); + return false; + }, + /** + * This is the friendly face to the function above. + * It converts a Controller and Action into a URL through the AJAX handler + * with GET and pushes the data and callback to the getByUrl + */ + get: function(controller, action, get, post, callback) { + // Build URL + var url = path+'/AJAX/JSON?method=getLightbox&submodule='+controller+'&subaction='+action; + if(typeof get !== "undefined" && get !== {}) { + url += '&'+$.param(get); + } + if(typeof post == "undefined") { + post = {}; + } + return this.getByUrl(url, post, callback); + }, + + /**********************************/ + /* ====== FORM SUBMISSIONS ====== */ + /**********************************/ + /** + * Returns all the input values from a form as an associated array + * + * This function takes a jQuery wrapped form + * $(event.target) for example + */ + getFormData: function($form) { + // Gather all the data + var inputs = $form.find('*[name]'); + var data = {}; + for(var i=0;i<inputs.length;i++) { + var currentName = inputs[i].name; + var array = currentName.substring(currentName.length-2) == '[]'; + if(array && !data[currentName.substring(0,currentName.length-2)]) { + data[currentName.substring(0,currentName.length-2)] = []; + } + // Submit buttons + if(inputs[i].type == 'submit') { + if($(inputs[i]).attr('clicked') == 'true') { + data[currentName] = inputs[i].value; + } + // Radio buttons + } else if(inputs[i].type == 'radio') { + if(inputs[i].checked) { + if(array) { + var n = currentName.substring(0,currentName.length-2); + data[n].push(inputs[i].value); + } else { + data[currentName] = inputs[i].value; + } + } + // Checkboxes + } else if($(inputs[i]).attr('type') != 'checkbox' || inputs[i].checked) { + if(array) { + var f = currentName.substring(0,currentName.length-2); + data[f].push(inputs[i].value); + } else { + data[currentName] = inputs[i].value; + } + } + } + return data; + }, + /** + * This function adds submission events to forms loaded inside the lightbox + * + * First, it will check for custom handlers, for those who want to handle everything. + * + * Then, it will check for custom form callbacks. These will be added to an anonymous + * function that will call Lightbox.submit with the form and the callback. + * + * Finally, if nothing custom is setup, it will add the default function which + * calls Lightbox.submit with a callback to close if there are no errors to display. + * + * This is a default open action, so it runs every time changeContent + * is called and the 'shown' lightbox event is triggered + */ + registerForms: function() { + var form = $("#modal").find('form'); + var name = $(form).attr('name'); + // Assign form handler based on name + if(typeof name !== "undefined" && typeof Lightbox.formHandlers[name] !== "undefined") { + $(form).unbind('submit').submit(Lightbox.formHandlers[name]); + // Default action, with custom callback + } else if(typeof Lightbox.formCallbacks[name] !== "undefined") { + $(form).unbind('submit').submit(function(evt){ + Lightbox.submit($(evt.target), Lightbox.formCallbacks[name]); + return false; + }); + // Default + } else { + $(form).unbind('submit').submit(function(evt){ + Lightbox.submit($(evt.target), function(html){ + Lightbox.checkForError(html, Lightbox.close); + }); + return false; + }); + } + }, + /** + * The default, automatic form submission + * + * This function gleans all the information in a form from the function above + * Then it uses the action="" attribute of the form to figure out where to send the data + * and the method="" attribute to send it the proper way + * + * In the wild, forms without an action="" are submitted to the current URL. + * In the case where we have a form with no action in the lightbox, + * we emulate that behaviour by submitting the last URL loaded through + * .getByUrl, stored in lastURL in the Lightbox object. + */ + submit: function($form, callback) { + // Default callback is to close + if(typeof callback == "undefined") { + callback = this.close; + } + var data = this.getFormData($form); + // If we have an action: parse + var POST = $form.attr('method') && $form.attr('method').toUpperCase() == 'POST'; + if($form.attr('action')) { + // Parse action location + var action = $form.attr('action').substring($form.attr('action').indexOf(path)+path.length+1); + var params = action.split('?'); + action = action.split('/'); + var get = params.length > 1 ? deparam(params[1]) : data['id'] ? {id:data['id']} : {}; + if(POST) { + this.get(action[0], action[action.length-1], get, data, callback); + } else { + this.get(action[0], action[action.length-1], data, {}, callback); + } + // If not: fake context by using the previous action + } else if(POST) { + this.getByUrl(this.lastURL, data, callback); + } else { + this.getByUrl(this.lastURL, {}, callback); + } + $(this).find('.modal-body').html(vufindString.loading + "..."); + } +}; + +/** + * This is where you add click events to open the lightbox. + * We do it here so that non-JS users still have a good time. + */ +$(document).ready(function() { + // Add handlers to the forms + Lightbox.addOpenAction(Lightbox.registerForms); + /** + * Hook into the Bootstrap close event + * + * Yes, the secret's out, our beloved Lightbox is a modal + */ + $('#modal').on('hidden.bs.modal', Lightbox.closeActions); + /** + * If a link with the class .modal-link triggers the lightbox, + * look for a title="" to use as our lightbox title. + */ + $('.modal-link,.help-link').click(function() { + var title = $(this).attr('title'); + if(typeof title === "undefined") { + title = $(this).html(); + } + $('#modal .modal-title').html(title); + Lightbox.titleSet = true; + }); }); \ No newline at end of file diff --git a/themes/bootstrap3/templates/cart/email.phtml b/themes/bootstrap3/templates/cart/email.phtml index 56a62ab00a6d22e28a8c5899989d44f589595363..d279a9202b4f88ce65d1a3dd2f998df76cd34e77 100644 --- a/themes/bootstrap3/templates/cart/email.phtml +++ b/themes/bootstrap3/templates/cart/email.phtml @@ -1,66 +1,66 @@ -<? - // Set page title. - $this->headTitle($this->translate('email_selected_favorites')); - - // Set up breadcrumbs: - $this->layout()->breadcrumbs = '<li>' . $this->getLastSearchLink($this->transEsc('Search'), '', '</li> ') - . '<li><a href="' .$this->url('cart-home'). '">' .$this->transEsc('Cart'). '</a></li> ' - . '<li class="active">' . $this->transEsc('email_selected_favorites') . '</li>'; -?> -<?=$this->flashmessages()?> -<form class="form-horizontal" action="<?=$this->url('cart-email')?>" method="post" name="bulkEmail"> - <? foreach ($this->records as $current): ?> - <input type="hidden" name="ids[]" value="<?=$this->escapeHtmlAttr($current->getResourceSource() . '|' . $current->getUniqueId())?>" /> - <? endforeach; ?> - <div class="form-group"> - <label class="col-sm-3 control-label"><?=$this->transEsc('Title')?></label> - <div class="col-sm-9"> - <? if(count($this->records) > 1): ?> - <button type="button" class="btn btn-default hidden" data-toggle="collapse" data-target="#itemhide"> - <?=count($this->records).' '.$this->transEsc('items') ?> - </button> - <div id="itemhide" class="collapse in"> - <ul> - <? foreach ($this->records as $current): ?> - <li><?=$this->escapeHtml($current->getBreadcrumb())?></li> - <? endforeach; ?> - </ul> - </div> - <? else: ?> - <span class="uneditable-input"><?=$this->records[0]->getBreadcrumb() ?></span> - <? endif; ?> - </div> - </div> - <div class="form-group"> - <label class="col-sm-3 control-label" for="email_to"><?=$this->transEsc('To')?>:</label> - <div class="col-sm-9"> - <input id="email_to" type="email" name="to" value="<?=isset($this->to) ? $this->to : ''?>" size="40" class="form-control" oninvalid="$('#modal .fa-spinner').remove()"/> - </div> - </div> - <? if (!$this->disableFrom): ?> - <div class="form-group"> - <label class="col-sm-3 control-label" for="email_from"><?=$this->transEsc('From')?>:</label> - <div class="col-sm-9"> - <input id="email_from" type="email" name="from" value="<?=isset($this->from) ? $this->from : ''?>" size="40" class="form-control" oninvalid="$('#modal .fa-spinner').remove()"/> - </div> - </div> - <? endif; ?> - <div class="form-group"> - <label class="col-sm-3 control-label" for="email_message"><?=$this->transEsc('Message')?>:</label> - <div class="col-sm-9"> - <textarea id="email_message" name="message" rows="3" cols="40" class="form-control"><?=isset($this->message) ? $this->message : ''?></textarea> - </div> - </div> - <div class="form-group"> - <div class="col-sm-9 col-sm-offset-3"> - <input class="btn btn-primary" type="submit" name="submit" value="<?=$this->transEsc('Send')?>"/> - </div> - </div> -</form> -<? - $script = <<<JS - $('button.btn.hidden').removeClass('hidden'); - $('.collapse.in').removeClass('in'); -JS; -?> +<? + // Set page title. + $this->headTitle($this->translate('email_selected_favorites')); + + // Set up breadcrumbs: + $this->layout()->breadcrumbs = '<li>' . $this->getLastSearchLink($this->transEsc('Search'), '', '</li> ') + . '<li><a href="' .$this->url('cart-home'). '">' .$this->transEsc('Cart'). '</a></li> ' + . '<li class="active">' . $this->transEsc('email_selected_favorites') . '</li>'; +?> +<?=$this->flashmessages()?> +<form class="form-horizontal" action="<?=$this->url('cart-email')?>" method="post" name="bulkEmail"> + <? foreach ($this->records as $current): ?> + <input type="hidden" name="ids[]" value="<?=$this->escapeHtmlAttr($current->getResourceSource() . '|' . $current->getUniqueId())?>" /> + <? endforeach; ?> + <div class="form-group"> + <label class="col-sm-3 control-label"><?=$this->transEsc('Title')?></label> + <div class="col-sm-9"> + <? if(count($this->records) > 1): ?> + <button type="button" class="btn btn-default hidden" data-toggle="collapse" data-target="#itemhide"> + <?=count($this->records).' '.$this->transEsc('items') ?> + </button> + <div id="itemhide" class="collapse in"> + <ul> + <? foreach ($this->records as $current): ?> + <li><?=$this->escapeHtml($current->getBreadcrumb())?></li> + <? endforeach; ?> + </ul> + </div> + <? else: ?> + <p class="form-control-static"><?=$this->records[0]->getBreadcrumb() ?></p> + <? endif; ?> + </div> + </div> + <div class="form-group"> + <label class="col-sm-3 control-label" for="email_to"><?=$this->transEsc('To')?>:</label> + <div class="col-sm-9"> + <input id="email_to" type="email" name="to" value="<?=isset($this->to) ? $this->to : ''?>" size="40" class="form-control" oninvalid="$('#modal .fa-spinner').remove()"/> + </div> + </div> + <? if (!$this->disableFrom): ?> + <div class="form-group"> + <label class="col-sm-3 control-label" for="email_from"><?=$this->transEsc('From')?>:</label> + <div class="col-sm-9"> + <input id="email_from" type="email" name="from" value="<?=isset($this->from) ? $this->from : ''?>" size="40" class="form-control" oninvalid="$('#modal .fa-spinner').remove()"/> + </div> + </div> + <? endif; ?> + <div class="form-group"> + <label class="col-sm-3 control-label" for="email_message"><?=$this->transEsc('Message')?>:</label> + <div class="col-sm-9"> + <textarea id="email_message" name="message" rows="3" cols="40" class="form-control"><?=isset($this->message) ? $this->message : ''?></textarea> + </div> + </div> + <div class="form-group"> + <div class="col-sm-9 col-sm-offset-3"> + <input class="btn btn-primary" type="submit" name="submit" value="<?=$this->transEsc('Send')?>"/> + </div> + </div> +</form> +<? + $script = <<<JS + $('button.btn.hidden').removeClass('hidden'); + $('.collapse.in').removeClass('in'); +JS; +?> <?=$this->inlineScript(\Zend\View\Helper\HeadScript::SCRIPT, $script, 'SET') ?> \ No newline at end of file