diff --git a/frontend_tests/casper_tests/09-navigation.js b/frontend_tests/casper_tests/09-navigation.js index 7bd73431aa..912587034f 100644 --- a/frontend_tests/casper_tests/09-navigation.js +++ b/frontend_tests/casper_tests/09-navigation.js @@ -32,7 +32,7 @@ function then_navigate_to_settings() { casper.click('a[href^="#settings"]'); casper.waitUntilVisible('#settings_page', function () { casper.test.assertExists('#settings_page', "Settings page is active"); - casper.click("#settings_page .exit"); + casper.click('#settings_page .exit'); }); }); }); @@ -49,6 +49,7 @@ function then_navigate_to_subscriptions() { casper.click('a[href^="#streams"]'); casper.waitUntilVisible("#subscription_overlay", function () { casper.test.assertExists('#subscriptions_table', "#subscriptions page is active"); + casper.click('#subscription_overlay .exit'); }); }); }); diff --git a/static/js/hashchange.js b/static/js/hashchange.js index 0bb6dbdb7f..1bd975cde9 100644 --- a/static/js/hashchange.js +++ b/static/js/hashchange.js @@ -243,7 +243,7 @@ function hashchanged(from_reload, e) { if (!should_ignore(old_hash || "#") || ignore.group !== get_hash_group(base)) { if (ignore.group !== get_hash_group(base)) { - exports.close_modals(); + modals.close_for_hash_change(); } // now only if the previous one should not have been ignored. @@ -267,7 +267,7 @@ function hashchanged(from_reload, e) { subs.change_state(get_hash_components()); } } else if (!should_ignore(window.location.hash) && !ignore.flag) { - exports.close_modals(); + modals.close_for_hash_change(); changing_hash = true; var ret = do_hashchange(from_reload); changing_hash = false; @@ -290,10 +290,6 @@ exports.initialize = function () { hashchanged(true); }; -exports.close_modals = function () { - $(".overlay.show").removeClass("show"); -}; - exports.exit_modal = function (callback) { if (should_ignore(window.location.hash)) { ui_util.blur_active_element(); diff --git a/static/js/modals.js b/static/js/modals.js index 0065964487..10cd7db836 100644 --- a/static/js/modals.js +++ b/static/js/modals.js @@ -2,7 +2,15 @@ var modals = (function () { var exports = {}; -exports.close = {}; +var active_overlay; +var close_handler; +var open_modal_name; + +function reset_state() { + active_overlay = undefined; + close_handler = undefined; + open_modal_name = undefined; +} exports.open_overlay = function (opts) { if (!opts.name || !opts.overlay || !opts.on_close) { @@ -10,6 +18,12 @@ exports.open_overlay = function (opts) { return; } + if (active_overlay || open_modal_name || close_handler) { + blueslip.error('Programming error--trying to open ' + opts.name + + ' before closing ' + open_modal_name); + return; + } + // Our overlays are kind of crufty...we have an HTML id // attribute for them and then a data-overlay attribute for // them. Make sure they match. @@ -18,22 +32,30 @@ exports.open_overlay = function (opts) { return; } + open_modal_name = opts.name; + active_overlay = opts.overlay; opts.overlay.addClass('show'); - exports.close[opts.name] = function () { + close_handler = function () { opts.on_close(); - exports.close[opts.name] = undefined; + reset_state(); }; }; exports.close_modal = function (name) { - $("[data-overlay='" + name + "']").removeClass("show"); - - if (exports.close[name]) { - exports.close[name](); - } else { + if ((name !== open_modal_name) || !close_handler) { blueslip.error("Modal close handler for " + name + " not properly setup." ); + return; } + + active_overlay.removeClass("show"); + + close_handler(); +}; + +exports.close_for_hash_change = function () { + $(".overlay.show").removeClass("show"); + reset_state(); }; exports.open_settings = function () { @@ -61,15 +83,7 @@ $(function () { var target_name = $target.attr("data-overlay"); - $target.removeClass("show"); - - // if an appropriate clearing/closing function for a modal exists, - // execute it. - if (exports.close[target_name]) { - exports.close[target_name](); - } else { - blueslip.error("Tried to close unknown modal " + target_name); - } + exports.close_modal(target_name); e.preventDefault(); e.stopPropagation();