Convert channel_members and channel_invite modals to react boostrap to fix performance issues

Этот коммит содержится в:
JoramWilander
2015-11-04 12:17:12 -05:00
родитель ebce34190a
Коммит 22b4e5c4c0
7 изменённых файлов: 325 добавлений и 343 удалений

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

@@ -1,20 +1,23 @@
// Copyright (c) 2015 Mattermost, Inc. All Rights Reserved. // Copyright (c) 2015 Mattermost, Inc. All Rights Reserved.
// See License.txt for license information. // See License.txt for license information.
const NavbarSearchBox = require('./search_bar.jsx');
const MessageWrapper = require('./message_wrapper.jsx');
const PopoverListMembers = require('./popover_list_members.jsx');
const EditChannelPurposeModal = require('./edit_channel_purpose_modal.jsx');
const ChannelInviteModal = require('./channel_invite_modal.jsx');
const ChannelMembersModal = require('./channel_members_modal.jsx');
const ChannelStore = require('../stores/channel_store.jsx'); const ChannelStore = require('../stores/channel_store.jsx');
const UserStore = require('../stores/user_store.jsx'); const UserStore = require('../stores/user_store.jsx');
const SearchStore = require('../stores/search_store.jsx'); const SearchStore = require('../stores/search_store.jsx');
const PreferenceStore = require('../stores/preference_store.jsx'); const PreferenceStore = require('../stores/preference_store.jsx');
const NavbarSearchBox = require('./search_bar.jsx');
const AsyncClient = require('../utils/async_client.jsx');
const Client = require('../utils/client.jsx');
const TextFormatting = require('../utils/text_formatting.jsx');
const Utils = require('../utils/utils.jsx');
const MessageWrapper = require('./message_wrapper.jsx');
const PopoverListMembers = require('./popover_list_members.jsx');
const EditChannelPurposeModal = require('./edit_channel_purpose_modal.jsx');
const AppDispatcher = require('../dispatcher/app_dispatcher.jsx'); const AppDispatcher = require('../dispatcher/app_dispatcher.jsx');
const Utils = require('../utils/utils.jsx');
const TextFormatting = require('../utils/text_formatting.jsx');
const AsyncClient = require('../utils/async_client.jsx');
const Client = require('../utils/client.jsx');
const Constants = require('../utils/constants.jsx'); const Constants = require('../utils/constants.jsx');
const ActionTypes = Constants.ActionTypes; const ActionTypes = Constants.ActionTypes;
@@ -31,6 +34,8 @@ export default class ChannelHeader extends React.Component {
const state = this.getStateFromStores(); const state = this.getStateFromStores();
state.showEditChannelPurposeModal = false; state.showEditChannelPurposeModal = false;
state.showInviteModal = false;
state.showMembersModal = false;
this.state = state; this.state = state;
} }
getStateFromStores() { getStateFromStores() {
@@ -86,7 +91,7 @@ export default class ChannelHeader extends React.Component {
let terms = ''; let terms = '';
if (user.notify_props && user.notify_props.mention_keys) { if (user.notify_props && user.notify_props.mention_keys) {
let termKeys = UserStore.getCurrentMentionKeys(); const termKeys = UserStore.getCurrentMentionKeys();
if (user.notify_props.all === 'true' && termKeys.indexOf('@all') !== -1) { if (user.notify_props.all === 'true' && termKeys.indexOf('@all') !== -1) {
termKeys.splice(termKeys.indexOf('@all'), 1); termKeys.splice(termKeys.indexOf('@all'), 1);
} }
@@ -146,7 +151,7 @@ export default class ChannelHeader extends React.Component {
channelTerm = 'Group'; channelTerm = 'Group';
} }
let dropdownContents = []; const dropdownContents = [];
if (isDirect) { if (isDirect) {
dropdownContents.push( dropdownContents.push(
<li <li
@@ -162,7 +167,7 @@ export default class ChannelHeader extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Set Channel Header... {'Set Channel Header...'}
</a> </a>
</li> </li>
); );
@@ -179,7 +184,7 @@ export default class ChannelHeader extends React.Component {
data-channelid={channel.id} data-channelid={channel.id}
href='#' href='#'
> >
View Info {'View Info'}
</a> </a>
</li> </li>
); );
@@ -192,11 +197,10 @@ export default class ChannelHeader extends React.Component {
> >
<a <a
role='menuitem' role='menuitem'
data-toggle='modal'
data-target='#channel_invite'
href='#' href='#'
onClick={() => this.setState({showInviteModal: true})}
> >
Add Members {'Add Members'}
</a> </a>
</li> </li>
); );
@@ -209,11 +213,10 @@ export default class ChannelHeader extends React.Component {
> >
<a <a
role='menuitem' role='menuitem'
data-toggle='modal'
data-target='#channel_members'
href='#' href='#'
onClick={() => this.setState({showMembersModal: true})}
> >
Manage Members {'Manage Members'}
</a> </a>
</li> </li>
); );
@@ -234,7 +237,7 @@ export default class ChannelHeader extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Set {channelTerm} Header... {'Set '}{channelTerm}{' Header...'}
</a> </a>
</li> </li>
); );
@@ -248,7 +251,7 @@ export default class ChannelHeader extends React.Component {
href='#' href='#'
onClick={() => this.setState({showEditChannelPurposeModal: true})} onClick={() => this.setState({showEditChannelPurposeModal: true})}
> >
Set {channelTerm} Purpose... {'Set '}{channelTerm}{' Purpose...'}
</a> </a>
</li> </li>
); );
@@ -265,7 +268,7 @@ export default class ChannelHeader extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Notification Preferences {'Notification Preferences'}
</a> </a>
</li> </li>
); );
@@ -286,7 +289,7 @@ export default class ChannelHeader extends React.Component {
data-name={channel.name} data-name={channel.name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Rename {channelTerm}... {'Rename '}{channelTerm}{'...'}
</a> </a>
</li> </li>
); );
@@ -303,7 +306,7 @@ export default class ChannelHeader extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Delete {channelTerm}... {'Delete '}{channelTerm}{'...'}
</a> </a>
</li> </li>
); );
@@ -319,7 +322,7 @@ export default class ChannelHeader extends React.Component {
href='#' href='#'
onClick={this.handleLeave} onClick={this.handleLeave}
> >
Leave {channelTerm} {'Leave '}{channelTerm}
</a> </a>
</li> </li>
); );
@@ -397,7 +400,7 @@ export default class ChannelHeader extends React.Component {
href='#' href='#'
onClick={this.searchMentions} onClick={this.searchMentions}
> >
Recent Mentions {'Recent Mentions'}
</a> </a>
</li> </li>
</ul> </ul>
@@ -411,6 +414,14 @@ export default class ChannelHeader extends React.Component {
onModalDismissed={() => this.setState({showEditChannelPurposeModal: false})} onModalDismissed={() => this.setState({showEditChannelPurposeModal: false})}
channel={channel} channel={channel}
/> />
<ChannelInviteModal
show={this.state.showInviteModal}
onModalDismissed={() => this.setState({showInviteModal: false})}
/>
<ChannelMembersModal
show={this.state.showMembersModal}
onModalDismissed={() => this.setState({showMembersModal: false})}
/>
</div> </div>
); );
} }

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

@@ -1,26 +1,25 @@
// Copyright (c) 2015 Mattermost, Inc. All Rights Reserved. // Copyright (c) 2015 Mattermost, Inc. All Rights Reserved.
// See License.txt for license information. // See License.txt for license information.
var UserStore = require('../stores/user_store.jsx'); const MemberList = require('./member_list.jsx');
var ChannelStore = require('../stores/channel_store.jsx'); const LoadingScreen = require('./loading_screen.jsx');
var MemberList = require('./member_list.jsx');
var LoadingScreen = require('./loading_screen.jsx'); const UserStore = require('../stores/user_store.jsx');
var utils = require('../utils/utils.jsx'); const ChannelStore = require('../stores/channel_store.jsx');
var client = require('../utils/client.jsx');
var AsyncClient = require('../utils/async_client.jsx'); const Utils = require('../utils/utils.jsx');
const Client = require('../utils/client.jsx');
const AsyncClient = require('../utils/async_client.jsx');
const Modal = ReactBootstrap.Modal;
export default class ChannelInviteModal extends React.Component { export default class ChannelInviteModal extends React.Component {
constructor() { constructor() {
super(); super();
this.componentDidMount = this.componentDidMount.bind(this);
this.componentWillUnmount = this.componentWillUnmount.bind(this);
this.onShow = this.onShow.bind(this);
this.onHide = this.onHide.bind(this);
this.onListenerChange = this.onListenerChange.bind(this); this.onListenerChange = this.onListenerChange.bind(this);
this.handleInvite = this.handleInvite.bind(this); this.handleInvite = this.handleInvite.bind(this);
this.isShown = false;
this.state = this.getStateFromStores(); this.state = this.getStateFromStores();
} }
getStateFromStores() { getStateFromStores() {
@@ -39,7 +38,7 @@ export default class ChannelInviteModal extends React.Component {
} }
} }
nonmembers.sort(function sortByUsername(a, b) { nonmembers.sort((a, b) => {
return a.username.localeCompare(b.username); return a.username.localeCompare(b.username);
}); });
@@ -49,35 +48,27 @@ export default class ChannelInviteModal extends React.Component {
} }
return { return {
nonmembers: nonmembers, nonmembers,
memberIds: memberIds, memberIds,
channelName: channelName, channelName,
loading: loading loading
}; };
} }
componentDidMount() { componentWillReceiveProps(nextProps) {
$(ReactDOM.findDOMNode(this)).on('hidden.bs.modal', this.onHide); if (!this.props.show && nextProps.show) {
$(ReactDOM.findDOMNode(this)).on('show.bs.modal', this.onShow); ChannelStore.addExtraInfoChangeListener(this.onListenerChange);
ChannelStore.addChangeListener(this.onListenerChange);
ChannelStore.addExtraInfoChangeListener(this.onListenerChange); UserStore.addChangeListener(this.onListenerChange);
ChannelStore.addChangeListener(this.onListenerChange); this.onListenerChange();
UserStore.addChangeListener(this.onListenerChange); } else if (this.props.show && !nextProps.show) {
} ChannelStore.removeExtraInfoChangeListener(this.onListenerChange);
componentWillUnmount() { ChannelStore.removeChangeListener(this.onListenerChange);
ChannelStore.removeExtraInfoChangeListener(this.onListenerChange); UserStore.removeChangeListener(this.onListenerChange);
ChannelStore.removeChangeListener(this.onListenerChange); }
UserStore.removeChangeListener(this.onListenerChange);
}
onShow() {
this.isShown = true;
this.onListenerChange();
}
onHide() {
this.isShown = false;
} }
onListenerChange() { onListenerChange() {
var newState = this.getStateFromStores(); var newState = this.getStateFromStores();
if (!utils.areStatesEqual(this.state, newState) && this.isShown) { if (!Utils.areStatesEqual(this.state, newState)) {
this.setState(newState); this.setState(newState);
} }
} }
@@ -90,8 +81,8 @@ export default class ChannelInviteModal extends React.Component {
var data = {}; var data = {};
data.user_id = userId; data.user_id = userId;
client.addChannelMember(ChannelStore.getCurrentId(), data, Client.addChannelMember(ChannelStore.getCurrentId(), data,
function sucess() { () => {
var nonmembers = this.state.nonmembers; var nonmembers = this.state.nonmembers;
var memberIds = this.state.memberIds; var memberIds = this.state.memberIds;
@@ -103,13 +94,12 @@ export default class ChannelInviteModal extends React.Component {
} }
} }
this.setState({inviteError: null, memberIds: memberIds, nonmembers: nonmembers}); this.setState({inviteError: null, memberIds, nonmembers});
AsyncClient.getChannelExtraInfo(true); AsyncClient.getChannelExtraInfo(true);
}.bind(this), },
(err) => {
function error(err) {
this.setState({inviteError: err.message}); this.setState({inviteError: err.message});
}.bind(this) }
); );
} }
render() { render() {
@@ -121,7 +111,7 @@ export default class ChannelInviteModal extends React.Component {
var currentMember = ChannelStore.getCurrentMember(); var currentMember = ChannelStore.getCurrentMember();
var isAdmin = false; var isAdmin = false;
if (currentMember) { if (currentMember) {
isAdmin = utils.isAdmin(currentMember.roles) || utils.isAdmin(UserStore.getCurrentUser().roles); isAdmin = Utils.isAdmin(currentMember.roles) || Utils.isAdmin(UserStore.getCurrentUser().roles);
} }
var content; var content;
@@ -138,43 +128,32 @@ export default class ChannelInviteModal extends React.Component {
} }
return ( return (
<div <Modal
className='modal fade more-modal' show={this.props.show}
id='channel_invite' onHide={this.props.onModalDismissed}
tabIndex='-1'
role='dialog'
aria-hidden='true'
> >
<div <Modal.Header closeButton={true}>
className='modal-dialog' <Modal.Title>{'Add New Members to '}<span className='name'>{this.state.channelName}</span></Modal.Title>
role='document' </Modal.Header>
> <Modal.Body>
<div className='modal-content'>
<div className='modal-header'>
<button
type='button'
className='close'
data-dismiss='modal'
aria-label='Close'
>
<span aria-hidden='true'>&times;</span>
</button>
<h4 className='modal-title'>Add New Members to <span className='name'>{this.state.channelName}</span></h4>
</div>
<div className='modal-body'>
{inviteError} {inviteError}
{content} {content}
</div> </Modal.Body>
<div className='modal-footer'> <Modal.Footer>
<button <button
type='button' type='button'
className='btn btn-default' className='btn btn-default'
data-dismiss='modal' onClick={this.props.onModalDismissed}
>Close</button> >
</div> {'Close'}
</div> </button>
</div> </Modal.Footer>
</div> </Modal>
); );
} }
} }
ChannelInviteModal.propTypes = {
show: React.PropTypes.bool.isRequired,
onModalDismissed: React.PropTypes.func.isRequired
};

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

@@ -1,200 +0,0 @@
// Copyright (c) 2015 Mattermost, Inc. All Rights Reserved.
// See License.txt for license information.
const UserStore = require('../stores/user_store.jsx');
const ChannelStore = require('../stores/channel_store.jsx');
const AsyncClient = require('../utils/async_client.jsx');
const MemberList = require('./member_list.jsx');
const Client = require('../utils/client.jsx');
const Utils = require('../utils/utils.jsx');
export default class ChannelMembers extends React.Component {
constructor(props) {
super(props);
this.getStateFromStores = this.getStateFromStores.bind(this);
this.onChange = this.onChange.bind(this);
this.handleRemove = this.handleRemove.bind(this);
this.onHide = this.onHide.bind(this);
this.onShow = this.onShow.bind(this);
this.state = this.getStateFromStores();
}
getStateFromStores() {
const users = UserStore.getActiveOnlyProfiles();
let memberList = ChannelStore.getCurrentExtraInfo().members;
let nonmemberList = [];
for (let id in users) {
if (users.hasOwnProperty(id)) {
let found = false;
for (let i = 0; i < memberList.length; i++) {
if (memberList[i].id === id) {
found = true;
break;
}
}
if (!found) {
nonmemberList.push(users[id]);
}
}
}
function compareByUsername(a, b) {
if (a.username < b.username) {
return -1;
} else if (a.username > b.username) {
return 1;
}
return 0;
}
memberList.sort(compareByUsername);
nonmemberList.sort(compareByUsername);
const channel = ChannelStore.getCurrent();
let channelName = '';
if (channel) {
channelName = channel.display_name;
}
return {
nonmemberList: nonmemberList,
memberList: memberList,
channelName: channelName
};
}
onHide() {
this.setState({renderMembers: false});
}
onShow() {
this.setState({renderMembers: true});
}
componentDidMount() {
ChannelStore.addExtraInfoChangeListener(this.onChange);
ChannelStore.addChangeListener(this.onChange);
$(ReactDOM.findDOMNode(this.refs.modal)).on('hidden.bs.modal', this.onHide);
$(ReactDOM.findDOMNode(this.refs.modal)).on('show.bs.modal', this.onShow);
}
componentWillUnmount() {
ChannelStore.removeExtraInfoChangeListener(this.onChange);
ChannelStore.removeChangeListener(this.onChange);
}
onChange() {
const newState = this.getStateFromStores();
if (!Utils.areStatesEqual(this.state, newState)) {
this.setState(newState);
}
}
handleRemove(userId) {
// Make sure the user is a member of the channel
let memberList = this.state.memberList;
let found = false;
for (let i = 0; i < memberList.length; i++) {
if (memberList[i].id === userId) {
found = true;
break;
}
}
if (!found) {
return;
}
let data = {};
data.user_id = userId;
Client.removeChannelMember(ChannelStore.getCurrentId(), data,
function handleRemoveSuccess() {
let oldMember;
for (let i = 0; i < memberList.length; i++) {
if (userId === memberList[i].id) {
oldMember = memberList[i];
memberList.splice(i, 1);
break;
}
}
let nonmemberList = this.state.nonmemberList;
if (oldMember) {
nonmemberList.push(oldMember);
}
this.setState({memberList: memberList, nonmemberList: nonmemberList});
AsyncClient.getChannelExtraInfo(true);
}.bind(this),
function handleRemoveError(err) {
this.setState({inviteError: err.message});
}.bind(this)
);
}
render() {
const currentMember = ChannelStore.getCurrentMember();
let isAdmin = false;
if (currentMember) {
isAdmin = Utils.isAdmin(currentMember.roles) || Utils.isAdmin(UserStore.getCurrentUser().roles);
}
var memberList = null;
if (this.state.renderMembers) {
memberList = (
<MemberList
memberList={this.state.memberList}
isAdmin={isAdmin}
handleRemove={this.handleRemove}
/>
);
}
return (
<div
className='modal fade more-modal'
ref='modal'
id='channel_members'
tabIndex='-1'
role='dialog'
aria-hidden='true'
>
<div className='modal-dialog'>
<div className='modal-content'>
<div className='modal-header'>
<button
type='button'
className='close'
data-dismiss='modal'
aria-label='Close'
>
<span aria-hidden='true'>×</span>
</button>
<h4 className='modal-title'><span className='name'>{this.state.channelName}</span> Members</h4>
<a
className='btn btn-md btn-primary'
data-toggle='modal'
data-target='#channel_invite'
>
<i className='glyphicon glyphicon-envelope'/> Add New Members
</a>
</div>
<div
ref='modalBody'
className='modal-body'
>
{memberList}
</div>
<div className='modal-footer'>
<button
type='button'
className='btn btn-default'
data-dismiss='modal'
>
Close
</button>
</div>
</div>
</div>
</div>
);
}
}

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

@@ -0,0 +1,193 @@
// Copyright (c) 2015 Mattermost, Inc. All Rights Reserved.
// See License.txt for license information.
const MemberList = require('./member_list.jsx');
const ChannelInviteModal = require('./channel_invite_modal.jsx');
const UserStore = require('../stores/user_store.jsx');
const ChannelStore = require('../stores/channel_store.jsx');
const AsyncClient = require('../utils/async_client.jsx');
const Client = require('../utils/client.jsx');
const Utils = require('../utils/utils.jsx');
const Modal = ReactBootstrap.Modal;
export default class ChannelMembersModal extends React.Component {
constructor(props) {
super(props);
this.getStateFromStores = this.getStateFromStores.bind(this);
this.onChange = this.onChange.bind(this);
this.handleRemove = this.handleRemove.bind(this);
const state = this.getStateFromStores();
state.showInviteModal = false;
this.state = state;
}
getStateFromStores() {
const users = UserStore.getActiveOnlyProfiles();
const memberList = ChannelStore.getCurrentExtraInfo().members;
const nonmemberList = [];
for (const id in users) {
if (users.hasOwnProperty(id)) {
let found = false;
for (let i = 0; i < memberList.length; i++) {
if (memberList[i].id === id) {
found = true;
break;
}
}
if (!found) {
nonmemberList.push(users[id]);
}
}
}
function compareByUsername(a, b) {
if (a.username < b.username) {
return -1;
} else if (a.username > b.username) {
return 1;
}
return 0;
}
memberList.sort(compareByUsername);
nonmemberList.sort(compareByUsername);
const channel = ChannelStore.getCurrent();
let channelName = '';
if (channel) {
channelName = channel.display_name;
}
return {
nonmemberList,
memberList,
channelName
};
}
componentWillReceiveProps(nextProps) {
if (!this.props.show && nextProps.show) {
ChannelStore.addExtraInfoChangeListener(this.onChange);
ChannelStore.addChangeListener(this.onChange);
} else if (this.props.show && !nextProps.show) {
ChannelStore.removeExtraInfoChangeListener(this.onChange);
ChannelStore.removeChangeListener(this.onChange);
}
}
onChange() {
const newState = this.getStateFromStores();
if (!Utils.areStatesEqual(this.state, newState)) {
this.setState(newState);
}
}
handleRemove(userId) {
// Make sure the user is a member of the channel
const memberList = this.state.memberList;
let found = false;
for (let i = 0; i < memberList.length; i++) {
if (memberList[i].id === userId) {
found = true;
break;
}
}
if (!found) {
return;
}
const data = {};
data.user_id = userId;
Client.removeChannelMember(ChannelStore.getCurrentId(), data,
() => {
let oldMember;
for (let i = 0; i < memberList.length; i++) {
if (userId === memberList[i].id) {
oldMember = memberList[i];
memberList.splice(i, 1);
break;
}
}
const nonmemberList = this.state.nonmemberList;
if (oldMember) {
nonmemberList.push(oldMember);
}
this.setState({memberList, nonmemberList});
AsyncClient.getChannelExtraInfo(true);
},
(err) => {
this.setState({inviteError: err.message});
}
);
}
render() {
const currentMember = ChannelStore.getCurrentMember();
let isAdmin = false;
if (currentMember) {
isAdmin = Utils.isAdmin(currentMember.roles) || Utils.isAdmin(UserStore.getCurrentUser().roles);
}
return (
<div>
<Modal
show={this.props.show}
onHide={this.props.onModalDismissed}
>
<Modal.Header closeButton={true}>
<Modal.Title><span className='name'>{this.state.channelName}</span>{' Members'}</Modal.Title>
<a
className='btn btn-md btn-primary'
href='#'
onClick={() => {
this.setState({showInviteModal: true});
this.props.onModalDismissed();
}}
>
<i className='glyphicon glyphicon-envelope'/>{' Add New Members'}
</a>
</Modal.Header>
<Modal.Body>
<div className='col-sm-12'>
<div className='team-member-list'>
<MemberList
memberList={this.state.memberList}
isAdmin={isAdmin}
handleRemove={this.handleRemove}
/>
</div>
</div>
</Modal.Body>
<Modal.Footer>
<button
type='button'
className='btn btn-default'
onClick={this.props.onModalDismissed}
>
{'Close'}
</button>
</Modal.Footer>
</Modal>
<ChannelInviteModal
show={this.state.showInviteModal}
onModalDismissed={() => this.setState({showInviteModal: false})}
/>
</div>
);
}
}
ChannelMembersModal.defaultProps = {
show: false
};
ChannelMembersModal.propTypes = {
show: React.PropTypes.bool.isRequired,
onModalDismissed: React.PropTypes.func.isRequired
};

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

@@ -1,22 +1,26 @@
// Copyright (c) 2015 Mattermost, Inc. All Rights Reserved. // Copyright (c) 2015 Mattermost, Inc. All Rights Reserved.
// See License.txt for license information. // See License.txt for license information.
var Client = require('../utils/client.jsx');
var AsyncClient = require('../utils/async_client.jsx');
var UserStore = require('../stores/user_store.jsx');
var ChannelStore = require('../stores/channel_store.jsx');
var TeamStore = require('../stores/team_store.jsx');
var MessageWrapper = require('./message_wrapper.jsx');
var NotifyCounts = require('./notify_counts.jsx');
const EditChannelPurposeModal = require('./edit_channel_purpose_modal.jsx'); const EditChannelPurposeModal = require('./edit_channel_purpose_modal.jsx');
const MessageWrapper = require('./message_wrapper.jsx');
const NotifyCounts = require('./notify_counts.jsx');
const ChannelMembersModal = require('./channel_members_modal.jsx');
const ChannelInviteModal = require('./channel_invite_modal.jsx');
const UserStore = require('../stores/user_store.jsx');
const ChannelStore = require('../stores/channel_store.jsx');
const TeamStore = require('../stores/team_store.jsx');
const Client = require('../utils/client.jsx');
const AsyncClient = require('../utils/async_client.jsx');
const Utils = require('../utils/utils.jsx'); const Utils = require('../utils/utils.jsx');
var Constants = require('../utils/constants.jsx'); const Constants = require('../utils/constants.jsx');
var ActionTypes = Constants.ActionTypes; const ActionTypes = Constants.ActionTypes;
var AppDispatcher = require('../dispatcher/app_dispatcher.jsx'); const AppDispatcher = require('../dispatcher/app_dispatcher.jsx');
var Popover = ReactBootstrap.Popover; const Popover = ReactBootstrap.Popover;
var OverlayTrigger = ReactBootstrap.OverlayTrigger; const OverlayTrigger = ReactBootstrap.OverlayTrigger;
export default class Navbar extends React.Component { export default class Navbar extends React.Component {
constructor(props) { constructor(props) {
@@ -29,6 +33,8 @@ export default class Navbar extends React.Component {
const state = this.getStateFromStores(); const state = this.getStateFromStores();
state.showEditChannelPurposeModal = false; state.showEditChannelPurposeModal = false;
state.showMembersModal = false;
state.showInviteModal = false;
this.state = state; this.state = state;
} }
getStateFromStores() { getStateFromStores() {
@@ -45,17 +51,18 @@ export default class Navbar extends React.Component {
} }
componentWillUnmount() { componentWillUnmount() {
ChannelStore.removeChangeListener(this.onChange); ChannelStore.removeChangeListener(this.onChange);
ChannelStore.removeExtraInfoChangeListener(this.onChange);
} }
handleSubmit(e) { handleSubmit(e) {
e.preventDefault(); e.preventDefault();
} }
handleLeave() { handleLeave() {
Client.leaveChannel(this.state.channel.id, Client.leaveChannel(this.state.channel.id,
function success() { () => {
AsyncClient.getChannels(true); AsyncClient.getChannels(true);
window.location.href = TeamStore.getCurrentTeamUrl() + '/channels/town-square'; window.location.href = TeamStore.getCurrentTeamUrl() + '/channels/town-square';
}, },
function error(err) { (err) => {
AsyncClient.dispatchError(err, 'handleLeave'); AsyncClient.dispatchError(err, 'handleLeave');
} }
); );
@@ -104,7 +111,7 @@ export default class Navbar extends React.Component {
data-channelid={channel.id} data-channelid={channel.id}
href='#' href='#'
> >
View Info {'View Info'}
</a> </a>
</li> </li>
); );
@@ -120,7 +127,7 @@ export default class Navbar extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Set Channel Header... {'Set Channel Header...'}
</a> </a>
</li> </li>
); );
@@ -145,11 +152,10 @@ export default class Navbar extends React.Component {
<li role='presentation'> <li role='presentation'>
<a <a
role='menuitem' role='menuitem'
data-toggle='modal'
data-target='#channel_invite'
href='#' href='#'
onClick={() => this.setState({showInviteModal: false})}
> >
Add Members {'Add Members'}
</a> </a>
</li> </li>
); );
@@ -161,7 +167,7 @@ export default class Navbar extends React.Component {
href='#' href='#'
onClick={this.handleLeave} onClick={this.handleLeave}
> >
Leave Channel {'Leave Channel'}
</a> </a>
</li> </li>
); );
@@ -175,11 +181,10 @@ export default class Navbar extends React.Component {
<li role='presentation'> <li role='presentation'>
<a <a
role='menuitem' role='menuitem'
data-toggle='modal'
data-target='#channel_members'
href='#' href='#'
onClick={() => this.setState({showMembersModal: true})}
> >
Manage Members {'Manage Members'}
</a> </a>
</li> </li>
); );
@@ -195,7 +200,7 @@ export default class Navbar extends React.Component {
data-name={channel.name} data-name={channel.name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Rename Channel... {'Rename Channel...'}
</a> </a>
</li> </li>
); );
@@ -210,7 +215,7 @@ export default class Navbar extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Delete Channel... {'Delete Channel...'}
</a> </a>
</li> </li>
); );
@@ -228,7 +233,7 @@ export default class Navbar extends React.Component {
data-title={channel.display_name} data-title={channel.display_name}
data-channelid={channel.id} data-channelid={channel.id}
> >
Notification Preferences {'Notification Preferences'}
</a> </a>
</li> </li>
); );
@@ -299,7 +304,7 @@ export default class Navbar extends React.Component {
data-toggle='collapse' data-toggle='collapse'
data-target='#navbar-collapse-1' data-target='#navbar-collapse-1'
> >
<span className='sr-only'>Toggle sidebar</span> <span className='sr-only'>{'Toggle sidebar'}</span>
<span className='icon-bar'></span> <span className='icon-bar'></span>
<span className='icon-bar'></span> <span className='icon-bar'></span>
<span className='icon-bar'></span> <span className='icon-bar'></span>
@@ -315,7 +320,7 @@ export default class Navbar extends React.Component {
data-target='#sidebar-nav' data-target='#sidebar-nav'
onClick={this.toggleLeftSidebar} onClick={this.toggleLeftSidebar}
> >
<span className='sr-only'>Toggle sidebar</span> <span className='sr-only'>{'Toggle sidebar'}</span>
<span className='icon-bar'></span> <span className='icon-bar'></span>
<span className='icon-bar'></span> <span className='icon-bar'></span>
<span className='icon-bar'></span> <span className='icon-bar'></span>
@@ -426,6 +431,14 @@ export default class Navbar extends React.Component {
onModalDismissed={() => this.setState({showEditChannelPurposeModal: false})} onModalDismissed={() => this.setState({showEditChannelPurposeModal: false})}
channel={channel} channel={channel}
/> />
<ChannelMembersModal
show={this.state.showMembersModal}
onModalDismissed={() => this.setState({showMembersModal: false})}
/>
<ChannelInviteModal
show={this.state.showInviteModal}
onModalDismissed={() => this.setState({showInviteModal: false})}
/>
</div> </div>
); );
} }

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

@@ -20,8 +20,6 @@ var PostDeletedModal = require('../components/post_deleted_modal.jsx');
var ChannelNotificationsModal = require('../components/channel_notifications.jsx'); var ChannelNotificationsModal = require('../components/channel_notifications.jsx');
var UserSettingsModal = require('../components/user_settings/user_settings_modal.jsx'); var UserSettingsModal = require('../components/user_settings/user_settings_modal.jsx');
var TeamSettingsModal = require('../components/team_settings_modal.jsx'); var TeamSettingsModal = require('../components/team_settings_modal.jsx');
var ChannelMembersModal = require('../components/channel_members.jsx');
var ChannelInviteModal = require('../components/channel_invite_modal.jsx');
var TeamMembersModal = require('../components/team_members.jsx'); var TeamMembersModal = require('../components/team_members.jsx');
var ChannelInfoModal = require('../components/channel_info_modal.jsx'); var ChannelInfoModal = require('../components/channel_info_modal.jsx');
var AccessHistoryModal = require('../components/access_history_modal.jsx'); var AccessHistoryModal = require('../components/access_history_modal.jsx');
@@ -127,16 +125,6 @@ function setupChannelPage(props) {
document.getElementById('channel_notifications_modal') document.getElementById('channel_notifications_modal')
); );
ReactDOM.render(
<ChannelMembersModal />,
document.getElementById('channel_members_modal')
);
ReactDOM.render(
<ChannelInviteModal />,
document.getElementById('channel_invite_modal')
);
ReactDOM.render( ReactDOM.render(
<ChannelInfoModal />, <ChannelInfoModal />,
document.getElementById('channel_info_modal') document.getElementById('channel_info_modal')

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

@@ -25,8 +25,6 @@
<div id="new_channel_modal"></div> <div id="new_channel_modal"></div>
<div id="post_deleted_modal"></div> <div id="post_deleted_modal"></div>
<div id="channel_notifications_modal"></div> <div id="channel_notifications_modal"></div>
<div id="channel_members_modal"></div>
<div id="channel_invite_modal"></div>
<div id="team_members_modal"></div> <div id="team_members_modal"></div>
<div id="direct_channel_modal"></div> <div id="direct_channel_modal"></div>
<div id="channel_info_modal"></div> <div id="channel_info_modal"></div>