diff --git a/components/at_mention/at_mention.jsx b/components/at_mention/at_mention.jsx
index 9d832657d4ac..63ae81422fde 100644
--- a/components/at_mention/at_mention.jsx
+++ b/components/at_mention/at_mention.jsx
@@ -9,7 +9,7 @@ import {Client4} from 'mattermost-redux/client';
import Pluggable from 'plugins/pluggable';
-import ProfilePopover from 'components/profile_popover.jsx';
+import ProfilePopover from 'components/profile_popover_new.jsx';
export default class AtMention extends React.PureComponent {
static propTypes = {
@@ -95,6 +95,7 @@ export default class AtMention extends React.PureComponent {
hide={this.hideProfilePopover}
isRHS={this.props.isRHS}
hasMention={this.props.hasMention}
+ parent={this}
/>
}
diff --git a/components/profile_picture.jsx b/components/profile_picture.jsx
index 0194ed8adb59..52ee492adedc 100644
--- a/components/profile_picture.jsx
+++ b/components/profile_picture.jsx
@@ -10,7 +10,7 @@ import Pluggable from 'plugins/pluggable';
import * as PostUtils from 'utils/post_utils.jsx';
-import ProfilePopover from './profile_popover.jsx';
+import ProfilePopover from './profile_popover_new.jsx';
import StatusIcon from './status_icon.jsx';
export default class ProfilePicture extends React.PureComponent {
@@ -18,7 +18,8 @@ export default class ProfilePicture extends React.PureComponent {
width: '36',
height: '36',
isRHS: false,
- hasMention: false
+ hasMention: false,
+ disablePopover: false
};
static propTypes = {
@@ -30,7 +31,8 @@ export default class ProfilePicture extends React.PureComponent {
isBusy: PropTypes.bool,
isRHS: PropTypes.bool,
hasMention: PropTypes.bool,
- post: PropTypes.object
+ post: PropTypes.object,
+ disablePopover: PropTypes.bool
};
hideProfilePopover = () => {
@@ -44,7 +46,7 @@ export default class ProfilePicture extends React.PureComponent {
if (this.props.post) {
isSystemMessage = PostUtils.isSystemMessage(this.props.post);
}
- if (this.props.user) {
+ if (this.props.user && !this.props.disablePopover) {
return (
}
diff --git a/components/profile_popover_new.jsx b/components/profile_popover_new.jsx
new file mode 100644
index 000000000000..bb416544f372
--- /dev/null
+++ b/components/profile_popover_new.jsx
@@ -0,0 +1,363 @@
+// Copyright (c) 2016-present Mattermost, Inc. All Rights Reserved.
+// See License.txt for license information.
+
+import PropTypes from 'prop-types';
+import React from 'react';
+import {OverlayTrigger, Popover, Tooltip} from 'react-bootstrap';
+import {browserHistory} from 'react-router';
+
+import {openDirectChannelToUser} from 'actions/channel_actions.jsx';
+import * as GlobalActions from 'actions/global_actions.jsx';
+import * as WebrtcActions from 'actions/webrtc_actions.jsx';
+import TeamStore from 'stores/team_store.jsx';
+import UserStore from 'stores/user_store.jsx';
+import WebrtcStore from 'stores/webrtc_store.jsx';
+
+import Constants from 'utils/constants.jsx';
+import * as Utils from 'utils/utils.jsx';
+
+const UserStatuses = Constants.UserStatuses;
+
+import emailIcon from 'images/icons/email_cta.png';
+import dmIcon from 'images/icons/dm_cta.png';
+import calendarIcon from 'images/icons/calendar_cta.png';
+
+class ProfilePopoverNew extends React.Component {
+ static getComponentName() {
+ return 'ProfilePopoverNew';
+ }
+
+ static propTypes = {
+
+ /**
+ * Source URL from the image to display in the popover
+ */
+ src: PropTypes.string.isRequired,
+
+ /**
+ * User the popover is being opened for
+ */
+ user: PropTypes.object.isRequired,
+
+ /**
+ * Status for the user, either 'offline', 'away', 'dnd' or 'online'
+ */
+ status: PropTypes.string,
+
+ /**
+ * Set to true if the user is in a WebRTC call
+ */
+ isBusy: PropTypes.bool,
+
+ /**
+ * Function to call to hide the popover
+ */
+ hide: PropTypes.func,
+
+ /**
+ * Set to true if the popover was opened from the right-hand
+ * sidebar (comment thread, search results, etc.)
+ */
+ isRHS: PropTypes.bool,
+
+ /**
+ * @internal
+ */
+ hasMention: PropTypes.bool,
+
+ /**
+ * @internal
+ */
+ parent: PropTypes.object,
+
+ ...Popover.propTypes
+ }
+
+ static defaultProps = {
+ isRHS: false,
+ hasMention: false
+ }
+
+ constructor(props) {
+ super(props);
+
+ this.initWebrtc = this.initWebrtc.bind(this);
+ this.handleShowDirectChannel = this.handleShowDirectChannel.bind(this);
+ this.handleMentionKeyClick = this.handleMentionKeyClick.bind(this);
+ this.state = {
+ currentUserId: UserStore.getCurrentId(),
+ loadingDMChannel: false
+ };
+ }
+ shouldComponentUpdate(nextProps) {
+ if (!Utils.areObjectsEqual(nextProps.user, this.props.user)) {
+ return true;
+ }
+
+ if (nextProps.src !== this.props.src) {
+ return true;
+ }
+
+ if (nextProps.status !== this.props.status) {
+ return true;
+ }
+
+ if (nextProps.isBusy !== this.props.isBusy) {
+ return true;
+ }
+
+ // React-Bootstrap Forwarded Props from OverlayTrigger to Popover
+ if (nextProps.arrowOffsetLeft !== this.props.arrowOffsetLeft) {
+ return true;
+ }
+
+ if (nextProps.arrowOffsetTop !== this.props.arrowOffsetTop) {
+ return true;
+ }
+
+ if (nextProps.positionLeft !== this.props.positionLeft) {
+ return true;
+ }
+
+ if (nextProps.positionTop !== this.props.positionTop) {
+ return true;
+ }
+
+ return false;
+ }
+
+ handleShowDirectChannel(e) {
+ e.preventDefault();
+
+ if (!this.props.user) {
+ return;
+ }
+
+ const user = this.props.user;
+
+ if (this.state.loadingDMChannel) {
+ return;
+ }
+
+ this.setState({loadingDMChannel: true});
+
+ openDirectChannelToUser(
+ user.id,
+ (channel) => {
+ if (Utils.isMobile()) {
+ GlobalActions.emitCloseRightHandSide();
+ }
+ this.setState({loadingDMChannel: false});
+ if (this.props.hide) {
+ this.props.hide();
+ }
+ browserHistory.push(TeamStore.getCurrentTeamRelativeUrl() + '/channels/' + channel.name);
+ }
+ );
+ }
+
+ initWebrtc() {
+ if (this.props.status !== UserStatuses.OFFLINE && !WebrtcStore.isBusy()) {
+ GlobalActions.emitCloseRightHandSide();
+ WebrtcActions.initWebrtc(this.props.user.id, true);
+ }
+ }
+
+ handleMentionKeyClick(e) {
+ e.preventDefault();
+
+ if (!this.props.user) {
+ return;
+ }
+ if (this.props.hide) {
+ this.props.hide();
+ }
+ GlobalActions.emitPopoverMentionKeyClick(this.props.isRHS, this.props.user.username);
+ }
+
+ render() {
+ const popoverProps = Object.assign({}, this.props);
+ delete popoverProps.user;
+ delete popoverProps.src;
+ delete popoverProps.parent;
+ delete popoverProps.status;
+ delete popoverProps.isBusy;
+ delete popoverProps.hide;
+ delete popoverProps.isRHS;
+ delete popoverProps.hasMention;
+ delete popoverProps.dispatch;
+
+ const email = this.props.user.email;
+ const username = this.props.user.username;
+ var dataContent = [];
+ var dataContentIcons = [];
+ var showEmail = global.window.mm_config.ShowEmailAddress === 'true' || UserStore.isSystemAdminForCurrentUser() || this.props.user.id === UserStore.getCurrentId();
+ var showDirectChannel = this.props.user.id !== UserStore.getCurrentId();
+ const fullname = Utils.getFullName(this.props.user);
+ const firstname = this.props.user.first_name;
+ if (fullname) {
+ dataContent.push(
+ {`See ${firstname}'s whober profile`}
+ )}
+ >
+
+
+ );
+ }
+
+ if (this.props.user.position) {
+ dataContent.push(
+ {this.props.user.position}}
+ >
+
+ {this.props.user.position}
+
+
+ );
+ }
+
+ if (showDirectChannel) {
+ dataContentIcons.push(
+
+ );
+ }
+ if (showEmail) {
+ dataContentIcons.push(
+
+ );
+ }
+ dataContentIcons.push(
+
+ );
+ if (showEmail || showDirectChannel) {
+ dataContent.push(
+
+ {dataContentIcons}
+
+ );
+ }
+ if (username && firstname) {
+ dataContent.push(
+ {`Mention to ${firstname}`}
+ )}
+ >
+
+
+ );
+ }
+
+ return (
+
+
+
+ {dataContent}
+
+
+ );
+ }
+}
+
+delete ProfilePopoverNew.propTypes.id;
+
+export default ProfilePopoverNew;
diff --git a/components/search_results_item.jsx b/components/search_results_item.jsx
index fd2c1b4363ac..986a3634d515 100644
--- a/components/search_results_item.jsx
+++ b/components/search_results_item.jsx
@@ -185,13 +185,11 @@ export default class SearchResultsItem extends React.Component {
}
let overrideUsername;
- let disableProfilePopover = false;
if (post.props &&
post.props.from_webhook &&
post.props.override_username &&
global.window.mm_config.EnablePostUsernameOverride === 'true') {
overrideUsername = post.props.override_username;
- disableProfilePopover = true;
}
let botIndicator;
@@ -205,6 +203,7 @@ export default class SearchResultsItem extends React.Component {
user={this.props.user}
status={this.props.status}
isBusy={this.props.isBusy}
+ disablePopover={true}
/>
);
@@ -322,7 +321,7 @@ export default class SearchResultsItem extends React.Component {
diff --git a/components/sidebar_header.jsx b/components/sidebar_header.jsx
index 70cf3fd07627..47cf38aeac51 100644
--- a/components/sidebar_header.jsx
+++ b/components/sidebar_header.jsx
@@ -81,6 +81,8 @@ export default class SidebarHeader extends React.Component {
}
let teamNameWithToolTip = null;
+
+ /*
if (this.props.teamDescription === '') {
teamNameWithToolTip = (
);
} else {
- var me = this.props.currentUser;
- const fullName = Utils.getFullName(me);
- teamNameWithToolTip = (
-
- {fullName}
-
- )}
- ref='descriptionOverlay'
- >
-
-
- );
- }
+
+ )}
+ ref='descriptionOverlay'
+ >
+
+
+ );
+
+ // }
return (
}
diff --git a/images/icons/calendar_cta.png b/images/icons/calendar_cta.png
new file mode 100644
index 000000000000..2ecdb018b1f2
Binary files /dev/null and b/images/icons/calendar_cta.png differ
diff --git a/images/icons/dm_cta.png b/images/icons/dm_cta.png
new file mode 100644
index 000000000000..0eddc59fa546
Binary files /dev/null and b/images/icons/dm_cta.png differ
diff --git a/images/icons/email_cta.png b/images/icons/email_cta.png
new file mode 100644
index 000000000000..b44079f2dbea
Binary files /dev/null and b/images/icons/email_cta.png differ
diff --git a/sass/components/_popover.scss b/sass/components/_popover.scss
index 27a959a03ed3..0bc2b8d72b6b 100644
--- a/sass/components/_popover.scss
+++ b/sass/components/_popover.scss
@@ -68,7 +68,6 @@
background: transparent;
border: none;
box-shadow: none;
- top: -190px !important;
.popover-title, .arrow {
display: none;
}
@@ -103,6 +102,11 @@
margin-bottom: 0;
}
}
+ .profile-popover-position {
+ font-size: 12px;
+ max-width: 185px;
+ margin: 0 8px;
+ }
.profile-popover-icons {
margin: 0 auto;
.profile-popover-icon {