summaryrefslogtreecommitdiffstats
path: root/webapp
diff options
context:
space:
mode:
authorNick Frazier <nrflaw@gmail.com>2016-12-26 09:25:50 -0500
committerChristopher Speller <crspeller@gmail.com>2016-12-26 09:25:50 -0500
commit0a1b0d051a1a7d83ad01502f8073d35ee5da95cc (patch)
tree24901635fc7bc3bc78f45efd4a92d943ba2efc54 /webapp
parent87d84dfc30d30a24af35411bac7dafb188575749 (diff)
downloadchat-0a1b0d051a1a7d83ad01502f8073d35ee5da95cc.tar.gz
chat-0a1b0d051a1a7d83ad01502f8073d35ee5da95cc.tar.bz2
chat-0a1b0d051a1a7d83ad01502f8073d35ee5da95cc.zip
Add error to RHS reply box for messages > 4000 chars, consistent with create post and edit post errors (#4871)
* functionality * CSS updates * cleanup * moved message length checks to Textbox component * cleanup
Diffstat (limited to 'webapp')
-rw-r--r--webapp/components/create_comment.jsx33
-rw-r--r--webapp/components/create_post.jsx30
-rw-r--r--webapp/components/edit_post_modal.jsx23
-rw-r--r--webapp/components/textbox.jsx34
-rw-r--r--webapp/sass/layout/_sidebar-right.scss18
-rw-r--r--webapp/sass/responsive/_mobile.scss5
-rw-r--r--webapp/sass/responsive/_tablet.scss4
7 files changed, 89 insertions, 58 deletions
diff --git a/webapp/components/create_comment.jsx b/webapp/components/create_comment.jsx
index 8ecda6777..09ec32b6b 100644
--- a/webapp/components/create_comment.jsx
+++ b/webapp/components/create_comment.jsx
@@ -55,6 +55,7 @@ export default class CreateComment extends React.Component {
this.focusTextbox = this.focusTextbox.bind(this);
this.showPostDeletedModal = this.showPostDeletedModal.bind(this);
this.hidePostDeletedModal = this.hidePostDeletedModal.bind(this);
+ this.handlePostError = this.handlePostError.bind(this);
PostStore.clearCommentDraftUploads();
MessageHistoryStore.resetHistoryIndex('comment');
@@ -96,6 +97,10 @@ export default class CreateComment extends React.Component {
}
}
+ handlePostError(postError) {
+ this.setState({postError});
+ }
+
handleSubmit(e) {
e.preventDefault();
@@ -109,16 +114,11 @@ export default class CreateComment extends React.Component {
const message = this.state.message;
- if (message.length > Constants.CHARACTER_LIMIT) {
- this.setState({
- postError: (
- <FormattedMessage
- id='create_comment.commentLength'
- defaultMessage='Comment length must be less than {max} characters.'
- values={{max: Constants.CHARACTER_LIMIT}}
- />
- )
- });
+ if (this.state.postError) {
+ this.setState({errorClass: 'animation--highlight'});
+ setTimeout(() => {
+ this.setState({errorClass: null});
+ }, Constants.ANIMATION_TIMEOUT);
return;
}
@@ -420,7 +420,8 @@ export default class CreateComment extends React.Component {
let postError = null;
if (this.state.postError) {
- postError = <label className='control-label'>{this.state.postError}</label>;
+ const postErrorClass = 'post-error' + (this.state.errorClass ? (' ' + this.state.errorClass) : '');
+ postError = <label className={postErrorClass}>{this.state.postError}</label>;
}
let preview = null;
@@ -434,11 +435,6 @@ export default class CreateComment extends React.Component {
);
}
- let postFooterClassName = 'post-create-footer';
- if (postError) {
- postFooterClassName += ' has-error';
- }
-
let uploadsInProgressText = null;
if (this.state.uploadsInProgress.length > 0) {
uploadsInProgressText = (
@@ -470,6 +466,7 @@ export default class CreateComment extends React.Component {
onChange={this.handleChange}
onKeyPress={this.commentMsgKeyPress}
onKeyDown={this.handleKeyDown}
+ handlePostError={this.handlePostError}
value={this.state.message}
onBlur={this.handleBlur}
createMessage={Utils.localizeMessage('create_comment.addComment', 'Add a comment...')}
@@ -494,7 +491,7 @@ export default class CreateComment extends React.Component {
channelId={this.props.channelId}
parentId={this.props.rootId}
/>
- <div className={postFooterClassName}>
+ <div className='post-create-footer'>
<input
type='button'
className='btn btn-primary comment-btn pull-right'
@@ -502,8 +499,8 @@ export default class CreateComment extends React.Component {
onClick={this.handleSubmit}
/>
{uploadsInProgressText}
- {preview}
{postError}
+ {preview}
{serverError}
</div>
</div>
diff --git a/webapp/components/create_post.jsx b/webapp/components/create_post.jsx
index 5346d05ad..8e75b6070 100644
--- a/webapp/components/create_post.jsx
+++ b/webapp/components/create_post.jsx
@@ -25,7 +25,7 @@ import PreferenceStore from 'stores/preference_store.jsx';
import Constants from 'utils/constants.jsx';
-import {FormattedHTMLMessage, FormattedMessage} from 'react-intl';
+import {FormattedHTMLMessage} from 'react-intl';
import {browserHistory} from 'react-router/es6';
const Preferences = Constants.Preferences;
@@ -61,7 +61,7 @@ export default class CreatePost extends React.Component {
this.showPostDeletedModal = this.showPostDeletedModal.bind(this);
this.hidePostDeletedModal = this.hidePostDeletedModal.bind(this);
this.showShortcuts = this.showShortcuts.bind(this);
- this.checkMessageLength = this.checkMessageLength.bind(this);
+ this.handlePostError = this.handlePostError.bind(this);
PostStore.clearDraftUploads();
@@ -81,6 +81,10 @@ export default class CreatePost extends React.Component {
};
}
+ handlePostError(postError) {
+ this.setState({postError});
+ }
+
handleSubmit(e) {
e.preventDefault();
@@ -218,25 +222,6 @@ export default class CreatePost extends React.Component {
const draft = PostStore.getCurrentDraft();
draft.message = message;
PostStore.storeCurrentDraft(draft);
-
- this.checkMessageLength(message);
- }
-
- checkMessageLength(message) {
- if (message.length > Constants.CHARACTER_LIMIT) {
- const errorMessage = (
- <FormattedMessage
- id='create_post.error_message'
- defaultMessage='Your message is too long. Character count: {length}/{limit}'
- values={{
- length: message.length,
- limit: Constants.CHARACTER_LIMIT
- }}
- />);
- this.setState({postError: errorMessage});
- } else {
- this.setState({postError: null});
- }
}
handleUploadClick() {
@@ -335,8 +320,6 @@ export default class CreatePost extends React.Component {
fullWidthTextBox: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_FULL_SCREEN,
showTutorialTip: tutorialStep === TutorialSteps.POST_POPOVER
});
-
- this.checkMessageLength(this.state.message);
}
componentDidMount() {
@@ -543,6 +526,7 @@ export default class CreatePost extends React.Component {
onChange={this.handleChange}
onKeyPress={this.postMsgKeyPress}
onKeyDown={this.handleKeyDown}
+ handlePostError={this.handlePostError}
value={this.state.message}
onBlur={this.handleBlur}
createMessage={Utils.localizeMessage('create_post.write', 'Write a message...')}
diff --git a/webapp/components/edit_post_modal.jsx b/webapp/components/edit_post_modal.jsx
index 1617d9f65..5f312170f 100644
--- a/webapp/components/edit_post_modal.jsx
+++ b/webapp/components/edit_post_modal.jsx
@@ -38,6 +38,7 @@ export default class EditPostModal extends React.Component {
this.onModalShown = this.onModalShown.bind(this);
this.onModalHide = this.onModalHide.bind(this);
this.onModalKeyDown = this.onModalKeyDown.bind(this);
+ this.handlePostError = this.handlePostError.bind(this);
this.state = {
editText: '',
@@ -52,6 +53,12 @@ export default class EditPostModal extends React.Component {
};
}
+ handlePostError(postError) {
+ if (this.state.postError !== postError) {
+ this.setState({postError});
+ }
+ }
+
handleEdit() {
const updatedPost = {
message: this.state.editText,
@@ -103,21 +110,6 @@ export default class EditPostModal extends React.Component {
this.setState({
editText: message
});
-
- if (message.length > Constants.CHARACTER_LIMIT) {
- const errorMessage = (
- <FormattedMessage
- id='create_post.error_message'
- defaultMessage='Your message is too long. Character count: {length}/{limit}'
- values={{
- length: message.length,
- limit: Constants.CHARACTER_LIMIT
- }}
- />);
- this.setState({postError: errorMessage});
- } else {
- this.setState({postError: ''});
- }
}
handleEditKeyPress(e) {
@@ -262,6 +254,7 @@ export default class EditPostModal extends React.Component {
onChange={this.handleChange}
onKeyPress={this.handleEditKeyPress}
onKeyDown={this.handleKeyDown}
+ handlePostError={this.handlePostError}
value={this.state.editText}
channelId={this.state.channel_id}
createMessage={Utils.localizeMessage('edit_post.editPost', 'Edit the post...')}
diff --git a/webapp/components/textbox.jsx b/webapp/components/textbox.jsx
index b9b000282..1189a51d8 100644
--- a/webapp/components/textbox.jsx
+++ b/webapp/components/textbox.jsx
@@ -32,6 +32,7 @@ export default class Textbox extends React.Component {
this.handleBlur = this.handleBlur.bind(this);
this.handleHeightChange = this.handleHeightChange.bind(this);
this.showPreview = this.showPreview.bind(this);
+ this.handleChange = this.handleChange.bind(this);
this.state = {
connection: ''
@@ -51,6 +52,10 @@ export default class Textbox extends React.Component {
ErrorStore.addChangeListener(this.onRecievedError);
}
+ componentWillMount() {
+ this.checkMessageLength(this.props.value);
+ }
+
componentWillUnmount() {
ErrorStore.removeChangeListener(this.onRecievedError);
}
@@ -65,6 +70,30 @@ export default class Textbox extends React.Component {
}
}
+ handleChange(e) {
+ this.checkMessageLength(e.target.value);
+ this.props.onChange(e);
+ }
+
+ checkMessageLength(message) {
+ if (this.props.handlePostError) {
+ if (message.length > Constants.CHARACTER_LIMIT) {
+ const errorMessage = (
+ <FormattedMessage
+ id='create_post.error_message'
+ defaultMessage='Your message is too long. Character count: {length}/{limit}'
+ values={{
+ length: message.length,
+ limit: Constants.CHARACTER_LIMIT
+ }}
+ />);
+ this.props.handlePostError(errorMessage);
+ } else {
+ this.props.handlePostError(null);
+ }
+ }
+ }
+
handleKeyPress(e) {
this.props.onKeyPress(e);
}
@@ -206,7 +235,7 @@ export default class Textbox extends React.Component {
type='textarea'
spellCheck='true'
placeholder={this.props.createMessage}
- onChange={this.props.onChange}
+ onChange={this.handleChange}
onKeyPress={this.handleKeyPress}
onKeyDown={this.handleKeyDown}
onBlur={this.handleBlur}
@@ -257,5 +286,6 @@ Textbox.propTypes = {
createMessage: React.PropTypes.string.isRequired,
onKeyDown: React.PropTypes.func,
onBlur: React.PropTypes.func,
- supportsCommands: React.PropTypes.bool.isRequired
+ supportsCommands: React.PropTypes.bool.isRequired,
+ handlePostError: React.PropTypes.func
};
diff --git a/webapp/sass/layout/_sidebar-right.scss b/webapp/sass/layout/_sidebar-right.scss
index 915bb2d09..8d5a1d044 100644
--- a/webapp/sass/layout/_sidebar-right.scss
+++ b/webapp/sass/layout/_sidebar-right.scss
@@ -59,6 +59,24 @@
form {
padding: .5em 15px 0;
}
+
+ .post-create-footer {
+ @include clearfix;
+ font-size: 13px;
+ overflow: visible;
+ position: relative;
+ clear: both;
+
+ .post-error {
+ font-weight: normal;
+ margin-bottom: 0;
+ display: inline-block;
+ font-size: .85em;
+ @include opacity(.55);
+ position: absolute;
+ top: -25px;
+ }
+ }
}
.help__format-text {
diff --git a/webapp/sass/responsive/_mobile.scss b/webapp/sass/responsive/_mobile.scss
index 1dcaacc60..16f0d3851 100644
--- a/webapp/sass/responsive/_mobile.scss
+++ b/webapp/sass/responsive/_mobile.scss
@@ -1073,6 +1073,11 @@
margin: .5em 0;
top: 0;
}
+
+ .post-error {
+ top: 0;
+ left: 0;
+ }
}
}
diff --git a/webapp/sass/responsive/_tablet.scss b/webapp/sass/responsive/_tablet.scss
index 4de187846..64b8ab6dd 100644
--- a/webapp/sass/responsive/_tablet.scss
+++ b/webapp/sass/responsive/_tablet.scss
@@ -42,6 +42,10 @@
top: 0;
left: 32px;
position: relative;
+
+ .sidebar--right & {
+ left: 0;
+ }
}
}