Merge pull request #2071 from hmhealey/plt1820

PLT-1820/PLT-1847 Cleaned up textbox focus code
Этот коммит содержится в:
Corey Hulen
2016-02-04 15:36:28 -08:00
родитель af6ade3380 c4344f8c02
Коммит 392b878a10
4 изменённых файлов: 36 добавлений и 41 удалений

Просмотреть файл

@@ -51,6 +51,7 @@ class CreateComment extends React.Component {
this.commentMsgKeyPress = this.commentMsgKeyPress.bind(this); this.commentMsgKeyPress = this.commentMsgKeyPress.bind(this);
this.handleUserInput = this.handleUserInput.bind(this); this.handleUserInput = this.handleUserInput.bind(this);
this.handleKeyDown = this.handleKeyDown.bind(this); this.handleKeyDown = this.handleKeyDown.bind(this);
this.handleUploadClick = this.handleUploadClick.bind(this);
this.handleUploadStart = this.handleUploadStart.bind(this); this.handleUploadStart = this.handleUploadStart.bind(this);
this.handleFileUploadComplete = this.handleFileUploadComplete.bind(this); this.handleFileUploadComplete = this.handleFileUploadComplete.bind(this);
this.handleUploadError = this.handleUploadError.bind(this); this.handleUploadError = this.handleUploadError.bind(this);
@@ -74,6 +75,8 @@ class CreateComment extends React.Component {
componentDidMount() { componentDidMount() {
PreferenceStore.addChangeListener(this.onPreferenceChange); PreferenceStore.addChangeListener(this.onPreferenceChange);
window.addEventListener('resize', this.handleResize); window.addEventListener('resize', this.handleResize);
this.refs.textbox.focus();
} }
componentWillUnmount() { componentWillUnmount() {
PreferenceStore.removeChangeListener(this.onPreferenceChange); PreferenceStore.removeChangeListener(this.onPreferenceChange);
@@ -94,6 +97,10 @@ class CreateComment extends React.Component {
$('.post-right__scroll').perfectScrollbar('update'); $('.post-right__scroll').perfectScrollbar('update');
} }
} }
if (prevProps.rootId !== this.props.rootId) {
this.refs.textbox.focus();
}
} }
handleSubmit(e) { handleSubmit(e) {
e.preventDefault(); e.preventDefault();
@@ -218,6 +225,9 @@ class CreateComment extends React.Component {
}); });
} }
} }
handleUploadClick() {
this.refs.textbox.focus();
}
handleUploadStart(clientIds) { handleUploadStart(clientIds) {
let draft = PostStore.getCommentDraft(this.props.rootId); let draft = PostStore.getCommentDraft(this.props.rootId);
@@ -225,6 +235,10 @@ class CreateComment extends React.Component {
PostStore.storeCommentDraft(this.props.rootId, draft); PostStore.storeCommentDraft(this.props.rootId, draft);
this.setState({uploadsInProgress: draft.uploadsInProgress}); this.setState({uploadsInProgress: draft.uploadsInProgress});
// this is a bit redundant with the code that sets focus when the file input is clicked,
// but this also resets the focus after a drag and drop
this.refs.textbox.focus();
} }
handleFileUploadComplete(filenames, clientIds) { handleFileUploadComplete(filenames, clientIds) {
let draft = PostStore.getCommentDraft(this.props.rootId); let draft = PostStore.getCommentDraft(this.props.rootId);
@@ -365,6 +379,7 @@ class CreateComment extends React.Component {
<FileUpload <FileUpload
ref='fileUpload' ref='fileUpload'
getFileCount={this.getFileCount} getFileCount={this.getFileCount}
onClick={this.handleUploadClick}
onUploadStart={this.handleUploadStart} onUploadStart={this.handleUploadStart}
onFileUpload={this.handleFileUploadComplete} onFileUpload={this.handleFileUploadComplete}
onUploadError={this.handleUploadError} onUploadError={this.handleUploadError}

Просмотреть файл

@@ -53,7 +53,7 @@ class CreatePost extends React.Component {
this.handleSubmit = this.handleSubmit.bind(this); this.handleSubmit = this.handleSubmit.bind(this);
this.postMsgKeyPress = this.postMsgKeyPress.bind(this); this.postMsgKeyPress = this.postMsgKeyPress.bind(this);
this.handleUserInput = this.handleUserInput.bind(this); this.handleUserInput = this.handleUserInput.bind(this);
this.resizePostHolder = this.resizePostHolder.bind(this); this.handleUploadClick = this.handleUploadClick.bind(this);
this.handleUploadStart = this.handleUploadStart.bind(this); this.handleUploadStart = this.handleUploadStart.bind(this);
this.handleFileUploadComplete = this.handleFileUploadComplete.bind(this); this.handleFileUploadComplete = this.handleFileUploadComplete.bind(this);
this.handleUploadError = this.handleUploadError.bind(this); this.handleUploadError = this.handleUploadError.bind(this);
@@ -62,7 +62,6 @@ class CreatePost extends React.Component {
this.onPreferenceChange = this.onPreferenceChange.bind(this); this.onPreferenceChange = this.onPreferenceChange.bind(this);
this.getFileCount = this.getFileCount.bind(this); this.getFileCount = this.getFileCount.bind(this);
this.handleKeyDown = this.handleKeyDown.bind(this); this.handleKeyDown = this.handleKeyDown.bind(this);
this.handleResize = this.handleResize.bind(this);
this.sendMessage = this.sendMessage.bind(this); this.sendMessage = this.sendMessage.bind(this);
PostStore.clearDraftUploads(); PostStore.clearDraftUploads();
@@ -76,34 +75,10 @@ class CreatePost extends React.Component {
previews: draft.previews, previews: draft.previews,
submitting: false, submitting: false,
initialText: draft.messageText, initialText: draft.messageText,
windowWidth: Utils.windowWidth(),
windowHeight: Utils.windowHeight(),
ctrlSend: false, ctrlSend: false,
showTutorialTip: false showTutorialTip: false
}; };
} }
handleResize() {
this.setState({
windowWidth: Utils.windowWidth(),
windowHeight: Utils.windowHeight()
});
}
componentDidUpdate(prevProps, prevState) {
if (prevState.previews.length !== this.state.previews.length) {
this.resizePostHolder();
return;
}
if (prevState.uploadsInProgress !== this.state.uploadsInProgress) {
this.resizePostHolder();
return;
}
if (prevState.windowWidth !== this.state.windowWidth || prevState.windowHeight !== this.state.windowHeight) {
this.resizePostHolder();
return;
}
}
getCurrentDraft() { getCurrentDraft() {
const draft = PostStore.getCurrentDraft(); const draft = PostStore.getCurrentDraft();
const safeDraft = {previews: [], messageText: '', uploadsInProgress: []}; const safeDraft = {previews: [], messageText: '', uploadsInProgress: []};
@@ -240,10 +215,8 @@ class CreatePost extends React.Component {
draft.message = messageText; draft.message = messageText;
PostStore.storeCurrentDraft(draft); PostStore.storeCurrentDraft(draft);
} }
resizePostHolder() { handleUploadClick() {
if (this.state.windowWidth > 960) { this.refs.textbox.focus();
$('#post_textbox').focus();
}
} }
handleUploadStart(clientIds, channelId) { handleUploadStart(clientIds, channelId) {
const draft = PostStore.getDraft(channelId); const draft = PostStore.getDraft(channelId);
@@ -252,6 +225,10 @@ class CreatePost extends React.Component {
PostStore.storeDraft(channelId, draft); PostStore.storeDraft(channelId, draft);
this.setState({uploadsInProgress: draft.uploadsInProgress}); this.setState({uploadsInProgress: draft.uploadsInProgress});
// this is a bit redundant with the code that sets focus when the file input is clicked,
// but this also resets the focus after a drag and drop
this.refs.textbox.focus();
} }
handleFileUploadComplete(filenames, clientIds, channelId) { handleFileUploadComplete(filenames, clientIds, channelId) {
const draft = PostStore.getDraft(channelId); const draft = PostStore.getDraft(channelId);
@@ -328,13 +305,16 @@ class CreatePost extends React.Component {
componentDidMount() { componentDidMount() {
ChannelStore.addChangeListener(this.onChange); ChannelStore.addChangeListener(this.onChange);
PreferenceStore.addChangeListener(this.onPreferenceChange); PreferenceStore.addChangeListener(this.onPreferenceChange);
this.resizePostHolder(); this.refs.textbox.focus();
window.addEventListener('resize', this.handleResize); }
componentDidUpdate(prevProps, prevState) {
if (prevState.channelId !== this.state.channelId) {
this.refs.textbox.focus();
}
} }
componentWillUnmount() { componentWillUnmount() {
ChannelStore.removeChangeListener(this.onChange); ChannelStore.removeChangeListener(this.onChange);
PreferenceStore.removeChangeListener(this.onPreferenceChange); PreferenceStore.removeChangeListener(this.onPreferenceChange);
window.removeEventListener('resize', this.handleResize);
} }
onChange() { onChange() {
const channelId = ChannelStore.getCurrentId(); const channelId = ChannelStore.getCurrentId();
@@ -457,7 +437,6 @@ class CreatePost extends React.Component {
onUserInput={this.handleUserInput} onUserInput={this.handleUserInput}
onKeyPress={this.postMsgKeyPress} onKeyPress={this.postMsgKeyPress}
onKeyDown={this.handleKeyDown} onKeyDown={this.handleKeyDown}
onHeightChange={this.resizePostHolder}
messageText={this.state.messageText} messageText={this.state.messageText}
createMessage={this.props.intl.formatMessage(holders.write)} createMessage={this.props.intl.formatMessage(holders.write)}
channelId={this.state.channelId} channelId={this.state.channelId}
@@ -467,6 +446,7 @@ class CreatePost extends React.Component {
<FileUpload <FileUpload
ref='fileUpload' ref='fileUpload'
getFileCount={this.getFileCount} getFileCount={this.getFileCount}
onClick={this.handleUploadClick}
onUploadStart={this.handleUploadStart} onUploadStart={this.handleUploadStart}
onFileUpload={this.handleFileUploadComplete} onFileUpload={this.handleFileUploadComplete}
onUploadError={this.handleUploadError} onUploadError={this.handleUploadError}

Просмотреть файл

@@ -310,6 +310,7 @@ class FileUpload extends React.Component {
ref='fileInput' ref='fileInput'
type='file' type='file'
onChange={this.handleChange} onChange={this.handleChange}
onClick={this.props.onClick}
multiple={multiple} multiple={multiple}
accept={accept} accept={accept}
/> />
@@ -322,6 +323,7 @@ FileUpload.propTypes = {
intl: intlShape.isRequired, intl: intlShape.isRequired,
onUploadError: React.PropTypes.func, onUploadError: React.PropTypes.func,
getFileCount: React.PropTypes.func, getFileCount: React.PropTypes.func,
onClick: React.PropTypes.func,
onFileUpload: React.PropTypes.func, onFileUpload: React.PropTypes.func,
onUploadStart: React.PropTypes.func, onUploadStart: React.PropTypes.func,
onTextDrop: React.PropTypes.func, onTextDrop: React.PropTypes.func,

Просмотреть файл

@@ -20,6 +20,7 @@ export default class Textbox extends React.Component {
constructor(props) { constructor(props) {
super(props); super(props);
this.focus = this.focus.bind(this);
this.getStateFromStores = this.getStateFromStores.bind(this); this.getStateFromStores = this.getStateFromStores.bind(this);
this.onRecievedError = this.onRecievedError.bind(this); this.onRecievedError = this.onRecievedError.bind(this);
this.handleKeyPress = this.handleKeyPress.bind(this); this.handleKeyPress = this.handleKeyPress.bind(this);
@@ -81,6 +82,10 @@ export default class Textbox extends React.Component {
} }
} }
focus() {
this.refs.message.getTextbox().focus();
}
resize() { resize() {
const textbox = this.refs.message.getTextbox(); const textbox = this.refs.message.getTextbox();
const $textbox = $(textbox); const $textbox = $(textbox);
@@ -90,8 +95,6 @@ export default class Textbox extends React.Component {
const borders = parseInt($textbox.css('border-bottom-width'), 10) + parseInt($textbox.css('border-top-width'), 10); const borders = parseInt($textbox.css('border-bottom-width'), 10) + parseInt($textbox.css('border-top-width'), 10);
const maxHeight = parseInt($textbox.css('max-height'), 10) - borders; const maxHeight = parseInt($textbox.css('max-height'), 10) - borders;
const prevHeight = $textbox.height();
// set the height to auto and remove the scrollbar so we can get the actual size of the contents // set the height to auto and remove the scrollbar so we can get the actual size of the contents
$textbox.css('height', 'auto').css('overflow-y', 'hidden'); $textbox.css('height', 'auto').css('overflow-y', 'hidden');
@@ -116,10 +119,6 @@ export default class Textbox extends React.Component {
if (this.state.preview) { if (this.state.preview) {
$(ReactDOM.findDOMNode(this.refs.preview)).height(height + borders); $(ReactDOM.findDOMNode(this.refs.preview)).height(height + borders);
} }
if (height !== prevHeight && this.props.onHeightChange) {
this.props.onHeightChange();
}
} }
showPreview(e) { showPreview(e) {
@@ -211,7 +210,6 @@ Textbox.propTypes = {
messageText: React.PropTypes.string.isRequired, messageText: React.PropTypes.string.isRequired,
onUserInput: React.PropTypes.func.isRequired, onUserInput: React.PropTypes.func.isRequired,
onKeyPress: React.PropTypes.func.isRequired, onKeyPress: React.PropTypes.func.isRequired,
onHeightChange: React.PropTypes.func,
createMessage: React.PropTypes.string.isRequired, createMessage: React.PropTypes.string.isRequired,
onKeyDown: React.PropTypes.func, onKeyDown: React.PropTypes.func,
supportsCommands: React.PropTypes.bool.isRequired supportsCommands: React.PropTypes.bool.isRequired