compose: Improve how we handle over character limit message error.

We improved it in the following ways:
* Show the error message with the maximum character
limit.

* Disable the send button.

* When the user tries to send the message via hotkeys
i.e, When "Press enter to send" is enabled or the user
uses "Shift" + "Enter" shortcut, Flash the red border
around the compose box.

Also renamed `check_and_set_overflow_text` to
`check_overflow_text` for better clarity.
This commit is contained in:
Riken Shah 2021-07-10 17:33:45 +00:00 committed by Tim Abbott
parent 43e7c2c7fa
commit 0dbc7e0d21
6 changed files with 61 additions and 13 deletions

View File

@ -462,29 +462,38 @@ test_ui("test_validate_stream_message_post_policy_full_members_only", ({override
); );
}); });
test_ui("test_check_and_set_overflow_text", () => { test_ui("test_check_overflow_text", () => {
page_params.max_message_length = 10000; page_params.max_message_length = 10000;
const textarea = $("#compose-textarea"); const textarea = $("#compose-textarea");
const indicator = $("#compose_limit_indicator"); const indicator = $("#compose_limit_indicator");
const send_button = $("#compose-send-button");
// Indicator should show red colored text // Indicator should show red colored text
textarea.val("a".repeat(10000 + 1)); textarea.val("a".repeat(10000 + 1));
compose_validate.check_and_set_overflow_text(); compose_validate.check_overflow_text();
assert.ok(indicator.hasClass("over_limit")); assert.ok(indicator.hasClass("over_limit"));
assert.equal(indicator.text(), "10001/10000"); assert.equal(indicator.text(), "10001/10000");
assert.ok(textarea.hasClass("over_limit")); assert.ok(textarea.hasClass("over_limit"));
assert.equal(
$("#compose-error-msg").html(),
"translated HTML: Message length should'nt be greatar than 10000 characters.",
);
assert.ok(send_button.prop("disabled"));
$("#compose-send-status").stop = () => ({fadeOut: () => {}});
// Indicator should show orange colored text // Indicator should show orange colored text
textarea.val("a".repeat(9000 + 1)); textarea.val("a".repeat(9000 + 1));
compose_validate.check_and_set_overflow_text(); compose_validate.check_overflow_text();
assert.ok(!indicator.hasClass("over_limit")); assert.ok(!indicator.hasClass("over_limit"));
assert.equal(indicator.text(), "9001/10000"); assert.equal(indicator.text(), "9001/10000");
assert.ok(!textarea.hasClass("over_limit")); assert.ok(!textarea.hasClass("over_limit"));
assert.ok(!send_button.prop("disabled"));
// Indicator must be empty // Indicator must be empty
textarea.val("a".repeat(9000)); textarea.val("a".repeat(9000));
compose_validate.check_and_set_overflow_text(); compose_validate.check_overflow_text();
assert.ok(!indicator.hasClass("over_limit")); assert.ok(!indicator.hasClass("over_limit"));
assert.equal(indicator.text(), ""); assert.equal(indicator.text(), "");
assert.ok(!textarea.hasClass("over_limit")); assert.ok(!textarea.hasClass("over_limit"));

View File

@ -180,7 +180,7 @@ export function create_message_object() {
export function clear_compose_box() { export function clear_compose_box() {
$("#compose-textarea").val("").trigger("focus"); $("#compose-textarea").val("").trigger("focus");
compose_validate.check_and_set_overflow_text(); compose_validate.check_overflow_text();
drafts.delete_active_draft(); drafts.delete_active_draft();
compose_ui.autosize_textarea($("#compose-textarea")); compose_ui.autosize_textarea($("#compose-textarea"));
$("#compose-send-status").hide(0); $("#compose-send-status").hide(0);
@ -617,7 +617,7 @@ export function initialize() {
}); });
$("#compose-textarea").on("input propertychange", () => { $("#compose-textarea").on("input propertychange", () => {
compose_validate.check_and_set_overflow_text(); compose_validate.check_overflow_text();
}); });
$("#compose form").on("submit", (e) => { $("#compose form").on("submit", (e) => {

View File

@ -113,7 +113,7 @@ function clear_box() {
compose_validate.set_user_acknowledged_announce_flag(undefined); compose_validate.set_user_acknowledged_announce_flag(undefined);
clear_textarea(); clear_textarea();
compose_validate.check_and_set_overflow_text(); compose_validate.check_overflow_text();
$("#compose-textarea").removeData("draft-id"); $("#compose-textarea").removeData("draft-id");
compose_ui.autosize_textarea($("#compose-textarea")); compose_ui.autosize_textarea($("#compose-textarea"));
$("#compose-send-status").hide(0); $("#compose-send-status").hide(0);

View File

@ -464,7 +464,7 @@ function validate_private_message() {
return true; return true;
} }
export function check_and_set_overflow_text() { export function check_overflow_text() {
const text = compose_state.message_content(); const text = compose_state.message_content();
const max_length = page_params.max_message_length; const max_length = page_params.max_message_length;
const indicator = $("#compose_limit_indicator"); const indicator = $("#compose_limit_indicator");
@ -473,20 +473,45 @@ export function check_and_set_overflow_text() {
indicator.addClass("over_limit"); indicator.addClass("over_limit");
$("#compose-textarea").addClass("over_limit"); $("#compose-textarea").addClass("over_limit");
indicator.text(text.length + "/" + max_length); indicator.text(text.length + "/" + max_length);
compose_error.show(
$t_html(
{
defaultMessage:
"Message length should'nt be greatar than {max_length} characters.",
},
{max_length},
),
);
$("#compose-send-button").prop("disabled", true);
} else if (text.length > 0.9 * max_length) { } else if (text.length > 0.9 * max_length) {
indicator.removeClass("over_limit"); indicator.removeClass("over_limit");
$("#compose-textarea").removeClass("over_limit"); $("#compose-textarea").removeClass("over_limit");
indicator.text(text.length + "/" + max_length); indicator.text(text.length + "/" + max_length);
$("#compose-send-button").prop("disabled", false);
if ($("#compose-send-status").hasClass("alert-error")) {
$("#compose-send-status").stop(true).fadeOut();
}
} else { } else {
indicator.text(""); indicator.text("");
$("#compose-textarea").removeClass("over_limit"); $("#compose-textarea").removeClass("over_limit");
$("#compose-send-button").prop("disabled", false);
if ($("#compose-send-status").hasClass("alert-error")) { if ($("#compose-send-status").hasClass("alert-error")) {
$("#compose-send-status").stop(true).fadeOut(); $("#compose-send-status").stop(true).fadeOut();
} }
} }
} }
export function warn_for_text_overflow_when_tries_to_send() {
if (compose_state.message_content().length > page_params.max_message_length) {
$("#compose-textarea").addClass("flash");
setTimeout(() => $("#compose-textarea").removeClass("flash"), 1500);
return false;
}
return true;
}
export function validate() { export function validate() {
$("#compose-send-button").prop("disabled", true).trigger("blur"); $("#compose-send-button").prop("disabled", true).trigger("blur");
const message_content = compose_state.message_content(); const message_content = compose_state.message_content();
@ -513,10 +538,7 @@ export function validate() {
); );
return false; return false;
} }
if (!warn_for_text_overflow_when_tries_to_send()) {
if (message_content.length > page_params.max_message_length) {
// We don't display an error message, since the red box already
// communicates clearly what you did wrong.
return false; return false;
} }

View File

@ -12,6 +12,7 @@ import * as compose from "./compose";
import * as compose_pm_pill from "./compose_pm_pill"; import * as compose_pm_pill from "./compose_pm_pill";
import * as compose_state from "./compose_state"; import * as compose_state from "./compose_state";
import * as compose_ui from "./compose_ui"; import * as compose_ui from "./compose_ui";
import * as compose_validate from "./compose_validate";
import {$t} from "./i18n"; import {$t} from "./i18n";
import * as message_store from "./message_store"; import * as message_store from "./message_store";
import * as muted_users from "./muted_users"; import * as muted_users from "./muted_users";
@ -218,7 +219,10 @@ function handle_keydown(e) {
// Enter // Enter
if (should_enter_send(e)) { if (should_enter_send(e)) {
e.preventDefault(); e.preventDefault();
if (!$("#compose-send-button").prop("disabled")) { if (
compose_validate.warn_for_text_overflow_when_tries_to_send() &&
!$("#compose-send-button").prop("disabled")
) {
$("#compose-send-button").prop("disabled", true); $("#compose-send-button").prop("disabled", true);
compose.finish(); compose.finish();
} }

View File

@ -353,9 +353,22 @@ textarea.new_message_textarea {
resize: vertical !important; resize: vertical !important;
margin-top: 5px; margin-top: 5px;
@keyframes flash {
0% {
box-shadow: none;
}
100% {
box-shadow: 0 0 0 1pt hsl(0, 100%, 50%);
}
}
&.over_limit, &.over_limit,
&.over_limit:focus { &.over_limit:focus {
box-shadow: 0 0 0 1pt hsl(0, 100%, 50%); box-shadow: 0 0 0 1pt hsl(0, 100%, 50%);
&.flash {
animation: flash 0.5s ease-in-out infinite;
}
} }
} }