diff --git a/templates/zephyr/compose.html b/templates/zephyr/compose.html index 0dc1ef6870..53859b44ac 100644 --- a/templates/zephyr/compose.html +++ b/templates/zephyr/compose.html @@ -1,6 +1,5 @@
-
×
× diff --git a/zephyr/static/js/compose.js b/zephyr/static/js/compose.js index 0282c17981..9d849fca7e 100644 --- a/zephyr/static/js/compose.js +++ b/zephyr/static/js/compose.js @@ -213,10 +213,6 @@ exports.start = function (msg_type, opts) { show('private', $("#" + (focus_area || 'private_message_recipient'))); } - if (message_snapshot !== undefined) { - $('#restore-draft').show(); - } - if (opts.replying_to_message !== undefined) { do_fade(opts.replying_to_message, msg_type); } @@ -239,6 +235,10 @@ exports.cancel = function () { compose.hide(); abort_xhr(); is_composing_message = false; + compose.clear(); + if (message_snapshot !== undefined) { + $('#restore-draft').show(); + } $(document).trigger($.Event('compose_canceled.zephyr')); }; @@ -383,8 +383,8 @@ $(function () { exports.hide = function () { exports.snapshot_message(); $('.message_comp').find('input, textarea, button').blur(); - $('.message_comp').slideUp(100, - function() { $('#compose').css({visibility: "hidden"});}); + $('#stream-message').hide(); + $('#private-message').hide(); notifications_bar.enable(); exports.unfade_messages(true); }; @@ -540,6 +540,15 @@ exports.validate = function () { $(function () { $("#new_message_content").autosize(); + + $("#new_message_content").click(function (e) { + // If we click in the composebox, start up a new message + if (!compose.composing()) { + respond_to_message(); + e.stopPropagation(); + } + }); + $("#compose").filedrop({ url: "json/upload_file", fallback_id: "file_input", diff --git a/zephyr/static/js/message_list.js b/zephyr/static/js/message_list.js index 1bb6947dfe..9bbc6f0cff 100644 --- a/zephyr/static/js/message_list.js +++ b/zephyr/static/js/message_list.js @@ -433,7 +433,7 @@ MessageList.prototype = { var selected_row_offset = selected_row.offset().top; var available_space_for_scroll = selected_row_offset - viewport_offset - - $("#floating_recipient_bar").height() - $("#searchbox_form").height(); + $("#floating_recipient_bar").height() - $("#searchbox_form").height() - $("#compose").height(); suppress_scroll_pointer_update = true; // Gets set to false in the scroll handler. // viewport (which is window) doesn't have a scrollTop, so scroll diff --git a/zephyr/static/js/notifications_bar.js b/zephyr/static/js/notifications_bar.js index fce73b116f..8cb9598543 100644 --- a/zephyr/static/js/notifications_bar.js +++ b/zephyr/static/js/notifications_bar.js @@ -53,7 +53,7 @@ exports.update = function () { if (on_custom) show(custom_message); else if (rows.last_visible().offset() !== null // otherwise the next line will error - && rows.last_visible().offset().top + rows.last_visible().height() > viewport.scrollTop() + viewport.height() + && rows.last_visible().offset().top + rows.last_visible().height() > viewport.scrollTop() + viewport.height() - $("#compose").height() && unread_in_current_view() > 0) show("More messages below"); else diff --git a/zephyr/static/js/ui.js b/zephyr/static/js/ui.js index 34ad8478d2..07fa01dc0c 100644 --- a/zephyr/static/js/ui.js +++ b/zephyr/static/js/ui.js @@ -866,6 +866,7 @@ $(function () { var row = $(this).closest(".message_row"); current_msg_list.select_id(rows.id(row)); respond_to_message(); + e.stopPropagation(); } mouse_moved = false; clicking = false; @@ -1018,7 +1019,16 @@ $(function () { $('#user_presences').on('click', 'a', function (e) { var email = $(e.target).attr('data-email'); compose.start('private', {private_message_recipient: email}); + // The preventDefault is necessary so that clicking the + // link doesn't jump us to the top of the page. e.preventDefault(); + // The stopPropagation is necessary so that we don't + // see the following sequence of events: + // 1. This click "opens" the composebox + // 2. This event propagates to the body, which says "oh, hey, the + // composebox is open and you clicked out of it, you must want to + // stop composing!" + e.stopPropagation(); }); $('#stream_filters li').on('click', 'a.subscription_name', function (e) { @@ -1126,6 +1136,19 @@ $(function () { if ($('.popover-inner').has(e.target).length === 0) { ui.hide_actions_popover(); } + + // Unfocus our compose area if we click out of it. + if (compose.composing()) { + compose.cancel(); + } + }); + + $("#compose").click(function (e) { + // Don't let clicks in the compose area count as + // "unfocusing" our compose -- in other words, e.g. + // clicking "Press enter to send" should not + // trigger the composebox-closing code above. + e.stopPropagation(); }); // side-bar-related handlers diff --git a/zephyr/static/styles/zephyr.css b/zephyr/static/styles/zephyr.css index 3e7e221ce6..191e6a5bcb 100644 --- a/zephyr/static/styles/zephyr.css +++ b/zephyr/static/styles/zephyr.css @@ -265,7 +265,6 @@ ul.filters i { } .message_comp { - display: none; border: 1px solid #EEE; background-color: white; padding: 8px 20px 8px 10px; @@ -503,6 +502,7 @@ blockquote p { /* normally 5px 14px; pull in the right and bottom a bit */ padding-right: 5px; padding-bottom: 0px; + border-top-width: 1px; cursor: default; } @@ -559,7 +559,6 @@ img.inline_profile_picture { } #compose { - visibility: hidden; position: fixed; bottom: 0px; background: white; @@ -584,21 +583,12 @@ img.inline_profile_picture { float: right; } -.composebox-close { - padding: 5px; - padding-top: 8px; /* = message_comp padding_top */ -} - .send-status-close:hover { cursor: pointer; opacity: .4; filter: alpha(opacity=40); } -.compose_table #private-message { - display: none; -} - .home-error-bar { margin-top: 5px; display: none; @@ -1072,6 +1062,7 @@ table.floating_recipient { #stream-message, #private-message { border: 1px solid grey; + display: none; } .emoji { diff --git a/zephyr/tests/frontend/common.js b/zephyr/tests/frontend/common.js index 92840364cf..653369f99b 100644 --- a/zephyr/tests/frontend/common.js +++ b/zephyr/tests/frontend/common.js @@ -93,7 +93,7 @@ exports.send_message = function (type, params) { casper.click('#left_bar_compose_' + type + '_button_big'); casper.fill('form[action^="/json/send_message"]', params); casper.click('#compose-send-button'); - casper.waitWhileVisible('#compose', function () { + casper.waitWhileVisible('#stream,#private-message', function () { last_send_or_update = timestamp(); }); }); diff --git a/zephyr/tests/frontend/tests/03-compose.js b/zephyr/tests/frontend/tests/03-compose.js index 83bc09f1fd..6c2f633ebc 100644 --- a/zephyr/tests/frontend/tests/03-compose.js +++ b/zephyr/tests/frontend/tests/03-compose.js @@ -13,20 +13,20 @@ casper.then(function () { casper.click('#left_bar_compose_stream_button_big'); casper.test.assertVisible('#stream', 'Switching from PM compose to stream compose'); - // Test closing the compose box - casper.click('.composebox-close'); + // Test "closing" the compose box + casper.click('body'); }); -casper.waitWhileVisible('#compose'); +casper.waitWhileVisible('#stream'); casper.then(function () { - casper.test.assertNotVisible('#compose', 'Close stream compose box'); + casper.test.assertNotVisible('#stream', 'Close stream compose box'); casper.click('#left_bar_compose_private_button_big'); - casper.click('.composebox-close'); + casper.click('body'); }); -casper.waitWhileVisible('#compose'); +casper.waitWhileVisible('#private-message'); casper.then(function () { - casper.test.assertNotVisible('#compose', 'Close PM compose box'); + casper.test.assertNotVisible('#private-message', 'Close PM compose box'); }); common.then_log_out();