Adding option to display channels sanely (#2761)
Этот коммит содержится в:
коммит произвёл
Harrison Healey
родитель
cf1f3ba322
Коммит
899ee09224
@@ -83,6 +83,7 @@ class CreatePost extends React.Component {
|
|||||||
submitting: false,
|
submitting: false,
|
||||||
initialText: draft.messageText,
|
initialText: draft.messageText,
|
||||||
ctrlSend: false,
|
ctrlSend: false,
|
||||||
|
centerTextbox: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED,
|
||||||
showTutorialTip: false,
|
showTutorialTip: false,
|
||||||
showPostDeletedModal: false
|
showPostDeletedModal: false
|
||||||
};
|
};
|
||||||
@@ -305,7 +306,8 @@ class CreatePost extends React.Component {
|
|||||||
|
|
||||||
// wait to load these since they may have changed since the component was constructed (particularly in the case of skipping the tutorial)
|
// wait to load these since they may have changed since the component was constructed (particularly in the case of skipping the tutorial)
|
||||||
this.setState({
|
this.setState({
|
||||||
ctrlSend: PreferenceStore.getBool(Constants.Preferences.CATEGORY_ADVANCED_SETTINGS, 'send_on_ctrl_enter'),
|
ctrlSend: PreferenceStore.getBool(Preferences.CATEGORY_ADVANCED_SETTINGS, 'send_on_ctrl_enter'),
|
||||||
|
centerTextbox: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED,
|
||||||
showTutorialTip: tutorialStep === TutorialSteps.POST_POPOVER
|
showTutorialTip: tutorialStep === TutorialSteps.POST_POPOVER
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -336,7 +338,8 @@ class CreatePost extends React.Component {
|
|||||||
const tutorialStep = PreferenceStore.getInt(Preferences.TUTORIAL_STEP, UserStore.getCurrentId(), 999);
|
const tutorialStep = PreferenceStore.getInt(Preferences.TUTORIAL_STEP, UserStore.getCurrentId(), 999);
|
||||||
this.setState({
|
this.setState({
|
||||||
showTutorialTip: tutorialStep === TutorialSteps.POST_POPOVER,
|
showTutorialTip: tutorialStep === TutorialSteps.POST_POPOVER,
|
||||||
ctrlSend: PreferenceStore.getBool(Constants.Preferences.CATEGORY_ADVANCED_SETTINGS, 'send_on_ctrl_enter')
|
ctrlSend: PreferenceStore.getBool(Preferences.CATEGORY_ADVANCED_SETTINGS, 'send_on_ctrl_enter'),
|
||||||
|
centerTextbox: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
getFileCount(channelId) {
|
getFileCount(channelId) {
|
||||||
@@ -441,11 +444,17 @@ class CreatePost extends React.Component {
|
|||||||
tutorialTip = this.createTutorialTip();
|
tutorialTip = this.createTutorialTip();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let centerClass = '';
|
||||||
|
if (this.state.centerTextbox) {
|
||||||
|
centerClass = 'center';
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<form
|
<form
|
||||||
id='create_post'
|
id='create_post'
|
||||||
ref='topDiv'
|
ref='topDiv'
|
||||||
role='form'
|
role='form'
|
||||||
|
className={centerClass}
|
||||||
onSubmit={this.handleSubmit}
|
onSubmit={this.handleSubmit}
|
||||||
>
|
>
|
||||||
<div className='post-create'>
|
<div className='post-create'>
|
||||||
|
|||||||
@@ -99,6 +99,10 @@ export default class Post extends React.Component {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (nextProps.center !== this.props.center) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
if (!Utils.areObjectsEqual(nextProps.user, this.props.user)) {
|
if (!Utils.areObjectsEqual(nextProps.user, this.props.user)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -203,13 +207,18 @@ export default class Post extends React.Component {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let centerClass = '';
|
||||||
|
if (this.props.center) {
|
||||||
|
centerClass = 'center';
|
||||||
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
<div
|
<div
|
||||||
id={'post_' + post.id}
|
id={'post_' + post.id}
|
||||||
className={'post ' + sameUserClass + ' ' + rootUser + ' ' + postType + ' ' + currentUserCss + ' ' + shouldHighlightClass + ' ' + systemMessageClass}
|
className={'post ' + sameUserClass + ' ' + rootUser + ' ' + postType + ' ' + currentUserCss + ' ' + shouldHighlightClass + ' ' + systemMessageClass}
|
||||||
>
|
>
|
||||||
<div className='post__content'>
|
<div className={'post__content ' + centerClass}>
|
||||||
<div className='post__img'>{profilePic}</div>
|
<div className='post__img'>{profilePic}</div>
|
||||||
<div>
|
<div>
|
||||||
<PostHeader
|
<PostHeader
|
||||||
@@ -251,5 +260,6 @@ Post.propTypes = {
|
|||||||
shouldHighlight: React.PropTypes.bool,
|
shouldHighlight: React.PropTypes.bool,
|
||||||
displayNameType: React.PropTypes.string,
|
displayNameType: React.PropTypes.string,
|
||||||
hasProfiles: React.PropTypes.bool,
|
hasProfiles: React.PropTypes.bool,
|
||||||
currentUser: React.PropTypes.object.isRequired
|
currentUser: React.PropTypes.object.isRequired,
|
||||||
|
center: React.PropTypes.bool
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -40,6 +40,7 @@ export default class PostsView extends React.Component {
|
|||||||
|
|
||||||
this.state = {
|
this.state = {
|
||||||
displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false'),
|
displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false'),
|
||||||
|
centerPosts: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED,
|
||||||
isScrolling: false,
|
isScrolling: false,
|
||||||
topPostId: null,
|
topPostId: null,
|
||||||
showUnreadMessageAlert: false
|
showUnreadMessageAlert: false
|
||||||
@@ -61,7 +62,10 @@ export default class PostsView extends React.Component {
|
|||||||
return 5;
|
return 5;
|
||||||
}
|
}
|
||||||
updateState() {
|
updateState() {
|
||||||
this.setState({displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false')});
|
this.setState({
|
||||||
|
displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false'),
|
||||||
|
centerPosts: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED
|
||||||
|
});
|
||||||
}
|
}
|
||||||
isAtBottom() {
|
isAtBottom() {
|
||||||
// consider the view to be at the bottom if it's within this many pixels of the bottom
|
// consider the view to be at the bottom if it's within this many pixels of the bottom
|
||||||
@@ -247,6 +251,7 @@ export default class PostsView extends React.Component {
|
|||||||
displayNameType={this.state.displayNameType}
|
displayNameType={this.state.displayNameType}
|
||||||
user={profile}
|
user={profile}
|
||||||
currentUser={this.props.currentUser}
|
currentUser={this.props.currentUser}
|
||||||
|
center={this.state.centerPosts}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
@@ -373,6 +378,7 @@ export default class PostsView extends React.Component {
|
|||||||
this.updateScrolling();
|
this.updateScrolling();
|
||||||
}
|
}
|
||||||
window.addEventListener('resize', this.handleResize);
|
window.addEventListener('resize', this.handleResize);
|
||||||
|
PreferenceStore.addChangeListener(this.updateState);
|
||||||
$('body').addClass('app__body');
|
$('body').addClass('app__body');
|
||||||
}
|
}
|
||||||
componentWillUnmount() {
|
componentWillUnmount() {
|
||||||
@@ -429,6 +435,9 @@ export default class PostsView extends React.Component {
|
|||||||
if (this.state.isScrolling !== nextState.isScrolling) {
|
if (this.state.isScrolling !== nextState.isScrolling) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
if (this.state.centerPosts !== nextState.centerPosts) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
if (!Utils.areObjectsEqual(this.props.profiles, nextProps.profiles)) {
|
if (!Utils.areObjectsEqual(this.props.profiles, nextProps.profiles)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -22,7 +22,8 @@ function getDisplayStateFromStores() {
|
|||||||
return {
|
return {
|
||||||
militaryTime: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'use_military_time', 'false'),
|
militaryTime: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'use_military_time', 'false'),
|
||||||
nameFormat: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'username'),
|
nameFormat: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'username'),
|
||||||
selectedFont: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'selected_font', Constants.DEFAULT_FONT)
|
selectedFont: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'selected_font', Constants.DEFAULT_FONT),
|
||||||
|
channelDisplayMode: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT)
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -63,8 +64,14 @@ export default class UserSettingsDisplay extends React.Component {
|
|||||||
name: 'selected_font',
|
name: 'selected_font',
|
||||||
value: this.state.selectedFont
|
value: this.state.selectedFont
|
||||||
};
|
};
|
||||||
|
const channelDisplayModePreference = {
|
||||||
|
user_id: userId,
|
||||||
|
category: Preferences.CATEGORY_DISPLAY_SETTINGS,
|
||||||
|
name: Preferences.CHANNEL_DISPLAY_MODE,
|
||||||
|
value: this.state.channelDisplayMode
|
||||||
|
};
|
||||||
|
|
||||||
AsyncClient.savePreferences([timePreference, namePreference, fontPreference],
|
AsyncClient.savePreferences([timePreference, namePreference, fontPreference, channelDisplayModePreference],
|
||||||
() => {
|
() => {
|
||||||
this.updateSection('');
|
this.updateSection('');
|
||||||
},
|
},
|
||||||
@@ -79,6 +86,9 @@ export default class UserSettingsDisplay extends React.Component {
|
|||||||
handleNameRadio(nameFormat) {
|
handleNameRadio(nameFormat) {
|
||||||
this.setState({nameFormat});
|
this.setState({nameFormat});
|
||||||
}
|
}
|
||||||
|
handleChannelDisplayModeRadio(channelDisplayMode) {
|
||||||
|
this.setState({channelDisplayMode});
|
||||||
|
}
|
||||||
handleFont(selectedFont) {
|
handleFont(selectedFont) {
|
||||||
Utils.applyFont(selectedFont);
|
Utils.applyFont(selectedFont);
|
||||||
this.setState({selectedFont});
|
this.setState({selectedFont});
|
||||||
@@ -102,6 +112,7 @@ export default class UserSettingsDisplay extends React.Component {
|
|||||||
const serverError = this.state.serverError || null;
|
const serverError = this.state.serverError || null;
|
||||||
let clockSection;
|
let clockSection;
|
||||||
let nameFormatSection;
|
let nameFormatSection;
|
||||||
|
let channelDisplayModeSection;
|
||||||
let fontSection;
|
let fontSection;
|
||||||
let languagesSection;
|
let languagesSection;
|
||||||
|
|
||||||
@@ -339,6 +350,105 @@ export default class UserSettingsDisplay extends React.Component {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (this.props.activeSection === Preferences.CHANNEL_DISPLAY_MODE) {
|
||||||
|
const channelDisplayMode = [false, false];
|
||||||
|
if (this.state.channelDisplayMode === Preferences.CHANNEL_DISPLAY_MODE_CENTERED) {
|
||||||
|
channelDisplayMode[0] = true;
|
||||||
|
} else {
|
||||||
|
channelDisplayMode[1] = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
const inputs = [
|
||||||
|
<div key='userDisplayNameOptions'>
|
||||||
|
<div className='radio'>
|
||||||
|
<label>
|
||||||
|
<input
|
||||||
|
type='radio'
|
||||||
|
checked={channelDisplayMode[0]}
|
||||||
|
onChange={this.handleChannelDisplayModeRadio.bind(this, Preferences.CHANNEL_DISPLAY_MODE_CENTERED)}
|
||||||
|
/>
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.fixedWidthCentered'
|
||||||
|
defaultMessage='Fixed with, centered'
|
||||||
|
/>
|
||||||
|
</label>
|
||||||
|
<br/>
|
||||||
|
</div>
|
||||||
|
<div className='radio'>
|
||||||
|
<label>
|
||||||
|
<input
|
||||||
|
type='radio'
|
||||||
|
checked={channelDisplayMode[1]}
|
||||||
|
onChange={this.handleChannelDisplayModeRadio.bind(this, Preferences.CHANNEL_DISPLAY_MODE_FULL_SCREEN)}
|
||||||
|
/>
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.fullScreen'
|
||||||
|
defaultMessage='Full screen'
|
||||||
|
/>
|
||||||
|
</label>
|
||||||
|
<br/>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<br/>
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.channeldisplaymode'
|
||||||
|
defaultMessage='How to display channels.'
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
];
|
||||||
|
|
||||||
|
channelDisplayModeSection = (
|
||||||
|
<SettingItemMax
|
||||||
|
title={
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.channelDisplayTitle'
|
||||||
|
defaultMessage='Channel Display Mode'
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
inputs={inputs}
|
||||||
|
submit={this.handleSubmit}
|
||||||
|
server_error={serverError}
|
||||||
|
updateSection={(e) => {
|
||||||
|
this.updateSection('');
|
||||||
|
e.preventDefault();
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
let describe;
|
||||||
|
if (this.state.channelDisplayMode === Preferences.CHANNEL_DISPLAY_MODE_CENTERED) {
|
||||||
|
describe = (
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.fixedWidthCentered'
|
||||||
|
defaultMessage='Fixed with, centered'
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
describe = (
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.fullScreen'
|
||||||
|
defaultMessage='Full screen'
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
channelDisplayModeSection = (
|
||||||
|
<SettingItemMin
|
||||||
|
title={
|
||||||
|
<FormattedMessage
|
||||||
|
id='user.settings.display.channelDisplayTitle'
|
||||||
|
defaultMessage='Channel Display Mode'
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
describe={describe}
|
||||||
|
updateSection={() => {
|
||||||
|
this.props.updateSection(Preferences.CHANNEL_DISPLAY_MODE);
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
if (this.props.activeSection === 'font') {
|
if (this.props.activeSection === 'font') {
|
||||||
const options = [];
|
const options = [];
|
||||||
Object.keys(Constants.FONTS).forEach((fontName, idx) => {
|
Object.keys(Constants.FONTS).forEach((fontName, idx) => {
|
||||||
@@ -491,6 +601,8 @@ export default class UserSettingsDisplay extends React.Component {
|
|||||||
<div className='divider-dark'/>
|
<div className='divider-dark'/>
|
||||||
{nameFormatSection}
|
{nameFormatSection}
|
||||||
<div className='divider-dark'/>
|
<div className='divider-dark'/>
|
||||||
|
{channelDisplayModeSection}
|
||||||
|
<div className='divider-dark'/>
|
||||||
{languagesSection}
|
{languagesSection}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -359,11 +359,14 @@ body.ios {
|
|||||||
.post-create__container {
|
.post-create__container {
|
||||||
form {
|
form {
|
||||||
margin: 0 auto;
|
margin: 0 auto;
|
||||||
max-width: 1028px;
|
padding: .5em 30px 0;
|
||||||
padding: .5em 14px 0;
|
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.center {
|
||||||
|
max-width: 1028px;
|
||||||
|
}
|
||||||
|
|
||||||
.post-create-body {
|
.post-create-body {
|
||||||
padding: 0 0 2px;
|
padding: 0 0 2px;
|
||||||
position: relative;
|
position: relative;
|
||||||
@@ -607,10 +610,10 @@ body.ios {
|
|||||||
.post__content {
|
.post__content {
|
||||||
display: table;
|
display: table;
|
||||||
margin: 0 auto;
|
margin: 0 auto;
|
||||||
max-width: 1000px;
|
|
||||||
position: relative;
|
position: relative;
|
||||||
table-layout: fixed;
|
table-layout: fixed;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
|
padding: 0 15px;
|
||||||
|
|
||||||
> div {
|
> div {
|
||||||
display: table-cell;
|
display: table-cell;
|
||||||
@@ -618,6 +621,10 @@ body.ios {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.center {
|
||||||
|
max-width: 1000px;
|
||||||
|
}
|
||||||
|
|
||||||
.post__header {
|
.post__header {
|
||||||
list-style: none;
|
list-style: none;
|
||||||
margin-bottom: 2px;
|
margin-bottom: 2px;
|
||||||
|
|||||||
@@ -517,7 +517,11 @@ export default {
|
|||||||
DISPLAY_PREFER_NICKNAME: 'nickname_full_name',
|
DISPLAY_PREFER_NICKNAME: 'nickname_full_name',
|
||||||
DISPLAY_PREFER_FULL_NAME: 'full_name',
|
DISPLAY_PREFER_FULL_NAME: 'full_name',
|
||||||
CATEGORY_ADVANCED_SETTINGS: 'advanced_settings',
|
CATEGORY_ADVANCED_SETTINGS: 'advanced_settings',
|
||||||
TUTORIAL_STEP: 'tutorial_step'
|
TUTORIAL_STEP: 'tutorial_step',
|
||||||
|
CHANNEL_DISPLAY_MODE: 'channel_display_mode',
|
||||||
|
CHANNEL_DISPLAY_MODE_CENTERED: 'centered',
|
||||||
|
CHANNEL_DISPLAY_MODE_FULL_SCREEN: 'full',
|
||||||
|
CHANNEL_DISPLAY_MODE_DEFAULT: 'centered'
|
||||||
},
|
},
|
||||||
TutorialSteps: {
|
TutorialSteps: {
|
||||||
INTRO_SCREENS: 0,
|
INTRO_SCREENS: 0,
|
||||||
|
|||||||
Ссылка в новой задаче
Block a user