PLT-3114 Moved preview collapse out of pre-release features (#3206)
* Added user setting to auto collapse image previews * Added slash commands for collapsing/expanding image previews * Added translation strings for collapse setting * Add default props for preview collapse setting
Этот коммит содержится в:
коммит произвёл
Corey Hulen
родитель
629b49a119
Коммит
1e245f19c7
77
api/command_expand_collapse.go
Обычный файл
77
api/command_expand_collapse.go
Обычный файл
@@ -0,0 +1,77 @@
|
||||
// Copyright (c) 2016 Mattermost, Inc. All Rights Reserved.
|
||||
// See License.txt for license information.
|
||||
|
||||
package api
|
||||
|
||||
import (
|
||||
"github.com/mattermost/platform/model"
|
||||
)
|
||||
|
||||
type ExpandProvider struct {
|
||||
}
|
||||
|
||||
type CollapseProvider struct {
|
||||
}
|
||||
|
||||
const (
|
||||
CMD_EXPAND = "expand"
|
||||
CMD_COLLAPSE = "collapse"
|
||||
)
|
||||
|
||||
func init() {
|
||||
RegisterCommandProvider(&ExpandProvider{})
|
||||
RegisterCommandProvider(&CollapseProvider{})
|
||||
}
|
||||
|
||||
func (me *ExpandProvider) GetTrigger() string {
|
||||
return CMD_EXPAND
|
||||
}
|
||||
|
||||
func (me *CollapseProvider) GetTrigger() string {
|
||||
return CMD_COLLAPSE
|
||||
}
|
||||
|
||||
func (me *ExpandProvider) GetCommand(c *Context) *model.Command {
|
||||
return &model.Command{
|
||||
Trigger: CMD_EXPAND,
|
||||
AutoComplete: true,
|
||||
AutoCompleteDesc: c.T("api.command_expand.desc"),
|
||||
DisplayName: c.T("api.command_expand.name"),
|
||||
}
|
||||
}
|
||||
|
||||
func (me *CollapseProvider) GetCommand(c *Context) *model.Command {
|
||||
return &model.Command{
|
||||
Trigger: CMD_COLLAPSE,
|
||||
AutoComplete: true,
|
||||
AutoCompleteDesc: c.T("api.command_collapse.desc"),
|
||||
DisplayName: c.T("api.command_collapse.name"),
|
||||
}
|
||||
}
|
||||
|
||||
func (me *ExpandProvider) DoCommand(c *Context, channelId string, message string) *model.CommandResponse {
|
||||
return setCollapsePreference(c, "false")
|
||||
}
|
||||
|
||||
func (me *CollapseProvider) DoCommand(c *Context, channelId string, message string) *model.CommandResponse {
|
||||
return setCollapsePreference(c, "true")
|
||||
}
|
||||
|
||||
func setCollapsePreference(c *Context, value string) *model.CommandResponse {
|
||||
pref := model.Preference{
|
||||
UserId: c.Session.UserId,
|
||||
Category: model.PREFERENCE_CATEGORY_DISPLAY_SETTINGS,
|
||||
Name: model.PREFERENCE_NAME_COLLAPSE_SETTING,
|
||||
Value: value,
|
||||
}
|
||||
|
||||
if result := <-Srv.Store.Preference().Save(&model.Preferences{pref}); result.Err != nil {
|
||||
return &model.CommandResponse{Text: c.T("api.command_expand_collapse.fail.app_error"), ResponseType: model.COMMAND_RESPONSE_TYPE_EPHEMERAL}
|
||||
}
|
||||
|
||||
socketMessage := model.NewMessage("", "", c.Session.UserId, model.ACTION_PREFERENCE_CHANGED)
|
||||
socketMessage.Add("preference", pref.ToJson())
|
||||
go Publish(socketMessage)
|
||||
|
||||
return &model.CommandResponse{}
|
||||
}
|
||||
47
api/command_expand_collapse_test.go
Обычный файл
47
api/command_expand_collapse_test.go
Обычный файл
@@ -0,0 +1,47 @@
|
||||
// Copyright (c) 2016 Mattermost, Inc. All Rights Reserved.
|
||||
// See License.txt for license information.
|
||||
|
||||
package api
|
||||
|
||||
import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/mattermost/platform/model"
|
||||
)
|
||||
|
||||
func TestExpandCommand(t *testing.T) {
|
||||
th := Setup().InitBasic()
|
||||
Client := th.BasicClient
|
||||
channel := th.BasicChannel
|
||||
|
||||
r1 := Client.Must(Client.Command(channel.Id, "/expand", false)).Data.(*model.CommandResponse)
|
||||
if r1 == nil {
|
||||
t.Fatal("Command failed to execute")
|
||||
}
|
||||
|
||||
time.Sleep(100 * time.Millisecond)
|
||||
|
||||
p1 := Client.Must(Client.GetPreference(model.PREFERENCE_CATEGORY_DISPLAY_SETTINGS, model.PREFERENCE_NAME_COLLAPSE_SETTING)).Data.(*model.Preference)
|
||||
if p1.Value != "false" {
|
||||
t.Fatal("preference not updated correctly")
|
||||
}
|
||||
}
|
||||
|
||||
func TestCollapseCommand(t *testing.T) {
|
||||
th := Setup().InitBasic()
|
||||
Client := th.BasicClient
|
||||
channel := th.BasicChannel
|
||||
|
||||
r1 := Client.Must(Client.Command(channel.Id, "/collapse", false)).Data.(*model.CommandResponse)
|
||||
if r1 == nil {
|
||||
t.Fatal("Command failed to execute")
|
||||
}
|
||||
|
||||
time.Sleep(100 * time.Millisecond)
|
||||
|
||||
p1 := Client.Must(Client.GetPreference(model.PREFERENCE_CATEGORY_DISPLAY_SETTINGS, model.PREFERENCE_NAME_COLLAPSE_SETTING)).Data.(*model.Preference)
|
||||
if p1.Value != "true" {
|
||||
t.Fatal("preference not updated correctly")
|
||||
}
|
||||
}
|
||||
20
i18n/en.json
20
i18n/en.json
@@ -399,6 +399,26 @@
|
||||
"id": "api.command_echo.name",
|
||||
"translation": "echo"
|
||||
},
|
||||
{
|
||||
"id": "api.command_collapse.desc",
|
||||
"translation": "Turn on auto-collapsing of image previews"
|
||||
},
|
||||
{
|
||||
"id": "api.command_collapse.name",
|
||||
"translation": "collapse"
|
||||
},
|
||||
{
|
||||
"id": "api.command_expand.desc",
|
||||
"translation": "Turn off auto-collapsing of image previews"
|
||||
},
|
||||
{
|
||||
"id": "api.command_expand_collapse.fail.app_error",
|
||||
"translation": "An error occured while expanding previews"
|
||||
},
|
||||
{
|
||||
"id": "api.command_expand.name",
|
||||
"translation": "expand"
|
||||
},
|
||||
{
|
||||
"id": "api.command_join.desc",
|
||||
"translation": "Join the open channel"
|
||||
|
||||
@@ -14,6 +14,9 @@ const (
|
||||
PREFERENCE_CATEGORY_TUTORIAL_STEPS = "tutorial_step"
|
||||
PREFERENCE_CATEGORY_ADVANCED_SETTINGS = "advanced_settings"
|
||||
|
||||
PREFERENCE_CATEGORY_DISPLAY_SETTINGS = "display_settings"
|
||||
PREFERENCE_NAME_COLLAPSE_SETTING = "collapse_previews"
|
||||
|
||||
PREFERENCE_CATEGORY_LAST = "last"
|
||||
PREFERENCE_NAME_LAST_CHANNEL = "channel"
|
||||
)
|
||||
|
||||
@@ -72,6 +72,10 @@ export default class Post extends React.Component {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (nextProps.previewCollapsed !== this.props.previewCollapsed) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!Utils.areObjectsEqual(nextProps.user, this.props.user)) {
|
||||
return true;
|
||||
}
|
||||
@@ -190,6 +194,7 @@ export default class Post extends React.Component {
|
||||
parentPost={parentPost}
|
||||
handleCommentClick={this.handleCommentClick}
|
||||
compactDisplay={this.props.compactDisplay}
|
||||
previewCollapsed={this.props.previewCollapsed}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
@@ -213,5 +218,6 @@ Post.propTypes = {
|
||||
currentUser: React.PropTypes.object.isRequired,
|
||||
center: React.PropTypes.bool,
|
||||
compactDisplay: React.PropTypes.bool,
|
||||
previewCollapsed: React.PropTypes.string,
|
||||
commentCount: React.PropTypes.number
|
||||
};
|
||||
|
||||
@@ -25,7 +25,11 @@ export default class PostBody extends React.Component {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (!Utils.areObjectsEqual(nextProps.compactDisplay, this.props.compactDisplay)) {
|
||||
if (nextProps.compactDisplay !== this.props.compactDisplay) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (nextProps.previewCollapsed !== this.props.previewCollapsed) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -172,6 +176,7 @@ export default class PostBody extends React.Component {
|
||||
post={this.props.post}
|
||||
message={messageWrapper}
|
||||
compactDisplay={this.props.compactDisplay}
|
||||
previewCollapsed={this.props.previewCollapsed}
|
||||
/>
|
||||
);
|
||||
}
|
||||
@@ -193,5 +198,6 @@ PostBody.propTypes = {
|
||||
parentPost: React.PropTypes.object,
|
||||
retryPost: React.PropTypes.func.isRequired,
|
||||
handleCommentClick: React.PropTypes.func.isRequired,
|
||||
compactDisplay: React.PropTypes.bool
|
||||
compactDisplay: React.PropTypes.bool,
|
||||
previewCollapsed: React.PropTypes.string
|
||||
};
|
||||
|
||||
@@ -22,10 +22,14 @@ export default class PostBodyAdditionalContent extends React.Component {
|
||||
this.toggleEmbedVisibility = this.toggleEmbedVisibility.bind(this);
|
||||
|
||||
this.state = {
|
||||
embedVisible: true
|
||||
embedVisible: props.previewCollapsed.startsWith('false')
|
||||
};
|
||||
}
|
||||
|
||||
componentWillReceiveProps(nextProps) {
|
||||
this.setState({embedVisible: nextProps.previewCollapsed.startsWith('false')});
|
||||
}
|
||||
|
||||
shouldComponentUpdate(nextProps, nextState) {
|
||||
if (!Utils.areObjectsEqual(nextProps.post, this.props.post)) {
|
||||
return true;
|
||||
@@ -118,25 +122,23 @@ export default class PostBodyAdditionalContent extends React.Component {
|
||||
|
||||
if (generateEmbed) {
|
||||
let messageWithToggle = [];
|
||||
if (Utils.isFeatureEnabled(Constants.PRE_RELEASE_FEATURES.EMBED_TOGGLE)) {
|
||||
// if message has only one line and starts with a link place toggle in this only line
|
||||
// else - place it in new line between message and embed
|
||||
const prependToggle = (/^\s*https?:\/\/.*$/).test(this.props.post.message);
|
||||
messageWithToggle.push(
|
||||
<a
|
||||
className={`post__embed-visibility ${prependToggle ? 'pull-left' : ''}`}
|
||||
data-expanded={this.state.embedVisible}
|
||||
aria-label='Toggle Embed Visibility'
|
||||
onClick={this.toggleEmbedVisibility}
|
||||
/>
|
||||
);
|
||||
if (prependToggle) {
|
||||
messageWithToggle.push(this.props.message);
|
||||
} else {
|
||||
messageWithToggle.unshift(this.props.message);
|
||||
}
|
||||
} else {
|
||||
|
||||
// if message has only one line and starts with a link place toggle in this only line
|
||||
// else - place it in new line between message and embed
|
||||
const prependToggle = (/^\s*https?:\/\/.*$/).test(this.props.post.message);
|
||||
messageWithToggle.push(
|
||||
<a
|
||||
className={`post__embed-visibility ${prependToggle ? 'pull-left' : ''}`}
|
||||
data-expanded={this.state.embedVisible}
|
||||
aria-label='Toggle Embed Visibility'
|
||||
onClick={this.toggleEmbedVisibility}
|
||||
/>
|
||||
);
|
||||
|
||||
if (prependToggle) {
|
||||
messageWithToggle.push(this.props.message);
|
||||
} else {
|
||||
messageWithToggle.unshift(this.props.message);
|
||||
}
|
||||
|
||||
return (
|
||||
@@ -156,8 +158,12 @@ export default class PostBodyAdditionalContent extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
PostBodyAdditionalContent.defaultProps = {
|
||||
previewCollapsed: 'false'
|
||||
};
|
||||
PostBodyAdditionalContent.propTypes = {
|
||||
post: React.PropTypes.object.isRequired,
|
||||
message: React.PropTypes.element.isRequired,
|
||||
compactDisplay: React.PropTypes.bool,
|
||||
message: React.PropTypes.element.isRequired
|
||||
previewCollapsed: React.PropTypes.string
|
||||
};
|
||||
|
||||
@@ -260,6 +260,7 @@ export default class PostList extends React.Component {
|
||||
center={this.props.displayPostsInCenter}
|
||||
commentCount={commentCount}
|
||||
compactDisplay={this.props.compactDisplay}
|
||||
previewCollapsed={this.props.previewsCollapsed}
|
||||
/>
|
||||
);
|
||||
|
||||
@@ -520,5 +521,6 @@ PostList.propTypes = {
|
||||
postsToHighlight: React.PropTypes.object,
|
||||
displayNameType: React.PropTypes.string,
|
||||
displayPostsInCenter: React.PropTypes.bool,
|
||||
compactDisplay: React.PropTypes.bool
|
||||
compactDisplay: React.PropTypes.bool,
|
||||
previewsCollapsed: React.PropTypes.string
|
||||
};
|
||||
|
||||
@@ -51,7 +51,8 @@ export default class PostViewController extends React.Component {
|
||||
scrollType: ScrollTypes.NEW_MESSAGE,
|
||||
displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false'),
|
||||
displayPostsInCenter: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED,
|
||||
compactDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT) === Preferences.MESSAGE_DISPLAY_COMPACT
|
||||
compactDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT) === Preferences.MESSAGE_DISPLAY_COMPACT,
|
||||
previewsCollapsed: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.COLLAPSE_DISPLAY, 'false')
|
||||
};
|
||||
}
|
||||
|
||||
@@ -67,11 +68,19 @@ export default class PostViewController extends React.Component {
|
||||
}
|
||||
}
|
||||
|
||||
onPreferenceChange() {
|
||||
onPreferenceChange(category) {
|
||||
// Bit of a hack to force render when this setting is updated
|
||||
// regardless of change
|
||||
let previewSuffix = '';
|
||||
if (category === Preferences.CATEGORY_DISPLAY_SETTINGS) {
|
||||
previewSuffix = '_' + Utils.generateId();
|
||||
}
|
||||
|
||||
this.setState({
|
||||
displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false'),
|
||||
displayPostsInCenter: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED,
|
||||
compactDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT) === Preferences.MESSAGE_DISPLAY_COMPACT
|
||||
compactDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT) === Preferences.MESSAGE_DISPLAY_COMPACT,
|
||||
previewsCollapsed: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.COLLAPSE_DISPLAY, 'false') + previewSuffix
|
||||
});
|
||||
}
|
||||
|
||||
@@ -132,6 +141,7 @@ export default class PostViewController extends React.Component {
|
||||
displayNameType: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'false'),
|
||||
displayPostsInCenter: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.CHANNEL_DISPLAY_MODE, Preferences.CHANNEL_DISPLAY_MODE_DEFAULT) === Preferences.CHANNEL_DISPLAY_MODE_CENTERED,
|
||||
compactDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT) === Preferences.MESSAGE_DISPLAY_COMPACT,
|
||||
previewsCollapsed: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.COLLAPSE_DISPLAY, 'false'),
|
||||
scrollType: ScrollTypes.NEW_MESSAGE
|
||||
});
|
||||
}
|
||||
@@ -183,6 +193,10 @@ export default class PostViewController extends React.Component {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (nextState.previewsCollapsed !== this.state.previewsCollapsed) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (nextState.lastViewed !== this.state.lastViewed) {
|
||||
return true;
|
||||
}
|
||||
@@ -241,6 +255,7 @@ export default class PostViewController extends React.Component {
|
||||
displayNameType={this.state.displayNameType}
|
||||
displayPostsInCenter={this.state.displayPostsInCenter}
|
||||
compactDisplay={this.state.compactDisplay}
|
||||
previewsCollapsed={this.state.previewsCollapsed}
|
||||
lastViewed={this.state.lastViewed}
|
||||
/>
|
||||
);
|
||||
|
||||
@@ -234,13 +234,6 @@ export default class AdvancedSettingsDisplay extends React.Component {
|
||||
defaultMessage='Show preview snippet of links below message'
|
||||
/>
|
||||
);
|
||||
case 'EMBED_TOGGLE':
|
||||
return (
|
||||
<FormattedMessage
|
||||
id='user.settings.advance.embed_toggle'
|
||||
defaultMessage='Show toggle for all embed previews'
|
||||
/>
|
||||
);
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
|
||||
@@ -24,7 +24,8 @@ function getDisplayStateFromStores() {
|
||||
nameFormat: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, 'name_format', 'username'),
|
||||
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),
|
||||
messageDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT)
|
||||
messageDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.MESSAGE_DISPLAY, Preferences.MESSAGE_DISPLAY_DEFAULT),
|
||||
collapseDisplay: PreferenceStore.get(Preferences.CATEGORY_DISPLAY_SETTINGS, Preferences.COLLAPSE_DISPLAY, Preferences.COLLAPSE_DISPLAY_DEFAULT)
|
||||
};
|
||||
}
|
||||
|
||||
@@ -41,9 +42,11 @@ export default class UserSettingsDisplay extends React.Component {
|
||||
this.updateSection = this.updateSection.bind(this);
|
||||
this.updateState = this.updateState.bind(this);
|
||||
this.deactivate = this.deactivate.bind(this);
|
||||
this.createCollapseSection = this.createCollapseSection.bind(this);
|
||||
|
||||
this.state = getDisplayStateFromStores();
|
||||
}
|
||||
|
||||
handleSubmit() {
|
||||
const userId = UserStore.getCurrentId();
|
||||
|
||||
@@ -77,8 +80,14 @@ export default class UserSettingsDisplay extends React.Component {
|
||||
name: Preferences.MESSAGE_DISPLAY,
|
||||
value: this.state.messageDisplay
|
||||
};
|
||||
const collapseDisplayPreference = {
|
||||
user_id: userId,
|
||||
category: Preferences.CATEGORY_DISPLAY_SETTINGS,
|
||||
name: Preferences.COLLAPSE_DISPLAY,
|
||||
value: this.state.collapseDisplay
|
||||
};
|
||||
|
||||
AsyncClient.savePreferences([timePreference, namePreference, fontPreference, channelDisplayModePreference, messageDisplayPreference],
|
||||
AsyncClient.savePreferences([timePreference, namePreference, fontPreference, channelDisplayModePreference, messageDisplayPreference, collapseDisplayPreference],
|
||||
() => {
|
||||
this.updateSection('');
|
||||
},
|
||||
@@ -87,27 +96,38 @@ export default class UserSettingsDisplay extends React.Component {
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
handleClockRadio(militaryTime) {
|
||||
this.setState({militaryTime});
|
||||
}
|
||||
|
||||
handleNameRadio(nameFormat) {
|
||||
this.setState({nameFormat});
|
||||
}
|
||||
|
||||
handleChannelDisplayModeRadio(channelDisplayMode) {
|
||||
this.setState({channelDisplayMode});
|
||||
}
|
||||
|
||||
handlemessageDisplayRadio(messageDisplay) {
|
||||
this.setState({messageDisplay});
|
||||
}
|
||||
|
||||
handleFont(selectedFont) {
|
||||
Utils.applyFont(selectedFont);
|
||||
this.setState({selectedFont});
|
||||
}
|
||||
|
||||
handleCollapseRadio(collapseDisplay) {
|
||||
this.setState({collapseDisplay});
|
||||
}
|
||||
|
||||
updateSection(section) {
|
||||
$('.settings-modal .modal-body').scrollTop(0).perfectScrollbar('update');
|
||||
this.updateState();
|
||||
this.props.updateSection(section);
|
||||
}
|
||||
|
||||
updateState() {
|
||||
const newState = getDisplayStateFromStores();
|
||||
if (!Utils.areObjectsEqual(newState, this.state)) {
|
||||
@@ -115,9 +135,118 @@ export default class UserSettingsDisplay extends React.Component {
|
||||
this.setState(newState);
|
||||
}
|
||||
}
|
||||
|
||||
deactivate() {
|
||||
this.updateState();
|
||||
}
|
||||
|
||||
createCollapseSection() {
|
||||
if (this.props.activeSection === 'collapse') {
|
||||
const collapseFormat = [false, false];
|
||||
if (this.state.collapseDisplay === 'true') {
|
||||
collapseFormat[0] = true;
|
||||
} else {
|
||||
collapseFormat[1] = true;
|
||||
}
|
||||
|
||||
const handleUpdateCollapseSection = (e) => {
|
||||
this.updateSection('');
|
||||
e.preventDefault();
|
||||
};
|
||||
|
||||
const inputs = [
|
||||
<div key='userDisplayCollapseOptions'>
|
||||
<div className='radio'>
|
||||
<label>
|
||||
<input
|
||||
type='radio'
|
||||
name='collapseFormat'
|
||||
checked={collapseFormat[0]}
|
||||
onChange={this.handleCollapseRadio.bind(this, 'true')}
|
||||
/>
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseOn'
|
||||
defaultMessage='On'
|
||||
/>
|
||||
</label>
|
||||
<br/>
|
||||
</div>
|
||||
<div className='radio'>
|
||||
<label>
|
||||
<input
|
||||
type='radio'
|
||||
name='collapseFormat'
|
||||
checked={collapseFormat[1]}
|
||||
onChange={this.handleCollapseRadio.bind(this, 'false')}
|
||||
/>
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseOff'
|
||||
defaultMessage='Off'
|
||||
/>
|
||||
</label>
|
||||
<br/>
|
||||
</div>
|
||||
<div>
|
||||
<br/>
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseDesc'
|
||||
defaultMessage='Toggle whether to automatically collapse all image previews.'
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
];
|
||||
|
||||
return (
|
||||
<SettingItemMax
|
||||
title={
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseDisplay'
|
||||
defaultMessage='Auto Collapse Previews'
|
||||
/>
|
||||
}
|
||||
inputs={inputs}
|
||||
submit={this.handleSubmit}
|
||||
server_error={this.state.serverError}
|
||||
updateSection={handleUpdateCollapseSection}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
let describe;
|
||||
if (this.state.collapseDisplay === 'true') {
|
||||
describe = (
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseOn'
|
||||
defaultMessage='On'
|
||||
/>
|
||||
);
|
||||
} else {
|
||||
describe = (
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseOff'
|
||||
defaultMessage='Off'
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
const handleUpdateCollapseSection = () => {
|
||||
this.props.updateSection('collapse');
|
||||
};
|
||||
|
||||
return (
|
||||
<SettingItemMin
|
||||
title={
|
||||
<FormattedMessage
|
||||
id='user.settings.display.collapseDisplay'
|
||||
defaultMessage='Auto Collapse Previews'
|
||||
/>
|
||||
}
|
||||
describe={describe}
|
||||
updateSection={handleUpdateCollapseSection}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
render() {
|
||||
const serverError = this.state.serverError || null;
|
||||
let clockSection;
|
||||
@@ -127,6 +256,8 @@ export default class UserSettingsDisplay extends React.Component {
|
||||
let languagesSection;
|
||||
let messageDisplaySection;
|
||||
|
||||
const collapseSection = this.createCollapseSection();
|
||||
|
||||
if (this.props.activeSection === 'clock') {
|
||||
const clockFormat = [false, false];
|
||||
if (this.state.militaryTime === 'true') {
|
||||
@@ -729,6 +860,8 @@ export default class UserSettingsDisplay extends React.Component {
|
||||
<div className='divider-dark'/>
|
||||
{nameFormatSection}
|
||||
<div className='divider-dark'/>
|
||||
{collapseSection}
|
||||
<div className='divider-dark'/>
|
||||
{messageDisplaySection}
|
||||
<div className='divider-dark'/>
|
||||
{channelDisplayModeSection}
|
||||
|
||||
@@ -1290,6 +1290,10 @@
|
||||
"user.settings.developer.register": "Register New Application",
|
||||
"user.settings.developer.thirdParty": "Open to register a new third-party application",
|
||||
"user.settings.developer.title": "Developer Settings",
|
||||
"user.settings.display.collapseOn": "On",
|
||||
"user.settings.display.collapseOff": "Off",
|
||||
"user.settings.display.collapseDesc": "Toggle whether to automatically collapse all image previews.",
|
||||
"user.settings.display.collapseDisplay": "Auto Collapse Previews",
|
||||
"user.settings.display.channelDisplayTitle": "Channel Display Mode",
|
||||
"user.settings.display.channeldisplaymode": "Select the width of the center channel.",
|
||||
"user.settings.display.clockDisplay": "Clock Display",
|
||||
|
||||
@@ -82,8 +82,8 @@ class PreferenceStoreClass extends EventEmitter {
|
||||
this.preferences.clear();
|
||||
}
|
||||
|
||||
emitChange() {
|
||||
this.emit(CHANGE_EVENT);
|
||||
emitChange(category) {
|
||||
this.emit(CHANGE_EVENT, category);
|
||||
}
|
||||
|
||||
addChangeListener(callback) {
|
||||
@@ -101,7 +101,7 @@ class PreferenceStoreClass extends EventEmitter {
|
||||
case ActionTypes.RECEIVED_PREFERENCE: {
|
||||
const preference = action.preference;
|
||||
this.setPreference(preference.category, preference.name, preference.value);
|
||||
this.emitChange();
|
||||
this.emitChange(preference.category);
|
||||
break;
|
||||
}
|
||||
case ActionTypes.RECEIVED_PREFERENCES:
|
||||
|
||||
@@ -547,7 +547,9 @@ export default {
|
||||
MESSAGE_DISPLAY: 'message_display',
|
||||
MESSAGE_DISPLAY_CLEAN: 'clean',
|
||||
MESSAGE_DISPLAY_COMPACT: 'compact',
|
||||
MESSAGE_DISPLAY_DEFAULT: 'clean'
|
||||
MESSAGE_DISPLAY_DEFAULT: 'clean',
|
||||
COLLAPSE_DISPLAY: 'collapse_previews',
|
||||
COLLAPSE_DISPLAY_DEFAULT: 'false'
|
||||
},
|
||||
TutorialSteps: {
|
||||
INTRO_SCREENS: 0,
|
||||
@@ -728,10 +730,6 @@ export default {
|
||||
EMBED_PREVIEW: {
|
||||
label: 'embed_preview',
|
||||
description: 'Show preview snippet of links below message'
|
||||
},
|
||||
EMBED_TOGGLE: {
|
||||
label: 'embed_toggle',
|
||||
description: 'Show toggle for all embed previews'
|
||||
}
|
||||
},
|
||||
OVERLAY_TIME_DELAY: 400,
|
||||
|
||||
Ссылка в новой задаче
Block a user