summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--NOTICE.txt33
-rw-r--r--api/command.go11
-rw-r--r--api/file.go2
-rw-r--r--api/post.go4
-rw-r--r--model/search_params.go4
-rw-r--r--model/search_params_test.go4
-rw-r--r--model/utils.go1
-rw-r--r--web/react/components/admin_console/license_settings.jsx7
-rw-r--r--web/react/components/channel_members_modal.jsx8
-rw-r--r--web/react/components/create_post.jsx10
-rw-r--r--web/react/components/file_attachment.jsx112
-rw-r--r--web/react/components/file_upload.jsx10
-rw-r--r--web/react/components/get_link_modal.jsx23
-rw-r--r--web/react/components/get_team_invite_link_modal.jsx4
-rw-r--r--web/react/components/invite_member_modal.jsx4
-rw-r--r--web/react/components/navbar_dropdown.jsx2
-rw-r--r--web/react/components/suggestion/search_suggestion_list.jsx2
-rw-r--r--web/react/components/textbox.jsx51
-rw-r--r--web/react/components/user_list_row.jsx4
-rw-r--r--web/react/components/user_settings/user_settings_modal.jsx2
-rw-r--r--web/react/utils/text_formatting.jsx13
-rw-r--r--web/sass-files/sass/partials/_post.scss24
-rw-r--r--web/static/i18n/en.json18
-rw-r--r--web/static/i18n/es.json31
-rw-r--r--web/static/i18n/pt.json71
25 files changed, 231 insertions, 224 deletions
diff --git a/NOTICE.txt b/NOTICE.txt
index b39ee7cc9..8491e2f17 100644
--- a/NOTICE.txt
+++ b/NOTICE.txt
@@ -1638,3 +1638,36 @@ LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+---
+
+This product contains a modified portion of 'fastclick', a library for eliminating the delay between a physical tap and the firing of a click event on mobile browsers.
+by FT Labs.
+
+* HOMEPAGE:
+ * https://github.com/ftlabs/fastclick
+
+* LICENSE:
+
+Copyright (c) 2014 The Financial Times Ltd.
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without
+restriction, including without limitation the rights to use,
+copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the
+Software is furnished to do so, subject to the following
+conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+OTHER DEALINGS IN THE SOFTWARE.
diff --git a/api/command.go b/api/command.go
index bebe6629c..451de2c33 100644
--- a/api/command.go
+++ b/api/command.go
@@ -111,7 +111,7 @@ func executeCommand(c *Context, w http.ResponseWriter, r *http.Request) {
if provider != nil {
response := provider.DoCommand(c, channelId, message)
- handleResponse(c, w, response, channelId, provider.GetCommand(c))
+ handleResponse(c, w, response, channelId, provider.GetCommand(c), true)
return
} else {
chanChan := Srv.Store.Channel().Get(channelId)
@@ -193,7 +193,7 @@ func executeCommand(c *Context, w http.ResponseWriter, r *http.Request) {
if response == nil {
c.Err = model.NewLocAppError("command", "api.command.execute_command.failed_empty.app_error", map[string]interface{}{"Trigger": trigger}, "")
} else {
- handleResponse(c, w, response, channelId, cmd)
+ handleResponse(c, w, response, channelId, cmd, false)
}
} else {
body, _ := ioutil.ReadAll(resp.Body)
@@ -211,11 +211,14 @@ func executeCommand(c *Context, w http.ResponseWriter, r *http.Request) {
c.Err = model.NewLocAppError("command", "api.command.execute_command.not_found.app_error", map[string]interface{}{"Trigger": trigger}, "")
}
-func handleResponse(c *Context, w http.ResponseWriter, response *model.CommandResponse, channelId string, cmd *model.Command) {
+func handleResponse(c *Context, w http.ResponseWriter, response *model.CommandResponse, channelId string, cmd *model.Command, builtIn bool) {
post := &model.Post{}
post.ChannelId = channelId
- post.AddProp("from_webhook", "true")
+
+ if !builtIn {
+ post.AddProp("from_webhook", "true")
+ }
if utils.Cfg.ServiceSettings.EnablePostUsernameOverride {
if len(cmd.Username) != 0 {
diff --git a/api/file.go b/api/file.go
index 5c983ea55..0011afd5b 100644
--- a/api/file.go
+++ b/api/file.go
@@ -52,7 +52,7 @@ const (
RotatedCCWMirrored = 7
RotatedCW = 8
- MaxImageSize = 4096 * 2160 // 4k resolution
+ MaxImageSize = 6048 * 4032 // 24 megapixels, roughly 36MB as a raw image
)
var fileInfoCache *utils.Cache = utils.NewLru(1000)
diff --git a/api/post.go b/api/post.go
index 9d3ba5ab1..e6560a8e8 100644
--- a/api/post.go
+++ b/api/post.go
@@ -604,12 +604,12 @@ func sendNotifications(c *Context, post *model.Post, team *model.Team, channel *
year := fmt.Sprintf("%d", tm.Year())
zone, _ := tm.Zone()
- subjectPage := NewServerTemplatePage("post_subject", c.Locale)
+ subjectPage := NewServerTemplatePage("post_subject", profileMap[id].Locale)
subjectPage.Props["Subject"] = userLocale("api.templates.post_subject",
map[string]interface{}{"SubjectText": subjectText, "TeamDisplayName": team.DisplayName,
"Month": month[:3], "Day": day, "Year": year})
- bodyPage := NewServerTemplatePage("post_body", c.Locale)
+ bodyPage := NewServerTemplatePage("post_body", profileMap[id].Locale)
bodyPage.Props["SiteURL"] = c.GetSiteURL()
bodyPage.Props["PostMessage"] = model.ClearMentionTags(post.Message)
bodyPage.Props["TeamLink"] = teamURL + "/channels/" + channel.Name
diff --git a/model/search_params.go b/model/search_params.go
index 9a7406a07..d31782691 100644
--- a/model/search_params.go
+++ b/model/search_params.go
@@ -89,9 +89,9 @@ func parseSearchFlags(input []string) ([]string, [][2]string) {
}
if !isFlag {
- // trim off surrounding punctuation
+ // trim off surrounding punctuation (note that we leave trailing asterisks to allow wildcards)
word = puncStart.ReplaceAllString(word, "")
- word = puncEnd.ReplaceAllString(word, "")
+ word = puncEndWildcard.ReplaceAllString(word, "")
// and remove extra pound #s
word = hashtagStart.ReplaceAllString(word, "#")
diff --git a/model/search_params_test.go b/model/search_params_test.go
index 59eb0a113..7138d82c4 100644
--- a/model/search_params_test.go
+++ b/model/search_params_test.go
@@ -216,4 +216,8 @@ func TestParseSearchParams(t *testing.T) {
if sp := ParseSearchParams("##hashtag +#plus+"); len(sp) != 1 || sp[0].Terms != "#hashtag #plus" || sp[0].IsHashtag != true || len(sp[0].InChannels) != 0 || len(sp[0].FromUsers) != 0 {
t.Fatalf("Incorrect output from parse search params: %v", sp[0])
}
+
+ if sp := ParseSearchParams("wildcar*"); len(sp) != 1 || sp[0].Terms != "wildcar*" || sp[0].IsHashtag != false || len(sp[0].InChannels) != 0 || len(sp[0].FromUsers) != 0 {
+ t.Fatalf("Incorrect output from parse search params: %v", sp[0])
+ }
}
diff --git a/model/utils.go b/model/utils.go
index 695d4a0cb..808c89e30 100644
--- a/model/utils.go
+++ b/model/utils.go
@@ -291,6 +291,7 @@ var validHashtag = regexp.MustCompile(`^(#[A-Za-zäöüÄÖÜß]+[A-Za-z0-9äö
var puncStart = regexp.MustCompile(`^[.,()&$!\?\[\]{}':;\\<>\-+=%^*|]+`)
var hashtagStart = regexp.MustCompile(`^#{2,}`)
var puncEnd = regexp.MustCompile(`[.,()&$#!\?\[\]{}':;\\<>\-+=%^*|]+$`)
+var puncEndWildcard = regexp.MustCompile(`[.,()&$#!\?\[\]{}':;\\<>\-+=%^|]+$`)
func ParseHashtags(text string) (string, string) {
words := strings.Fields(text)
diff --git a/web/react/components/admin_console/license_settings.jsx b/web/react/components/admin_console/license_settings.jsx
index fdbe912ef..d4dfa13f2 100644
--- a/web/react/components/admin_console/license_settings.jsx
+++ b/web/react/components/admin_console/license_settings.jsx
@@ -120,8 +120,7 @@ class LicenseSettings extends React.Component {
expires: Utils.displayDate(parseInt(global.window.mm_license.ExpiresAt, 10)),
ldap: global.window.mm_license.LDAP
}}
- defaultMessage='<div><p>This compiled release of Mattermost platform is provided under a <a href="http://mattermost.com" target="_blank">commercial license</a>
- from Mattermost, Inc. based on your subscription level and is subject to the <a href="{terms}" target="_blank">Terms of Service.</a></p>
+ defaultMessage='<div><p>This compiled release of Mattermost platform is provided under a <a href="http://mattermost.com" target="_blank">commercial license</a> from Mattermost, Inc. based on your subscription level and is subject to the <a href="{terms}" target="_blank">Terms of Service.</a></p>
<p>Your subscription details are as follows:</p>
Name: {name}<br />
Company or organization name: {company}<br/>
@@ -152,9 +151,7 @@ class LicenseSettings extends React.Component {
<p className='help-text'>
<FormattedHTMLMessage
id='admin.licence.keyMigration'
- defaultMessage='If you’re migrating servers you may need to remove your license key from this server in order to install it on a new server. To start,
- <a href="http://mattermost.com" target="_blank">disable all Enterprise Edition features on this server</a>.
- This will enable the ability to remove the license key and downgrade this server from Enterprise Edition to Team Edition.'
+ defaultMessage='If you’re migrating servers you may need to remove your license key from this server in order to install it on a new server. To start, <a href="http://mattermost.com" target="_blank">disable all Enterprise Edition features on this server</a>. This will enable the ability to remove the license key and downgrade this server from Enterprise Edition to Team Edition.'
/>
</p>
</div>
diff --git a/web/react/components/channel_members_modal.jsx b/web/react/components/channel_members_modal.jsx
index 688ab7dd2..3ec93a616 100644
--- a/web/react/components/channel_members_modal.jsx
+++ b/web/react/components/channel_members_modal.jsx
@@ -44,6 +44,7 @@ export default class ChannelMembersModal extends React.Component {
}
getStateFromStores() {
const extraInfo = ChannelStore.getCurrentExtraInfo();
+ const profiles = UserStore.getActiveOnlyProfiles();
if (extraInfo.member_count !== extraInfo.members.length) {
AsyncClient.getChannelExtraInfo(this.props.channel.id, -1);
@@ -53,9 +54,8 @@ export default class ChannelMembersModal extends React.Component {
};
}
- // clone the member list since we mutate it later on
const memberList = extraInfo.members.map((member) => {
- return Object.assign({}, member);
+ return profiles[member.id];
});
function compareByUsername(a, b) {
@@ -130,8 +130,8 @@ export default class ChannelMembersModal extends React.Component {
onClick={this.handleRemove.bind(this, user)}
>
<FormattedMessage
- id='channel_members_modal.removeMember'
- defaultMessage='Remove Member'
+ id='channel_members_modal.remove'
+ defaultMessage='Remove'
/>
</button>
);
diff --git a/web/react/components/create_post.jsx b/web/react/components/create_post.jsx
index 9d7a19554..62319b1a7 100644
--- a/web/react/components/create_post.jsx
+++ b/web/react/components/create_post.jsx
@@ -130,7 +130,7 @@ class CreatePost extends React.Component {
post.message,
false,
(data) => {
- PostStore.storeDraft(data.channel_id, null);
+ PostStore.storeDraft(this.state.channelId, null);
this.setState({messageText: '', submitting: false, postError: null, previews: [], serverError: null});
if (data.goto_location && data.goto_location.length > 0) {
@@ -262,9 +262,7 @@ class CreatePost extends React.Component {
message = err.message;
}
- if (clientId === -1) {
- this.setState({serverError: message});
- } else {
+ if (clientId !== -1) {
const draft = PostStore.getDraft(this.state.channelId);
const index = draft.uploadsInProgress.indexOf(clientId);
@@ -274,8 +272,10 @@ class CreatePost extends React.Component {
PostStore.storeDraft(this.state.channelId, draft);
- this.setState({uploadsInProgress: draft.uploadsInProgress, serverError: message});
+ this.setState({uploadsInProgress: draft.uploadsInProgress});
}
+
+ this.setState({serverError: message});
}
removePreview(id) {
const previews = Object.assign([], this.state.previews);
diff --git a/web/react/components/file_attachment.jsx b/web/react/components/file_attachment.jsx
index 810f90b13..6aeae638f 100644
--- a/web/react/components/file_attachment.jsx
+++ b/web/react/components/file_attachment.jsx
@@ -19,12 +19,10 @@ class FileAttachment extends React.Component {
super(props);
this.loadFiles = this.loadFiles.bind(this);
- this.playGif = this.playGif.bind(this);
- this.stopGif = this.stopGif.bind(this);
this.addBackgroundImage = this.addBackgroundImage.bind(this);
this.canSetState = false;
- this.state = {fileSize: -1, mime: '', playing: false, loading: false, format: ''};
+ this.state = {fileSize: -1};
}
componentDidMount() {
this.loadFiles();
@@ -95,42 +93,6 @@ class FileAttachment extends React.Component {
return true;
}
- playGif(e, filename) {
- var img = new Image();
- var fileUrl = utils.getFileUrl(filename);
-
- this.setState({loading: true});
- img.load(fileUrl);
- img.onload = () => {
- var state = {playing: true, loading: false};
-
- switch (true) {
- case img.width > img.height:
- state.format = 'landscape';
- break;
- case img.height > img.width:
- state.format = 'portrait';
- break;
- default:
- state.format = 'quadrat';
- break;
- }
-
- this.setState(state);
-
- // keep displaying background image for a short moment while browser is
- // loading gif, to prevent white background flashing through
- setTimeout(() => this.removeBackgroundImage.bind(this)(filename), 100);
- };
- img.onError = () => this.setState({loading: false});
-
- e.stopPropagation();
- }
- stopGif(e, filename) {
- this.setState({playing: false});
- this.addBackgroundImage(filename);
- e.stopPropagation();
- }
getFileInfoFromName(name) {
var fileInfo = utils.splitFileLocation(name);
@@ -164,74 +126,18 @@ class FileAttachment extends React.Component {
var filename = this.props.filename;
var fileInfo = utils.splitFileLocation(filename);
- var fileUrl = utils.getFileUrl(filename);
+ var fileUrl = utils.getFileUrl(filename, true);
var type = utils.getFileType(fileInfo.ext);
- var playbackControls = '';
- var loadedFile = '';
- var loadingIndicator = '';
- if (this.state.mime === 'image/gif') {
- playbackControls = (
- <div
- className='file-playback-controls play'
- onClick={(e) => this.playGif(e, filename)}
- >
- {"►"}
- </div>
- );
- }
- if (this.state.playing) {
- loadedFile = (
- <img
- className={'file__loaded ' + this.state.format}
- src={fileUrl}
- />
- );
- playbackControls = (
+ var thumbnail;
+ if (type === 'image') {
+ thumbnail = (
<div
- className='file-playback-controls stop'
- onClick={(e) => this.stopGif(e, filename)}
- >
- {"■"}
- </div>
- );
- }
- if (this.state.loading) {
- loadingIndicator = (
- <img
- className='spinner file__loading'
- src='/static/images/load.gif'
+ ref={filename}
+ className='post__load'
+ style={{backgroundImage: 'url(/static/images/load.gif)'}}
/>
);
- playbackControls = '';
- }
-
- var thumbnail;
- if (type === 'image') {
- if (this.state.playing) {
- thumbnail = (
- <div
- ref={filename}
- className='post__load'
- style={{backgroundImage: 'url(/static/images/load.gif)'}}
- >
- {playbackControls}
- {loadedFile}
- </div>
- );
- } else {
- thumbnail = (
- <div
- ref={filename}
- className='post__load'
- style={{backgroundImage: 'url(/static/images/load.gif)'}}
- >
- {loadingIndicator}
- {playbackControls}
- {loadedFile}
- </div>
- );
- }
} else {
thumbnail = <div className={'file-icon ' + utils.getIconClassName(type)}/>;
}
@@ -242,7 +148,7 @@ class FileAttachment extends React.Component {
filename,
function success(data) {
if (this.canSetState) {
- this.setState({fileSize: parseInt(data.size, 10), mime: data.mime});
+ this.setState({fileSize: parseInt(data.size, 10)});
}
}.bind(this),
function error() {
diff --git a/web/react/components/file_upload.jsx b/web/react/components/file_upload.jsx
index cb8ede51b..f8965e13e 100644
--- a/web/react/components/file_upload.jsx
+++ b/web/react/components/file_upload.jsx
@@ -108,12 +108,12 @@ class FileUpload extends React.Component {
}
}
- handleChange() {
- var element = $(ReactDOM.findDOMNode(this.refs.fileInput));
+ handleChange(e) {
+ if (e.target.files.length > 0) {
+ this.uploadFiles(e.target.files);
- this.uploadFiles(element.prop('files'));
-
- Utils.clearFileInput(element[0]);
+ Utils.clearFileInput(e.target);
+ }
}
handleDrop(e) {
diff --git a/web/react/components/get_link_modal.jsx b/web/react/components/get_link_modal.jsx
index 6a5c3b588..3309d690c 100644
--- a/web/react/components/get_link_modal.jsx
+++ b/web/react/components/get_link_modal.jsx
@@ -41,8 +41,6 @@ export default class GetLinkModal extends React.Component {
}
render() {
- const userCreationEnabled = global.window.mm_config.EnableUserCreation === 'true';
-
let helpText = null;
if (this.props.helpText) {
helpText = (
@@ -55,7 +53,7 @@ export default class GetLinkModal extends React.Component {
}
let copyLink = null;
- if (userCreationEnabled && document.queryCommandSupported('copy')) {
+ if (document.queryCommandSupported('copy')) {
copyLink = (
<button
data-copy-btn='true'
@@ -71,17 +69,14 @@ export default class GetLinkModal extends React.Component {
);
}
- let linkText = null;
- if (userCreationEnabled) {
- linkText = (
- <textarea
- className='form-control no-resize min-height'
- readOnly='true'
- ref='textarea'
- value={this.props.link}
- />
- );
- }
+ const linkText = (
+ <textarea
+ className='form-control no-resize min-height'
+ readOnly='true'
+ ref='textarea'
+ value={this.props.link}
+ />
+ );
var copyLinkConfirm = null;
if (this.state.copiedLink) {
diff --git a/web/react/components/get_team_invite_link_modal.jsx b/web/react/components/get_team_invite_link_modal.jsx
index 299729250..ba6164dbf 100644
--- a/web/react/components/get_team_invite_link_modal.jsx
+++ b/web/react/components/get_team_invite_link_modal.jsx
@@ -15,7 +15,7 @@ const holders = defineMessages({
},
help: {
id: 'get_team_invite_link_modal.help',
- defaultMessage: 'Send teammates the link below for them to sign-up to this team site.'
+ defaultMessage: 'Send teammates the link below for them to sign-up to this team site. The Team Invite Link can be shared with multiple teammates as it does not change unless it\'s regenerated in Team Settings by a Team Admin.'
},
helpDisabled: {
id: 'get_team_invite_link_modal.helpDisabled',
@@ -73,4 +73,4 @@ GetTeamInviteLinkModal.propTypes = {
intl: intlShape.isRequired
};
-export default injectIntl(GetTeamInviteLinkModal); \ No newline at end of file
+export default injectIntl(GetTeamInviteLinkModal);
diff --git a/web/react/components/invite_member_modal.jsx b/web/react/components/invite_member_modal.jsx
index 0c0330c40..184ba1357 100644
--- a/web/react/components/invite_member_modal.jsx
+++ b/web/react/components/invite_member_modal.jsx
@@ -495,7 +495,7 @@ class InviteMemberModal extends React.Component {
<ConfirmModal
title={formatMessage(holders.modalTitle)}
message={formatMessage(holders.modalMessage)}
- confirm_button={formatMessage(holders.modalButton)}
+ confirmButton={formatMessage(holders.modalButton)}
show={this.state.showConfirmModal}
onConfirm={this.handleHide.bind(this, false)}
onCancel={() => this.setState({showConfirmModal: false})}
@@ -512,4 +512,4 @@ InviteMemberModal.propTypes = {
intl: intlShape.isRequired
};
-export default injectIntl(InviteMemberModal); \ No newline at end of file
+export default injectIntl(InviteMemberModal);
diff --git a/web/react/components/navbar_dropdown.jsx b/web/react/components/navbar_dropdown.jsx
index e9df03c33..0ddd6ff4f 100644
--- a/web/react/components/navbar_dropdown.jsx
+++ b/web/react/components/navbar_dropdown.jsx
@@ -107,7 +107,7 @@ export default class NavbarDropdown extends React.Component {
</li>
);
- if (this.props.teamType === Constants.OPEN_TEAM) {
+ if (this.props.teamType === Constants.OPEN_TEAM && global.window.mm_config.EnableUserCreation === 'true') {
teamLink = (
<li>
<a
diff --git a/web/react/components/suggestion/search_suggestion_list.jsx b/web/react/components/suggestion/search_suggestion_list.jsx
index 40f5d8777..60a5562fa 100644
--- a/web/react/components/suggestion/search_suggestion_list.jsx
+++ b/web/react/components/suggestion/search_suggestion_list.jsx
@@ -30,7 +30,7 @@ export default class SearchSuggestionList extends SuggestionList {
text = (
<FormattedMessage
id='suggestion.search.private'
- defaultMessage='Public Groups'
+ defaultMessage='Private Groups'
/>
);
}
diff --git a/web/react/components/textbox.jsx b/web/react/components/textbox.jsx
index 23ecfb57b..c119abcbc 100644
--- a/web/react/components/textbox.jsx
+++ b/web/react/components/textbox.jsx
@@ -129,12 +129,12 @@ export default class Textbox extends React.Component {
}
render() {
+ const hasText = this.props.messageText.length > 0;
+
let previewLink = null;
if (Utils.isFeatureEnabled(PreReleaseFeatures.MARKDOWN_PREVIEW)) {
- const previewLinkVisible = this.props.messageText.length > 0;
previewLink = (
<a
- style={{visibility: previewLinkVisible ? 'visible' : 'hidden'}}
onClick={this.showPreview}
className='textbox-preview-link'
>
@@ -153,6 +153,51 @@ export default class Textbox extends React.Component {
);
}
+ let helpText = (
+ <div
+ style={{visibility: hasText ? 'visible' : 'hidden', opacity: hasText ? '1' : '0'}}
+ className='help_format_text'
+ >
+ <b>
+ <FormattedMessage
+ id='textbox.bold'
+ defaultMessage='**bold**'
+ />
+ </b>
+ <i>
+ <FormattedMessage
+ id='textbox.italic'
+ defaultMessage='_italic_'
+ />
+ </i>
+ <span>~~<strike>
+ <FormattedMessage
+ id='textbox.strike'
+ defaultMessage='strike'
+ />
+ </strike>~~ </span>
+ <code>
+ <FormattedMessage
+ id='textbox.inlinecode'
+ defaultMessage='`inline code`'
+ />
+ </code>
+ <code>
+ <FormattedMessage
+ id='textbox.preformatted'
+ defaultMessage='```preformatted```'
+ />
+ </code>
+ <span>
+ <FormattedMessage
+ id='textbox.quote'
+ defaultMessage='>quote'
+ />
+ </span>
+ {previewLink}
+ </div>
+ );
+
return (
<div
ref='wrapper'
@@ -184,7 +229,7 @@ export default class Textbox extends React.Component {
dangerouslySetInnerHTML={{__html: this.state.preview ? TextFormatting.formatText(this.props.messageText) : ''}}
>
</div>
- {previewLink}
+ {helpText}
<a
target='_blank'
href='http://docs.mattermost.com/help/getting-started/messaging-basics.html'
diff --git a/web/react/components/user_list_row.jsx b/web/react/components/user_list_row.jsx
index 68b723f35..d8442e770 100644
--- a/web/react/components/user_list_row.jsx
+++ b/web/react/components/user_list_row.jsx
@@ -10,9 +10,9 @@ export default function UserListRow({user, actions}) {
let name = user.username;
if (user.nickname && nameFormat === Constants.Preferences.DISPLAY_PREFER_NICKNAME) {
- name = `${user.nickname} (${user.username})`;
+ name = `${user.nickname} (@${user.username})`;
} else if ((user.first_name || user.last_name) && (nameFormat === Constants.Preferences.DISPLAY_PREFER_NICKNAME || nameFormat === Constants.Preferences.DISPLAY_PREFER_FULL_NAME)) {
- name = `${Utils.getFullName(user)} (${user.username})`;
+ name = `${Utils.getFullName(user)} (@${user.username})`;
}
const buttons = actions.map((Action, index) => {
diff --git a/web/react/components/user_settings/user_settings_modal.jsx b/web/react/components/user_settings/user_settings_modal.jsx
index 80d03d88e..fa3415988 100644
--- a/web/react/components/user_settings/user_settings_modal.jsx
+++ b/web/react/components/user_settings/user_settings_modal.jsx
@@ -309,7 +309,7 @@ class UserSettingsModal extends React.Component {
<ConfirmModal
title={formatMessage(holders.confirmTitle)}
message={formatMessage(holders.confirmMsg)}
- confirm_button={formatMessage(holders.confirmBtns)}
+ confirmButton={formatMessage(holders.confirmBtns)}
show={this.state.showConfirmModal}
onConfirm={this.handleConfirm}
onCancel={this.handleCancelConfirmation}
diff --git a/web/react/utils/text_formatting.jsx b/web/react/utils/text_formatting.jsx
index dae2252a6..a930e9ece 100644
--- a/web/react/utils/text_formatting.jsx
+++ b/web/react/utils/text_formatting.jsx
@@ -123,14 +123,13 @@ function autolinkAtMentions(text, tokens) {
return (Constants.SPECIAL_MENTIONS.indexOf(u) !== -1 || UserStore.getProfileByUsername(u));
}
- function addToken(username, mention, extraText) {
+ function addToken(username, mention) {
const index = tokens.size;
const alias = `MM_ATMENTION${index}`;
tokens.set(alias, {
value: `<a class='mention-link' href='#' data-mention='${username}'>${mention}</a>`,
- originalText: mention,
- extraText
+ originalText: mention
});
return alias;
}
@@ -152,9 +151,9 @@ function autolinkAtMentions(text, tokens) {
usernameLower = usernameLower.substring(0, c - 1);
if (mentionExists(usernameLower)) {
- const extraText = originalUsername.substr(c - 1);
- const alias = addToken(usernameLower, '@' + usernameLower, extraText);
- return alias;
+ const suffix = originalUsername.substr(c - 1);
+ const alias = addToken(usernameLower, '@' + usernameLower);
+ return alias + suffix;
}
} else {
// If the last character is not punctuation, no point in going any further
@@ -188,7 +187,7 @@ function highlightCurrentMentions(text, tokens) {
const newAlias = `MM_SELFMENTION${index}`;
newTokens.set(newAlias, {
- value: `<span class='mention-highlight'>${alias}</span>` + (token.extraText || ''),
+ value: `<span class='mention-highlight'>${alias}</span>`,
originalText: token.originalText
});
output = output.replace(alias, newAlias);
diff --git a/web/sass-files/sass/partials/_post.scss b/web/sass-files/sass/partials/_post.scss
index 4478b3f15..a667a851c 100644
--- a/web/sass-files/sass/partials/_post.scss
+++ b/web/sass-files/sass/partials/_post.scss
@@ -58,22 +58,38 @@ body.ios {
box-shadow: none;
white-space: normal;
}
- .textbox-preview-link, .textbox-help-link {
+ .textbox-help-link {
position: absolute;
z-index: 3;
bottom: -23px;
font-size: 13px;
cursor: pointer;
}
- .textbox-preview-link {
- right: 45px;
- }
.textbox-help-link {
right: 0;
}
min-height:36px;
}
+.help_format_text {
+ position: absolute;
+ z-index: 3;
+ bottom: -23px;
+ font-size: 0.7em;
+ right: 45px;
+ color: #999;
+ transition: visibility 0s, opacity 0.5s linear;
+
+ b, i, code {
+ margin-right: 3px;
+ }
+ .textbox-preview-link{
+ font-size: 13px;
+ cursor: pointer;
+ margin-left: 15px;
+ }
+}
+
.date-separator, .new-separator {
text-align: center;
height: 2em;
diff --git a/web/static/i18n/en.json b/web/static/i18n/en.json
index 7c6a71259..6915f7d26 100644
--- a/web/static/i18n/en.json
+++ b/web/static/i18n/en.json
@@ -190,10 +190,10 @@
"admin.ldap.uernameAttrDesc": "The attribute in the LDAP server that will be used to populate the username field in Mattermost. This may be the same as the ID Attribute.",
"admin.ldap.usernameAttrEx": "Ex \"sAMAccountName\"",
"admin.ldap.usernameAttrTitle": "Username Attribute:",
- "admin.licence.keyMigration": "If you’re migrating servers you may need to remove your license key from this server in order to install it on a new server. To start,<a href=\"http://mattermost.com\" target=\"_blank\">disable all Enterprise Edition features on this server</a>.This will enable the ability to remove the license key and downgrade this server from Enterprise Edition to Team Edition.",
+ "admin.licence.keyMigration": "If you’re migrating servers you may need to remove your license key from this server in order to install it on a new server. To start, <a href=\"http://mattermost.com\" target=\"_blank\">disable all Enterprise Edition features on this server</a>. This will enable the ability to remove the license key and downgrade this server from Enterprise Edition to Team Edition.",
"admin.license.edition": "Edition: ",
"admin.license.enterpriseEdition": "Mattermost Enterprise Edition. Designed for enterprise-scale communication.",
- "admin.license.enterpriseType": "<div><p>This compiled release of Mattermost platform is provided under a <a href=\"http://mattermost.com\" target=\"_blank\">commercial license</a>from Mattermost, Inc. based on your subscription level and is subject to the <a href=\"{terms}\" target=\"_blank\">Terms of Service.</a></p><p>Your subscription details are as follows:</p>Name: {name}<br />Company or organization name: {company}<br/>Number of users: {users}<br/>License issued: {issued}<br/>Start date of license: {start}<br/>Expiry date of license: {expires}<br/>LDAP: {ldap}<br/></div>",
+ "admin.license.enterpriseType": "<div><p>This compiled release of Mattermost platform is provided under a <a href=\"http://mattermost.com\" target=\"_blank\">commercial license</a> from Mattermost, Inc. based on your subscription level and is subject to the <a href=\"{terms}\" target=\"_blank\">Terms of Service.</a></p><p>Your subscription details are as follows:</p>Name: {name}<br />Company or organization name: {company}<br/>Number of users: {users}<br/>License issued: {issued}<br/>Start date of license: {start}<br/>Expiry date of license: {expires}<br/>LDAP: {ldap}<br/></div>",
"admin.license.key": "License Key: ",
"admin.license.keyRemove": "Remove Enterprise License and Downgrade Server",
"admin.license.removing": "Removing License...",
@@ -277,8 +277,8 @@
"admin.service.attemptTitle": "Maximum Login Attempts:",
"admin.service.cmdsDesc": "When true, user created slash commands will be allowed.",
"admin.service.cmdsTitle": "Enable Slash Commands: ",
- "admin.service.corsEx": "http://example.com https://example.com",
"admin.service.corsDescription": "Enable HTTP Cross origin request from specific domains (separate by a spacebar). Use \"*\" if you want to allow CORS from any domain or leave it blank to disable it.",
+ "admin.service.corsEx": "http://example.com https://example.com",
"admin.service.corsTitle": "Allow Cross-origin Requests from:",
"admin.service.developerDesc": "(Developer Option) When true, extra information around errors will be displayed in the UI.",
"admin.service.developerTitle": "Enable Developer Mode: ",
@@ -561,7 +561,7 @@
"channel_loader.wrote": " wrote: ",
"channel_members_modal.addNew": " Add New Members",
"channel_members_modal.close": "Close",
- "channel_members_modal.removeMember": "Remove Member",
+ "channel_members_modal.remove": "Remove",
"channel_memebers_modal.members": " Members",
"channel_modal.cancel": "Cancel",
"channel_modal.channel": "Channel",
@@ -702,7 +702,7 @@
"get_link.copy": "Copy Link",
"get_post_link_modal.help": "The link below allows authorized users to see your post.",
"get_post_link_modal.title": "Copy Permalink",
- "get_team_invite_link_modal.help": "Send teammates the link below for them to sign-up to this team site.",
+ "get_team_invite_link_modal.help": "Send teammates the link below for them to sign-up to this team site. The Team Invite Link can be shared with multiple teammates as it does not change unless it's regenerated in Team Settings by a Team Admin.",
"get_team_invite_link_modal.helpDisabled": "User creation has been disabled for your team. Please ask your team administrator for details.",
"get_team_invite_link_modal.title": "Team Invite Link",
"intro_messages.DM": "This is the start of your direct message history with {teammate}.<br />Direct messages and files shared here are not shown to people outside this area.",
@@ -966,7 +966,7 @@
"sso_signup.team_error": "Please enter a team name",
"suggestion.mention.all": "Notifies everyone in the team",
"suggestion.mention.channel": "Notifies everyone in the channel",
- "suggestion.search.private": "Public Groups",
+ "suggestion.search.private": "Private Groups",
"suggestion.search.public": "Public Channels",
"team_export_tab.download": "download",
"team_export_tab.export": "Export",
@@ -1054,9 +1054,15 @@
"team_signup_welcome.validEmailError": "Please enter a valid email address",
"team_signup_welcome.welcome": "Welcome to:",
"team_signup_welcome.yes": "Yes, this address is correct",
+ "textbox.bold": "**bold**",
"textbox.edit": "Edit message",
"textbox.help": "Help",
+ "textbox.inlinecode": "`inline code`",
+ "textbox.italic": "_italic_",
+ "textbox.preformatted": "```preformatted```",
"textbox.preview": "Preview",
+ "textbox.quote": ">quote",
+ "textbox.strike": "strike",
"tutorial_intro.allSet": "You’re all set",
"tutorial_intro.end": "Click “Next” to enter Town Square. This is the first channel teammates see when they sign up. Use it for posting updates everyone needs to know.",
"tutorial_intro.invite": "Invite teammates",
diff --git a/web/static/i18n/es.json b/web/static/i18n/es.json
index dc012df14..091b1e846 100644
--- a/web/static/i18n/es.json
+++ b/web/static/i18n/es.json
@@ -190,7 +190,7 @@
"admin.ldap.uernameAttrDesc": "El atributo en el servidor LDAP que se utilizará para poblar el nombre de usuario en Mattermost. Este puede ser igual al Attributo Id.",
"admin.ldap.usernameAttrEx": "Ej \"sAMAccountName\"",
"admin.ldap.usernameAttrTitle": "Atributo Usuario:",
- "admin.licence.keyMigration": "Si estás migrando servidores es posible que necesites remover tu licencia de este servidor para poder instalarlo en un servidor nuevo. Para empezar,<a href=\"http://mattermost.com\" target=\"_blank\">deshabilita todas las características de la Edición Enterprise de este servidor</a>.Esta operación habilitará la opción para remover la licencia y degradar este servidor de la Edición Enterprise a la Edición Team.",
+ "admin.licence.keyMigration": "Si estás migrando servidores es posible que necesites remover tu licencia de este servidor para poder instalarlo en un servidor nuevo. Para empezar, <a href=\"http://mattermost.com\" target=\"_blank\">deshabilita todas las características de la Edición Enterprise de este servidor</a>. Esta operación habilitará la opción para remover la licencia y degradar este servidor de la Edición Enterprise a la Edición Team.",
"admin.license.edition": "Edición: ",
"admin.license.enterpriseEdition": "Mattermost Edición Enterprise. Diseñada para comunicación de escala empresarial.",
"admin.license.enterpriseType": "<div><p>Esta versión compilada de la plataforma de Mattermost es provista bajo una <a href=\"http://mattermost.com\" target=\"_blank\">licencia comercial</a> de Mattermost, Inc. en función en su nivel de subscripción y bajo los <a href=\"{terms}\" target=\"_blank\">Términos del Servicio.</a></p><p>Los detalles de tu subscripción son los siguientes:</p>Nombre: {name}<br />Nombre compañía u organización: {company}<br/>Cantidad de usuarios: {users}<br/>Licencia emitida: {issued}<br/>Fecha de inicio: {start}<br/>Fecha de expiración: {expires}<br/>LDAP: {ldap}<br/></div>",
@@ -277,8 +277,8 @@
"admin.service.attemptTitle": "Máximo de intentos de conexión:",
"admin.service.cmdsDesc": "Cuando es verdadero, se permite la creación de comandos de barra por usuarios.",
"admin.service.cmdsTitle": "Habilitar Comandos de Barra: ",
- "admin.service.corsEx": "http://ejemplo.com https://ejemplo.com",
"admin.service.corsDescription": "Habilita las solicitudes HTTP de origen cruzado para dominios en específico (separados por un espacio). Utiliza \"*\" si quieres habilitar CORS desde cualquier dominio o deja el campo en blanco para deshabilitarlo.",
+ "admin.service.corsEx": "http://ejemplo.com https://ejemplo.com",
"admin.service.corsTitle": "Permitir Solicitudes de Origen Cruzado desde:",
"admin.service.developerDesc": "(Opción de Desarrollador) Cuando está asignado en verdadero, información extra sobre errores se muestra en el UI.",
"admin.service.developerTitle": "Habilitar modo de Desarrollador: ",
@@ -561,7 +561,6 @@
"channel_loader.wrote": " escribió: ",
"channel_members_modal.addNew": " Agregar nuevos Miembros",
"channel_members_modal.close": "Cerrar",
- "channel_members_modal.removeMember": "Elminar Miembro",
"channel_memebers_modal.members": " Miembros",
"channel_modal.cancel": "Cancelar",
"channel_modal.channel": "Canal",
@@ -702,7 +701,7 @@
"get_link.copy": "Copiar Enlace",
"get_post_link_modal.help": "En enlace de abajo permite a los usuarios autorizados a ver tu mensaje.",
"get_post_link_modal.title": "Copiar enlace Permanente",
- "get_team_invite_link_modal.help": "Enviar a los compañeros de equipo el enlace que se muestra a continuación para permitirles registrarse a este equipo.",
+ "get_team_invite_link_modal.help": "Envía el siguiente enlace a tus compañeros para que se registren a este equipo. El enlace de invitación al equipo puede ser compartido con multiples compañeros y el mismo no cambiará a menos que sea regenerado en la Configuración del Equipo por un Administrador del Equipo.",
"get_team_invite_link_modal.helpDisabled": "La creación de usuario ha sido deshabilitada para tu equipo. Por favor solicita más detalles a tu administrador de equipo.",
"get_team_invite_link_modal.title": "Enlace de Invitación al Equipo",
"intro_messages.DM": "Este es el inicio de tu historial de mensajes directos con {teammate}.<br />Los mensajes directos y archivos que se comparten aquí no son mostrados a personas fuera de esta área.",
@@ -983,18 +982,18 @@
"team_import_tab.summary": "Ver Resumen",
"team_member_modal.close": "Cerrar",
"team_member_modal.members": "{team} Miembros",
- "team_members_modal.confirmDemoteDescription": "Si te degradas a ti mismo de la función de Administrador de Sistema y no hay otro usuario con privilegios de Administrador de Sistema, tendrás que volver a asignar un Administrador del Sistema accediendo al servidor de Mattermost a través de un terminal y ejecutar el siguiente comando.",
- "team_members_modal.confirmDemoteRoleTitle": "Confirmar el decenso del rol de Administrador de Sistema",
- "team_members_modal.confirmDemotion": "Confirmar decenso",
- "team_members_modal.confirmDemotionCmd": "platform -assign_role -team_name=\"tuequipo\" -email=\"nombre@tuempresa.com\" -role=\"system_admin\"",
- "team_members_modal.inactive": "Inactivo",
- "team_members_modal.makeActive": "Activar",
- "team_members_modal.makeAdmin": "Convertir a Admin de Equipo",
- "team_members_modal.makeInactive": "Desactivar",
- "team_members_modal.makeMember": "Convertir en Miembro",
- "team_members_modal.member": "Miembro",
- "team_members_modal.systemAdmin": "Administrador de Sistema",
- "team_members_modal.teamAdmin": "Admin de Equipo",
+ "team_members_dropdown.confirmDemoteDescription": "Si te degradas a ti mismo de la función de Administrador de Sistema y no hay otro usuario con privilegios de Administrador de Sistema, tendrás que volver a asignar un Administrador del Sistema accediendo al servidor de Mattermost a través de un terminal y ejecutar el siguiente comando.",
+ "team_members_dropdown.confirmDemoteRoleTitle": "Confirmar el decenso del rol de Administrador de Sistema",
+ "team_members_dropdown.confirmDemotion": "Confirmar decenso",
+ "team_members_dropdown.confirmDemotionCmd": "platform -assign_role -team_name=\"tuequipo\" -email=\"nombre@tuempresa.com\" -role=\"system_admin\"",
+ "team_members_dropdown.inactive": "Inactivo",
+ "team_members_dropdown.makeActive": "Activar",
+ "team_members_dropdown.makeAdmin": "Hacer Admin de Equipo",
+ "team_members_dropdown.makeInactive": "Inactivar",
+ "team_members_dropdown.makeMember": "Hacer Miembro",
+ "team_members_dropdown.member": "Miembro",
+ "team_members_dropdown.systemAdmin": "Admin del Sistema",
+ "team_members_dropdown.teamAdmin": "Admin del Equipo",
"team_settings_modal.exportTab": "Exportar",
"team_settings_modal.generalTab": "General",
"team_settings_modal.importTab": "Importar",
diff --git a/web/static/i18n/pt.json b/web/static/i18n/pt.json
index ef5b9a2ab..99ef71b35 100644
--- a/web/static/i18n/pt.json
+++ b/web/static/i18n/pt.json
@@ -21,33 +21,6 @@
"activity_log_modal.android": "Android",
"activity_log_modal.androidNativeApp": "App Nativo Android",
"activity_log_modal.iphoneNativeApp": "App Nativo para iPhone",
- "analytics.chart.loading": "Carregando...",
- "analytics.chart.meaningful": "Não há dados suficientes para uma representação significativa.",
- "analytics.system.activeUsers": "Usuários Ativos Com Posts",
- "analytics.system.channelTypes": "Tipos de Canal",
- "analytics.system.postTypes": "Posts, Arquivos e Hashtags",
- "analytics.system.privateGroups": "Grupos Privados",
- "analytics.system.publicChannels": "Canais Públicos",
- "analytics.system.textPosts": "Post com Texto somente",
- "analytics.system.title": "Estatísticas do Sistema",
- "analytics.system.totalFilePosts": "Posts com Arquivos",
- "analytics.system.totalHashtagPosts": "Posts com Hashtags",
- "analytics.system.totalIncomingWebhooks": "Webhooks Entrada",
- "analytics.system.totalOutgoingWebhooks": "Webhooks Saída",
- "analytics.system.totalCommands": "Total de Comandos",
- "analytics.system.totalSessions": "Total de Sessões",
- "analytics.system.totalPosts": "Total Posts",
- "analytics.system.totalUsers": "Total de Usuários",
- "analytics.system.totalTeams": "Total de Equipes",
- "analytics.system.totalChannels": "Total de Canais",
- "analytics.team.activeUsers": "Usuários Ativos Com Posts",
- "analytics.team.recentActive": "Usuários Ativos Recentes",
- "analytics.team.newlyCreated": "Novos Usuários Criados",
- "analytics.team.privateGroups": "Grupos Privados",
- "analytics.team.publicChannels": "Canais Públicos",
- "analytics.team.title": "Estatísticas de Equipe para {team}",
- "analytics.team.totalPosts": "Total Posts",
- "analytics.team.totalUsers": "Total de Usuários",
"admin.audits.reload": "Recarregar",
"admin.audits.title": "Atividade de Usuário",
"admin.email.allowEmailSignInDescription": "Quando verdadeiro, Mattermost permite aos usuários fazer login usando o e-mail e senha.",
@@ -217,10 +190,10 @@
"admin.ldap.uernameAttrDesc": "O atributo no servidor LDAP que será usado para preencher o campo nome de usuário no Mattermost. Este pode ser o mesmo que o Atributo ID.",
"admin.ldap.usernameAttrEx": "Ex \"sAMAccountName\"",
"admin.ldap.usernameAttrTitle": "Atributo do Usuário:",
- "admin.licence.keyMigration": "Se você estiver migrando seu servidor você pode precisar remover sua chave da licença deste servidor a pedido para instala-la em um novo servidor. Para iniciar,<a href=\"http://mattermost.com\" target=\"_blank\">desativar todos os recursos Enterprise Edition deste servidor</a>.Isto irá habilitar para remover a chave da licença e fazer downgrade deste servidor Enterprise Edition para Team Edition.",
+ "admin.licence.keyMigration": "Se você estiver migrando seu servidor você pode precisar remover sua chave da licença deste servidor a pedido para instala-la em um novo servidor. Para iniciar, <a href=\"http://mattermost.com\" target=\"_blank\">desativar todos os recursos Enterprise Edition deste servidor</a>. Isto irá habilitar para remover a chave da licença e fazer downgrade deste servidor Enterprise Edition para Team Edition.",
"admin.license.edition": "Edição: ",
"admin.license.enterpriseEdition": "Mattermost Enterprise Edition. Desenvolvido para escala empresarial de comunicação.",
- "admin.license.enterpriseType": "<div><p>Esta versão compilada da plataforma Mattermost é fornecida sob a <a href=\"http://mattermost.com\" target=\"_blank\">licença comercial</a>para Mattermost, Inc. com base em seu nível de subscrição e está sujeito a <a href=\"{terms}\" target=\"_blank\">Termos de Serviço.</a></p><p>Os detalhes de sua assinatura, são como segue:</p>Nome: {name}<br />Nome da Empresa ou organização: {company}<br/>Número de usuários: {users}<br/>Licença emitida: {issued}<br/>Data de Início da licença: {start}<br/>Data de expiração da licença: {expires}<br/>LDAP: {ldap}<br/></div>",
+ "admin.license.enterpriseType": "<div><p>Esta versão compilada da plataforma Mattermost é fornecida sob a <a href=\"http://mattermost.com\" target=\"_blank\">licença comercial</a> para Mattermost, Inc. com base em seu nível de subscrição e está sujeito a <a href=\"{terms}\" target=\"_blank\">Termos de Serviço.</a></p><p>Os detalhes de sua assinatura, são como segue:</p>Nome: {name}<br />Nome da Empresa ou organização: {company}<br/>Número de usuários: {users}<br/>Licença emitida: {issued}<br/>Data de Início da licença: {start}<br/>Data de expiração da licença: {expires}<br/>LDAP: {ldap}<br/></div>",
"admin.license.key": "Chave da Licença: ",
"admin.license.keyRemove": "Remover a Licença Enterprise e fazer Downgrade do Servidor",
"admin.license.removing": "Removendo a Licença...",
@@ -451,6 +424,33 @@
"admin.user_item.resetPwd": "Resetar Senha",
"admin.user_item.sysAdmin": "Admin do Sistema",
"admin.user_item.teamAdmin": "Admin Equipe",
+ "analytics.chart.loading": "Carregando...",
+ "analytics.chart.meaningful": "Não há dados suficientes para uma representação significativa.",
+ "analytics.system.activeUsers": "Usuários Ativos Com Posts",
+ "analytics.system.channelTypes": "Tipos de Canal",
+ "analytics.system.postTypes": "Posts, Arquivos e Hashtags",
+ "analytics.system.privateGroups": "Grupos Privados",
+ "analytics.system.publicChannels": "Canais Públicos",
+ "analytics.system.textPosts": "Post com Texto somente",
+ "analytics.system.title": "Estatísticas do Sistema",
+ "analytics.system.totalChannels": "Total de Canais",
+ "analytics.system.totalCommands": "Total de Comandos",
+ "analytics.system.totalFilePosts": "Posts com Arquivos",
+ "analytics.system.totalHashtagPosts": "Posts com Hashtags",
+ "analytics.system.totalIncomingWebhooks": "Webhooks Entrada",
+ "analytics.system.totalOutgoingWebhooks": "Webhooks Saída",
+ "analytics.system.totalPosts": "Total Posts",
+ "analytics.system.totalSessions": "Total de Sessões",
+ "analytics.system.totalTeams": "Total de Equipes",
+ "analytics.system.totalUsers": "Total de Usuários",
+ "analytics.team.activeUsers": "Usuários Ativos Com Posts",
+ "analytics.team.newlyCreated": "Novos Usuários Criados",
+ "analytics.team.privateGroups": "Grupos Privados",
+ "analytics.team.publicChannels": "Canais Públicos",
+ "analytics.team.recentActive": "Usuários Ativos Recentes",
+ "analytics.team.title": "Estatísticas de Equipe para {team}",
+ "analytics.team.totalPosts": "Total Posts",
+ "analytics.team.totalUsers": "Total de Usuários",
"audit_table.accountActive": "Conta inativada",
"audit_table.accountInactive": "Conta inativada",
"audit_table.action": "Ação",
@@ -547,18 +547,17 @@
"channel_invite.add": " Adicionar",
"channel_invite.addNewMembers": "Adicionar Novo Membro para ",
"channel_invite.close": "Fechar",
+ "channel_loader.connection_error": "Parece existir um problema com a sua conexão de internet.",
"channel_loader.posted": "Postado",
"channel_loader.socketError": "Por favor verifique sua conexão, Mattermost está inalcançável. Se este problema persistir, peça ao administrador para verificar a porta WebSocket.",
"channel_loader.someone": "Alguém",
"channel_loader.something": " fez algo novo",
+ "channel_loader.unknown_error": "Recebido um código de status inesperado do servidor.",
"channel_loader.uploadedFile": " enviado um arquivo",
"channel_loader.uploadedImage": " enviado uma imagem",
"channel_loader.wrote": " escreveu: ",
- "channel_loader.connection_error": "Parece existir um problema com a sua conexão de internet.",
- "channel_loader.unknown_error": "Recebido um código de status inesperado do servidor.",
"channel_members_modal.addNew": " Adicionar Novos Membros",
"channel_members_modal.close": "Fechar",
- "channel_members_modal.removeMember": "Remover Membro",
"channel_memebers_modal.members": " Membros",
"channel_modal.cancel": "Cancelar",
"channel_modal.channel": "Canal",
@@ -699,7 +698,6 @@
"get_link.copy": "Copiar Link",
"get_post_link_modal.help": "O link abaixo permite que usuários autorizados possam ver seus posts.",
"get_post_link_modal.title": "Copiar Permalink",
- "get_team_invite_link_modal.help": "Enviar a equipe de trabalho o link abaixo para eles se inscreverem nesta equipe.",
"get_team_invite_link_modal.helpDisabled": "Criação de usuários está desabilitada para sua equipe. Por favor peça ao administrador de equipe por detalhes.",
"get_team_invite_link_modal.title": "Link para Convite de Equipe",
"intro_messages.DM": "Este é o início do seu histórico de mensagens diretas com {teammate}.<br />Mensagens diretas e arquivos compartilhados aqui não são mostrados para pessoas de fora desta área.",
@@ -962,7 +960,6 @@
"sso_signup.team_error": "Por favor entre o nome da equipe",
"suggestion.mention.all": "Notificar todo mundo na equipe",
"suggestion.mention.channel": "Notifica todos no canal",
- "suggestion.search.private": "Grupos Públicos",
"suggestion.search.public": "Canais Públicos",
"team_export_tab.download": "download",
"team_export_tab.export": "Exportar",
@@ -1050,9 +1047,15 @@
"team_signup_welcome.validEmailError": "Por favor entre um endereço de e-mail válido",
"team_signup_welcome.welcome": "Bem-vindo:",
"team_signup_welcome.yes": "Sim, este endereço de email está correto",
+ "textbox.bold": "**negrito**",
"textbox.edit": "Editar mensagem",
"textbox.help": "Ajuda",
+ "textbox.inlinecode": "`código`",
+ "textbox.italic": "_itálico_",
+ "textbox.preformatted": "```pre-formatado```",
"textbox.preview": "Pré-visualização",
+ "textbox.quote": ">citado",
+ "textbox.strike": "tachado",
"tutorial_intro.allSet": "Está tudo pronto",
"tutorial_intro.end": "Clique em “Próximo” para entrar Town Square. Este é o primeiro canal que sua equipe de trabalho vê quando eles se inscrevem. Use para postar atualizações que todos precisam saber.",
"tutorial_intro.invite": "Convidar pessoas para equipe",