mirror of
https://github.com/discourse/discourse.git
synced 2025-05-22 05:01:14 +08:00
Add ES6 support to more files
This commit is contained in:
@ -46,7 +46,6 @@
|
|||||||
"_",
|
"_",
|
||||||
"alert",
|
"alert",
|
||||||
"containsInstance",
|
"containsInstance",
|
||||||
"parseHTML",
|
|
||||||
"deepEqual",
|
"deepEqual",
|
||||||
"notEqual",
|
"notEqual",
|
||||||
"define",
|
"define",
|
||||||
|
@ -1,8 +1,9 @@
|
|||||||
import DiscourseController from 'discourse/controllers/controller';
|
import DiscourseController from 'discourse/controllers/controller';
|
||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
export default DiscourseController.extend({
|
export default DiscourseController.extend({
|
||||||
|
|
||||||
filterEmailLogs: Discourse.debounce(function() {
|
filterEmailLogs: debounce(function() {
|
||||||
var self = this;
|
var self = this;
|
||||||
Discourse.EmailLog.findAll(this.get("filter")).then(function(logs) {
|
Discourse.EmailLog.findAll(this.get("filter")).then(function(logs) {
|
||||||
self.set("model", logs);
|
self.set("model", logs);
|
||||||
|
@ -1,7 +1,8 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import DiscourseController from 'discourse/controllers/controller';
|
import DiscourseController from 'discourse/controllers/controller';
|
||||||
|
|
||||||
export default DiscourseController.extend({
|
export default DiscourseController.extend({
|
||||||
filterEmailLogs: Discourse.debounce(function() {
|
filterEmailLogs: debounce(function() {
|
||||||
var self = this;
|
var self = this;
|
||||||
Discourse.EmailLog.findAll(this.get("filter")).then(function(logs) {
|
Discourse.EmailLog.findAll(this.get("filter")).then(function(logs) {
|
||||||
self.set("model", logs);
|
self.set("model", logs);
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import { outputExportResult } from 'discourse/lib/export-result';
|
import { outputExportResult } from 'discourse/lib/export-result';
|
||||||
import { exportEntity } from 'discourse/lib/export-csv';
|
import { exportEntity } from 'discourse/lib/export-csv';
|
||||||
|
|
||||||
@ -6,7 +7,7 @@ export default Ember.ArrayController.extend({
|
|||||||
itemController: 'admin-log-screened-ip-address',
|
itemController: 'admin-log-screened-ip-address',
|
||||||
filter: null,
|
filter: null,
|
||||||
|
|
||||||
show: Discourse.debounce(function() {
|
show: debounce(function() {
|
||||||
var self = this;
|
var self = this;
|
||||||
self.set('loading', true);
|
self.set('loading', true);
|
||||||
Discourse.ScreenedIpAddress.findAll(this.get("filter")).then(function(result) {
|
Discourse.ScreenedIpAddress.findAll(this.get("filter")).then(function(result) {
|
||||||
|
@ -1,8 +1,10 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
export default Ember.ArrayController.extend({
|
export default Ember.ArrayController.extend({
|
||||||
loading: false,
|
loading: false,
|
||||||
filter: null,
|
filter: null,
|
||||||
|
|
||||||
show: Discourse.debounce(function() {
|
show: debounce(function() {
|
||||||
var self = this;
|
var self = this;
|
||||||
self.set('loading', true);
|
self.set('loading', true);
|
||||||
Discourse.Permalink.findAll(self.get("filter")).then(function(result) {
|
Discourse.Permalink.findAll(self.get("filter")).then(function(result) {
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import Presence from 'discourse/mixins/presence';
|
import Presence from 'discourse/mixins/presence';
|
||||||
|
|
||||||
export default Ember.ArrayController.extend(Presence, {
|
export default Ember.ArrayController.extend(Presence, {
|
||||||
@ -50,7 +51,7 @@ export default Ember.ArrayController.extend(Presence, {
|
|||||||
this.transitionToRoute("adminSiteSettingsCategory", category || "all_results");
|
this.transitionToRoute("adminSiteSettingsCategory", category || "all_results");
|
||||||
},
|
},
|
||||||
|
|
||||||
filterContent: Discourse.debounce(function() {
|
filterContent: debounce(function() {
|
||||||
if (this.get("_skipBounce")) {
|
if (this.get("_skipBounce")) {
|
||||||
this.set("_skipBounce", false);
|
this.set("_skipBounce", false);
|
||||||
} else {
|
} else {
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import { i18n } from 'discourse/lib/computed';
|
import { i18n } from 'discourse/lib/computed';
|
||||||
|
|
||||||
export default Ember.ArrayController.extend({
|
export default Ember.ArrayController.extend({
|
||||||
@ -33,7 +34,7 @@ export default Ember.ArrayController.extend({
|
|||||||
return I18n.t('admin.users.titles.' + this.get('query'));
|
return I18n.t('admin.users.titles.' + this.get('query'));
|
||||||
}.property('query'),
|
}.property('query'),
|
||||||
|
|
||||||
_filterUsers: Discourse.debounce(function() {
|
_filterUsers: debounce(function() {
|
||||||
this._refreshUsers();
|
this._refreshUsers();
|
||||||
}, 250).observes('listFilter'),
|
}, 250).observes('listFilter'),
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import { renderSpinner } from 'discourse/helpers/loading-spinner';
|
import { renderSpinner } from 'discourse/helpers/loading-spinner';
|
||||||
|
|
||||||
export default Discourse.View.extend({
|
export default Discourse.View.extend({
|
||||||
@ -9,7 +10,7 @@ export default Discourse.View.extend({
|
|||||||
this.setProperties({ formattedLogs: "", index: 0 });
|
this.setProperties({ formattedLogs: "", index: 0 });
|
||||||
},
|
},
|
||||||
|
|
||||||
_updateFormattedLogs: Discourse.debounce(function() {
|
_updateFormattedLogs: debounce(function() {
|
||||||
const logs = this.get("controller.model");
|
const logs = this.get("controller.model");
|
||||||
if (logs.length === 0) {
|
if (logs.length === 0) {
|
||||||
this._reset(); // reset the cached logs whenever the model is reset
|
this._reset(); // reset the cached logs whenever the model is reset
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default Discourse.View.extend({
|
export default Discourse.View.extend({
|
||||||
classNames: ["admin-backups"],
|
classNames: ["admin-backups"],
|
||||||
|
|
||||||
@ -12,7 +14,7 @@ export default Discourse.View.extend({
|
|||||||
$link.data("auto-route", true);
|
$link.data("auto-route", true);
|
||||||
}
|
}
|
||||||
|
|
||||||
Discourse.URL.redirectTo($link.data("href"));
|
DiscourseURL.redirectTo($link.data("href"));
|
||||||
});
|
});
|
||||||
}.on("didInsertElement"),
|
}.on("didInsertElement"),
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
import { buildCategoryPanel } from 'discourse/components/edit-category-panel';
|
import { buildCategoryPanel } from 'discourse/components/edit-category-panel';
|
||||||
import { categoryBadgeHTML } from 'discourse/helpers/category-link';
|
import { categoryBadgeHTML } from 'discourse/helpers/category-link';
|
||||||
|
|
||||||
@ -53,7 +54,7 @@ export default buildCategoryPanel('general', {
|
|||||||
|
|
||||||
actions: {
|
actions: {
|
||||||
showCategoryTopic() {
|
showCategoryTopic() {
|
||||||
Discourse.URL.routeTo(this.get('category.topic_url'));
|
DiscourseURL.routeTo(this.get('category.topic_url'));
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
const TopicCategoryComponent = Ember.Component.extend({
|
const TopicCategoryComponent = Ember.Component.extend({
|
||||||
needsSecondRow: Ember.computed.gt('secondRowItems.length', 0),
|
needsSecondRow: Ember.computed.gt('secondRowItems.length', 0),
|
||||||
secondRowItems: function() { return []; }.property(),
|
secondRowItems: function() { return []; }.property(),
|
||||||
@ -10,7 +12,7 @@ const TopicCategoryComponent = Ember.Component.extend({
|
|||||||
jumpToTopPost() {
|
jumpToTopPost() {
|
||||||
const topic = this.get('topic');
|
const topic = this.get('topic');
|
||||||
if (topic) {
|
if (topic) {
|
||||||
Discourse.URL.routeTo(topic.get('firstPostUrl'));
|
DiscourseURL.routeTo(topic.get('firstPostUrl'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
import { setting } from 'discourse/lib/computed';
|
import { setting } from 'discourse/lib/computed';
|
||||||
|
|
||||||
export default Ember.Component.extend({
|
export default Ember.Component.extend({
|
||||||
@ -26,7 +27,7 @@ export default Ember.Component.extend({
|
|||||||
|
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
|
|
||||||
Discourse.URL.routeTo('/');
|
DiscourseURL.routeTo('/');
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default Ember.Component.extend({
|
export default Ember.Component.extend({
|
||||||
tagName: 'ul',
|
tagName: 'ul',
|
||||||
classNameBindings: [':nav', ':nav-pills'],
|
classNameBindings: [':nav', ':nav-pills'],
|
||||||
@ -24,7 +26,7 @@ export default Ember.Component.extend({
|
|||||||
this.set('expanded',false);
|
this.set('expanded',false);
|
||||||
}
|
}
|
||||||
$(window).off('click.navigation-bar');
|
$(window).off('click.navigation-bar');
|
||||||
Discourse.URL.appEvents.off('dom:clean', this, this.ensureDropClosed);
|
DiscourseURL.appEvents.off('dom:clean', this, this.ensureDropClosed);
|
||||||
},
|
},
|
||||||
|
|
||||||
actions: {
|
actions: {
|
||||||
@ -33,7 +35,7 @@ export default Ember.Component.extend({
|
|||||||
var self = this;
|
var self = this;
|
||||||
if (this.get('expanded')) {
|
if (this.get('expanded')) {
|
||||||
|
|
||||||
Discourse.URL.appEvents.on('dom:clean', this, this.ensureDropClosed);
|
DiscourseURL.appEvents.on('dom:clean', this, this.ensureDropClosed);
|
||||||
|
|
||||||
Em.run.next(function() {
|
Em.run.next(function() {
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import Presence from 'discourse/mixins/presence';
|
import Presence from 'discourse/mixins/presence';
|
||||||
import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
||||||
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
// Modal related to changing the ownership of posts
|
// Modal related to changing the ownership of posts
|
||||||
export default Ember.Controller.extend(Presence, SelectedPostsCount, ModalFunctionality, {
|
export default Ember.Controller.extend(Presence, SelectedPostsCount, ModalFunctionality, {
|
||||||
@ -43,7 +44,7 @@ export default Ember.Controller.extend(Presence, SelectedPostsCount, ModalFuncti
|
|||||||
// success
|
// success
|
||||||
self.send('closeModal');
|
self.send('closeModal');
|
||||||
self.get('topicController').send('toggleMultiSelect');
|
self.get('topicController').send('toggleMultiSelect');
|
||||||
Em.run.next(function() { Discourse.URL.routeTo(result.url); });
|
Em.run.next(function() { DiscourseURL.routeTo(result.url); });
|
||||||
}, function() {
|
}, function() {
|
||||||
// failure
|
// failure
|
||||||
self.flash(I18n.t('topic.change_owner.error'), 'alert-error');
|
self.flash(I18n.t('topic.change_owner.error'), 'alert-error');
|
||||||
|
@ -1,5 +1,8 @@
|
|||||||
import { setting } from 'discourse/lib/computed';
|
import { setting } from 'discourse/lib/computed';
|
||||||
import Presence from 'discourse/mixins/presence';
|
import Presence from 'discourse/mixins/presence';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
|
import Draft from 'discourse/models/draft';
|
||||||
|
|
||||||
export default Ember.ObjectController.extend(Presence, {
|
export default Ember.ObjectController.extend(Presence, {
|
||||||
needs: ['modal', 'topic', 'composer-messages', 'application'],
|
needs: ['modal', 'topic', 'composer-messages', 'application'],
|
||||||
@ -72,7 +75,7 @@ export default Ember.ObjectController.extend(Presence, {
|
|||||||
const composer = this;
|
const composer = this;
|
||||||
|
|
||||||
return this.store.find('post', postId).then(function(post) {
|
return this.store.find('post', postId).then(function(post) {
|
||||||
const quote = Discourse.Quote.build(post, post.get("raw"), {raw: true, full: true});
|
const quote = Quote.build(post, post.get("raw"), {raw: true, full: true});
|
||||||
composer.appendBlockAtCursor(quote);
|
composer.appendBlockAtCursor(quote);
|
||||||
composer.set('model.loading', false);
|
composer.set('model.loading', false);
|
||||||
});
|
});
|
||||||
@ -262,7 +265,7 @@ export default Ember.ObjectController.extend(Presence, {
|
|||||||
if (!composer.get('replyingToTopic') || !disableJumpReply) {
|
if (!composer.get('replyingToTopic') || !disableJumpReply) {
|
||||||
const post = result.target;
|
const post = result.target;
|
||||||
if (post && !staged) {
|
if (post && !staged) {
|
||||||
Discourse.URL.routeTo(post.get('url'));
|
DiscourseURL.routeTo(post.get('url'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}).catch(function(error) {
|
}).catch(function(error) {
|
||||||
@ -278,7 +281,7 @@ export default Ember.ObjectController.extend(Presence, {
|
|||||||
Em.run.schedule('afterRender', function() {
|
Em.run.schedule('afterRender', function() {
|
||||||
if (staged && !disableJumpReply) {
|
if (staged && !disableJumpReply) {
|
||||||
const postNumber = staged.get('post_number');
|
const postNumber = staged.get('post_number');
|
||||||
Discourse.URL.jumpToPost(postNumber, { skipIfOnScreen: true });
|
DiscourseURL.jumpToPost(postNumber, { skipIfOnScreen: true });
|
||||||
self.appEvents.trigger('post:highlight', postNumber);
|
self.appEvents.trigger('post:highlight', postNumber);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
@ -415,7 +418,7 @@ export default Ember.ObjectController.extend(Presence, {
|
|||||||
|
|
||||||
// we need a draft sequence for the composer to work
|
// we need a draft sequence for the composer to work
|
||||||
if (opts.draftSequence === undefined) {
|
if (opts.draftSequence === undefined) {
|
||||||
return Discourse.Draft.get(opts.draftKey).then(function(data) {
|
return Draft.get(opts.draftKey).then(function(data) {
|
||||||
opts.draftSequence = data.draft_sequence;
|
opts.draftSequence = data.draft_sequence;
|
||||||
opts.draft = data.draft;
|
opts.draft = data.draft;
|
||||||
self._setModel(composerModel, opts);
|
self._setModel(composerModel, opts);
|
||||||
@ -477,7 +480,7 @@ export default Ember.ObjectController.extend(Presence, {
|
|||||||
|
|
||||||
// View a new reply we've made
|
// View a new reply we've made
|
||||||
viewNewReply() {
|
viewNewReply() {
|
||||||
Discourse.URL.routeTo(this.get('model.createdPost.url'));
|
DiscourseURL.routeTo(this.get('model.createdPost.url'));
|
||||||
this.close();
|
this.close();
|
||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
@ -485,7 +488,7 @@ export default Ember.ObjectController.extend(Presence, {
|
|||||||
destroyDraft() {
|
destroyDraft() {
|
||||||
const key = this.get('model.draftKey');
|
const key = this.get('model.draftKey');
|
||||||
if (key) {
|
if (key) {
|
||||||
Discourse.Draft.clear(key, this.get('model.draftSequence'));
|
Draft.clear(key, this.get('model.draftSequence'));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
||||||
import DiscourseController from 'discourse/controllers/controller';
|
import DiscourseController from 'discourse/controllers/controller';
|
||||||
import { setting } from 'discourse/lib/computed';
|
import { setting } from 'discourse/lib/computed';
|
||||||
@ -151,7 +152,7 @@ export default DiscourseController.extend(ModalFunctionality, {
|
|||||||
}
|
}
|
||||||
}.observes('emailValidation', 'accountEmail'),
|
}.observes('emailValidation', 'accountEmail'),
|
||||||
|
|
||||||
fetchExistingUsername: Discourse.debounce(function() {
|
fetchExistingUsername: debounce(function() {
|
||||||
const self = this;
|
const self = this;
|
||||||
Discourse.User.checkUsername(null, this.get('accountEmail')).then(function(result) {
|
Discourse.User.checkUsername(null, this.get('accountEmail')).then(function(result) {
|
||||||
if (result.suggestion && (self.blank('accountUsername') || self.get('accountUsername') === self.get('authOptions.username'))) {
|
if (result.suggestion && (self.blank('accountUsername') || self.get('accountUsername') === self.get('authOptions.username'))) {
|
||||||
@ -227,7 +228,7 @@ export default DiscourseController.extend(ModalFunctionality, {
|
|||||||
return !this.blank('accountUsername') && this.get('accountUsername').length >= this.get('minUsernameLength');
|
return !this.blank('accountUsername') && this.get('accountUsername').length >= this.get('minUsernameLength');
|
||||||
},
|
},
|
||||||
|
|
||||||
checkUsernameAvailability: Discourse.debounce(function() {
|
checkUsernameAvailability: debounce(function() {
|
||||||
const _this = this;
|
const _this = this;
|
||||||
if (this.shouldCheckUsernameMatch()) {
|
if (this.shouldCheckUsernameMatch()) {
|
||||||
return Discourse.User.checkUsername(this.get('accountUsername'), this.get('accountEmail')).then(function(result) {
|
return Discourse.User.checkUsername(this.get('accountUsername'), this.get('accountEmail')).then(function(result) {
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default Ember.ObjectController.extend({
|
export default Ember.ObjectController.extend({
|
||||||
needs: ['navigation/category', 'discovery/topics', 'application'],
|
needs: ['navigation/category', 'discovery/topics', 'application'],
|
||||||
loading: false,
|
loading: false,
|
||||||
@ -22,7 +24,7 @@ export default Ember.ObjectController.extend({
|
|||||||
|
|
||||||
actions: {
|
actions: {
|
||||||
changePeriod(p) {
|
changePeriod(p) {
|
||||||
Discourse.URL.routeTo(this.showMoreUrl(p));
|
DiscourseURL.routeTo(this.showMoreUrl(p));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
||||||
import ObjectController from 'discourse/controllers/object';
|
import ObjectController from 'discourse/controllers/object';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
// Modal for editing / creating a category
|
// Modal for editing / creating a category
|
||||||
export default ObjectController.extend(ModalFunctionality, {
|
export default ObjectController.extend(ModalFunctionality, {
|
||||||
@ -71,7 +72,7 @@ export default ObjectController.extend(ModalFunctionality, {
|
|||||||
this.get('model').save().then(function(result) {
|
this.get('model').save().then(function(result) {
|
||||||
self.send('closeModal');
|
self.send('closeModal');
|
||||||
model.setProperties({slug: result.category.slug, id: result.category.id });
|
model.setProperties({slug: result.category.slug, id: result.category.id });
|
||||||
Discourse.URL.redirectTo("/c/" + Discourse.Category.slugFor(model));
|
DiscourseURL.redirectTo("/c/" + Discourse.Category.slugFor(model));
|
||||||
}).catch(function(error) {
|
}).catch(function(error) {
|
||||||
if (error && error.responseText) {
|
if (error && error.responseText) {
|
||||||
self.flash($.parseJSON(error.responseText).errors[0], 'error');
|
self.flash($.parseJSON(error.responseText).errors[0], 'error');
|
||||||
@ -92,7 +93,7 @@ export default ObjectController.extend(ModalFunctionality, {
|
|||||||
self.get('model').destroy().then(function(){
|
self.get('model').destroy().then(function(){
|
||||||
// success
|
// success
|
||||||
self.send('closeModal');
|
self.send('closeModal');
|
||||||
Discourse.URL.redirectTo("/categories");
|
DiscourseURL.redirectTo("/categories");
|
||||||
}, function(error){
|
}, function(error){
|
||||||
|
|
||||||
if (error && error.responseText) {
|
if (error && error.responseText) {
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import Presence from 'discourse/mixins/presence';
|
import Presence from 'discourse/mixins/presence';
|
||||||
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
||||||
import ObjectController from 'discourse/controllers/object';
|
import ObjectController from 'discourse/controllers/object';
|
||||||
|
import Invite from 'discourse/models/invite';
|
||||||
|
|
||||||
export default ObjectController.extend(Presence, ModalFunctionality, {
|
export default ObjectController.extend(Presence, ModalFunctionality, {
|
||||||
needs: ['user-invited-show'],
|
needs: ['user-invited-show'],
|
||||||
@ -140,7 +141,7 @@ export default ObjectController.extend(Presence, ModalFunctionality, {
|
|||||||
return this.get('model').createInvite(this.get('emailOrUsername').trim(), groupNames).then(result => {
|
return this.get('model').createInvite(this.get('emailOrUsername').trim(), groupNames).then(result => {
|
||||||
model.setProperties({ saving: false, finished: true });
|
model.setProperties({ saving: false, finished: true });
|
||||||
if (!this.get('invitingToTopic')) {
|
if (!this.get('invitingToTopic')) {
|
||||||
Discourse.Invite.findInvitedBy(this.currentUser, userInvitedController.get('filter')).then(invite_model => {
|
Invite.findInvitedBy(this.currentUser, userInvitedController.get('filter')).then(invite_model => {
|
||||||
userInvitedController.set('model', invite_model);
|
userInvitedController.set('model', invite_model);
|
||||||
userInvitedController.set('totalInvites', invite_model.invites.length);
|
userInvitedController.set('totalInvites', invite_model.invites.length);
|
||||||
});
|
});
|
||||||
|
@ -2,6 +2,7 @@ import Presence from 'discourse/mixins/presence';
|
|||||||
import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
||||||
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
||||||
import { movePosts, mergeTopic } from 'discourse/models/topic';
|
import { movePosts, mergeTopic } from 'discourse/models/topic';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
// Modal related to merging of topics
|
// Modal related to merging of topics
|
||||||
export default Ember.Controller.extend(SelectedPostsCount, ModalFunctionality, Presence, {
|
export default Ember.Controller.extend(SelectedPostsCount, ModalFunctionality, Presence, {
|
||||||
@ -54,7 +55,7 @@ export default Ember.Controller.extend(SelectedPostsCount, ModalFunctionality, P
|
|||||||
// Posts moved
|
// Posts moved
|
||||||
self.send('closeModal');
|
self.send('closeModal');
|
||||||
self.get('topicController').send('toggleMultiSelect');
|
self.get('topicController').send('toggleMultiSelect');
|
||||||
Em.run.next(function() { Discourse.URL.routeTo(result.url); });
|
Em.run.next(function() { DiscourseURL.routeTo(result.url); });
|
||||||
}).catch(function() {
|
}).catch(function() {
|
||||||
self.flash(I18n.t('topic.merge_topic.error'));
|
self.flash(I18n.t('topic.merge_topic.error'));
|
||||||
}).finally(function() {
|
}).finally(function() {
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import { setting, propertyEqual } from 'discourse/lib/computed';
|
import { setting, propertyEqual } from 'discourse/lib/computed';
|
||||||
import Presence from 'discourse/mixins/presence';
|
import Presence from 'discourse/mixins/presence';
|
||||||
import ObjectController from 'discourse/controllers/object';
|
import ObjectController from 'discourse/controllers/object';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default ObjectController.extend(Presence, {
|
export default ObjectController.extend(Presence, {
|
||||||
taken: false,
|
taken: false,
|
||||||
@ -46,7 +47,7 @@ export default ObjectController.extend(Presence, {
|
|||||||
if (result) {
|
if (result) {
|
||||||
self.set('saving', true);
|
self.set('saving', true);
|
||||||
self.get('content').changeUsername(self.get('newUsername')).then(function() {
|
self.get('content').changeUsername(self.get('newUsername')).then(function() {
|
||||||
Discourse.URL.redirectTo("/users/" + self.get('newUsername').toLowerCase() + "/preferences");
|
DiscourseURL.redirectTo("/users/" + self.get('newUsername').toLowerCase() + "/preferences");
|
||||||
}, function() {
|
}, function() {
|
||||||
// error
|
// error
|
||||||
self.set('error', true);
|
self.set('error', true);
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import DiscourseController from 'discourse/controllers/controller';
|
import DiscourseController from 'discourse/controllers/controller';
|
||||||
import loadScript from 'discourse/lib/load-script';
|
import loadScript from 'discourse/lib/load-script';
|
||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
|
|
||||||
export default DiscourseController.extend({
|
export default DiscourseController.extend({
|
||||||
needs: ['topic', 'composer'],
|
needs: ['topic', 'composer'],
|
||||||
@ -114,7 +115,7 @@ export default DiscourseController.extend({
|
|||||||
}
|
}
|
||||||
|
|
||||||
const buffer = this.get('buffer');
|
const buffer = this.get('buffer');
|
||||||
const quotedText = Discourse.Quote.build(post, buffer);
|
const quotedText = Quote.build(post, buffer);
|
||||||
composerOpts.quote = quotedText;
|
composerOpts.quote = quotedText;
|
||||||
if (composerController.get('content.viewOpen') || composerController.get('content.viewDraft')) {
|
if (composerController.get('content.viewOpen') || composerController.get('content.viewDraft')) {
|
||||||
composerController.appendBlockAtCursor(quotedText.trim());
|
composerController.appendBlockAtCursor(quotedText.trim());
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import Presence from 'discourse/mixins/presence';
|
import Presence from 'discourse/mixins/presence';
|
||||||
import searchForTerm from 'discourse/lib/search-for-term';
|
import searchForTerm from 'discourse/lib/search-for-term';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
let _dontSearch = false;
|
let _dontSearch = false;
|
||||||
|
|
||||||
@ -138,7 +139,7 @@ export default Em.Controller.extend(Presence, {
|
|||||||
|
|
||||||
const url = this.get('fullSearchUrlRelative');
|
const url = this.get('fullSearchUrlRelative');
|
||||||
if (url) {
|
if (url) {
|
||||||
Discourse.URL.routeTo(url);
|
DiscourseURL.routeTo(url);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -3,6 +3,7 @@ import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
|||||||
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
import ModalFunctionality from 'discourse/mixins/modal-functionality';
|
||||||
import { extractError } from 'discourse/lib/ajax-error';
|
import { extractError } from 'discourse/lib/ajax-error';
|
||||||
import { movePosts } from 'discourse/models/topic';
|
import { movePosts } from 'discourse/models/topic';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
// Modal related to auto closing of topics
|
// Modal related to auto closing of topics
|
||||||
export default Ember.Controller.extend(SelectedPostsCount, ModalFunctionality, Presence, {
|
export default Ember.Controller.extend(SelectedPostsCount, ModalFunctionality, Presence, {
|
||||||
@ -55,7 +56,7 @@ export default Ember.Controller.extend(SelectedPostsCount, ModalFunctionality, P
|
|||||||
// Posts moved
|
// Posts moved
|
||||||
self.send('closeModal');
|
self.send('closeModal');
|
||||||
self.get('topicController').send('toggleMultiSelect');
|
self.get('topicController').send('toggleMultiSelect');
|
||||||
Ember.run.next(function() { Discourse.URL.routeTo(result.url); });
|
Ember.run.next(function() { DiscourseURL.routeTo(result.url); });
|
||||||
}).catch(function(xhr) {
|
}).catch(function(xhr) {
|
||||||
self.flash(extractError(xhr, I18n.t('topic.split_topic.error')));
|
self.flash(extractError(xhr, I18n.t('topic.split_topic.error')));
|
||||||
}).finally(function() {
|
}).finally(function() {
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
function entranceDate(dt, showTime) {
|
function entranceDate(dt, showTime) {
|
||||||
var today = new Date();
|
var today = new Date();
|
||||||
|
|
||||||
@ -51,11 +53,11 @@ export default Ember.Controller.extend({
|
|||||||
},
|
},
|
||||||
|
|
||||||
enterTop: function() {
|
enterTop: function() {
|
||||||
Discourse.URL.routeTo(this.get('model.url'));
|
DiscourseURL.routeTo(this.get('model.url'));
|
||||||
},
|
},
|
||||||
|
|
||||||
enterBottom: function() {
|
enterBottom: function() {
|
||||||
Discourse.URL.routeTo(this.get('model.lastPostUrl'));
|
DiscourseURL.routeTo(this.get('model.lastPostUrl'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default Ember.ObjectController.extend({
|
export default Ember.ObjectController.extend({
|
||||||
needs: ['topic'],
|
needs: ['topic'],
|
||||||
progressPosition: null,
|
progressPosition: null,
|
||||||
@ -62,7 +64,7 @@ export default Ember.ObjectController.extend({
|
|||||||
// Route and close the expansion
|
// Route and close the expansion
|
||||||
jumpTo: function(url) {
|
jumpTo: function(url) {
|
||||||
this.set('expanded', false);
|
this.set('expanded', false);
|
||||||
Discourse.URL.routeTo(url);
|
DiscourseURL.routeTo(url);
|
||||||
},
|
},
|
||||||
|
|
||||||
streamPercentage: function() {
|
streamPercentage: function() {
|
||||||
|
@ -3,6 +3,7 @@ import BufferedContent from 'discourse/mixins/buffered-content';
|
|||||||
import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
import SelectedPostsCount from 'discourse/mixins/selected-posts-count';
|
||||||
import { spinnerHTML } from 'discourse/helpers/loading-spinner';
|
import { spinnerHTML } from 'discourse/helpers/loading-spinner';
|
||||||
import Topic from 'discourse/models/topic';
|
import Topic from 'discourse/models/topic';
|
||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
import { setting } from 'discourse/lib/computed';
|
import { setting } from 'discourse/lib/computed';
|
||||||
|
|
||||||
export default ObjectController.extend(SelectedPostsCount, BufferedContent, {
|
export default ObjectController.extend(SelectedPostsCount, BufferedContent, {
|
||||||
@ -109,7 +110,7 @@ export default ObjectController.extend(SelectedPostsCount, BufferedContent, {
|
|||||||
replyToPost(post) {
|
replyToPost(post) {
|
||||||
const composerController = this.get('controllers.composer'),
|
const composerController = this.get('controllers.composer'),
|
||||||
quoteController = this.get('controllers.quote-button'),
|
quoteController = this.get('controllers.quote-button'),
|
||||||
quotedText = Discourse.Quote.build(quoteController.get('post'), quoteController.get('buffer')),
|
quotedText = Quote.build(quoteController.get('post'), quoteController.get('buffer')),
|
||||||
topic = post ? post.get('topic') : this.get('model');
|
topic = post ? post.get('topic') : this.get('model');
|
||||||
|
|
||||||
quoteController.set('buffer', '');
|
quoteController.set('buffer', '');
|
||||||
@ -412,7 +413,7 @@ export default ObjectController.extend(SelectedPostsCount, BufferedContent, {
|
|||||||
replyAsNewTopic(post) {
|
replyAsNewTopic(post) {
|
||||||
const composerController = this.get('controllers.composer'),
|
const composerController = this.get('controllers.composer'),
|
||||||
quoteController = this.get('controllers.quote-button'),
|
quoteController = this.get('controllers.quote-button'),
|
||||||
quotedText = Discourse.Quote.build(quoteController.get('post'), quoteController.get('buffer')),
|
quotedText = Quote.build(quoteController.get('post'), quoteController.get('buffer')),
|
||||||
self = this;
|
self = this;
|
||||||
|
|
||||||
quoteController.deselectText();
|
quoteController.deselectText();
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
import { propertyNotEqual, setting } from 'discourse/lib/computed';
|
import { propertyNotEqual, setting } from 'discourse/lib/computed';
|
||||||
|
|
||||||
export default Ember.Controller.extend({
|
export default Ember.Controller.extend({
|
||||||
@ -41,7 +42,7 @@ export default Ember.Controller.extend({
|
|||||||
// Don't show on mobile
|
// Don't show on mobile
|
||||||
if (Discourse.Mobile.mobileView) {
|
if (Discourse.Mobile.mobileView) {
|
||||||
const url = "/users/" + username;
|
const url = "/users/" + username;
|
||||||
Discourse.URL.routeTo(url);
|
DiscourseURL.routeTo(url);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
import Invite from 'discourse/models/invite';
|
||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
// This controller handles actions related to a user's invitations
|
// This controller handles actions related to a user's invitations
|
||||||
export default Ember.ObjectController.extend({
|
export default Ember.ObjectController.extend({
|
||||||
user: null,
|
user: null,
|
||||||
@ -19,9 +22,9 @@ export default Ember.ObjectController.extend({
|
|||||||
|
|
||||||
@observes searchTerm
|
@observes searchTerm
|
||||||
**/
|
**/
|
||||||
_searchTermChanged: Discourse.debounce(function() {
|
_searchTermChanged: debounce(function() {
|
||||||
var self = this;
|
var self = this;
|
||||||
Discourse.Invite.findInvitedBy(self.get('user'), this.get('filter'), this.get('searchTerm')).then(function (invites) {
|
Invite.findInvitedBy(self.get('user'), this.get('filter'), this.get('searchTerm')).then(function (invites) {
|
||||||
self.set('model', invites);
|
self.set('model', invites);
|
||||||
});
|
});
|
||||||
}, 250).observes('searchTerm'),
|
}, 250).observes('searchTerm'),
|
||||||
@ -57,35 +60,23 @@ export default Ember.ObjectController.extend({
|
|||||||
|
|
||||||
actions: {
|
actions: {
|
||||||
|
|
||||||
/**
|
rescind(invite) {
|
||||||
Rescind a given invite
|
|
||||||
|
|
||||||
@method rescive
|
|
||||||
@param {Discourse.Invite} invite the invite to rescind.
|
|
||||||
**/
|
|
||||||
rescind: function(invite) {
|
|
||||||
invite.rescind();
|
invite.rescind();
|
||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
reinvite(invite) {
|
||||||
Resend a given invite
|
|
||||||
|
|
||||||
@method reinvite
|
|
||||||
@param {Discourse.Invite} invite the invite to resend.
|
|
||||||
**/
|
|
||||||
reinvite: function(invite) {
|
|
||||||
invite.reinvite();
|
invite.reinvite();
|
||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
|
|
||||||
loadMore: function() {
|
loadMore() {
|
||||||
var self = this;
|
var self = this;
|
||||||
var model = self.get('model');
|
var model = self.get('model');
|
||||||
|
|
||||||
if (self.get('canLoadMore') && !self.get('invitesLoading')) {
|
if (self.get('canLoadMore') && !self.get('invitesLoading')) {
|
||||||
self.set('invitesLoading', true);
|
self.set('invitesLoading', true);
|
||||||
Discourse.Invite.findInvitedBy(self.get('user'), self.get('filter'), self.get('searchTerm'), model.invites.length).then(function(invite_model) {
|
Invite.findInvitedBy(self.get('user'), self.get('filter'), self.get('searchTerm'), model.invites.length).then(function(invite_model) {
|
||||||
self.set('invitesLoading', false);
|
self.set('invitesLoading', false);
|
||||||
model.invites.pushObjects(invite_model.invites);
|
model.invites.pushObjects(invite_model.invites);
|
||||||
if(invite_model.invites.length === 0 || invite_model.invites.length < Discourse.SiteSettings.invites_per_page) {
|
if(invite_model.invites.length === 0 || invite_model.invites.length < Discourse.SiteSettings.invites_per_page) {
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
export default Ember.Controller.extend({
|
export default Ember.Controller.extend({
|
||||||
needs: ["application"],
|
needs: ["application"],
|
||||||
queryParams: ["period", "order", "asc", "name"],
|
queryParams: ["period", "order", "asc", "name"],
|
||||||
@ -8,7 +10,7 @@ export default Ember.Controller.extend({
|
|||||||
|
|
||||||
showTimeRead: Ember.computed.equal("period", "all"),
|
showTimeRead: Ember.computed.equal("period", "all"),
|
||||||
|
|
||||||
_setName: Discourse.debounce(function() {
|
_setName: debounce(function() {
|
||||||
this.set("name", this.get("nameInput"));
|
this.set("name", this.get("nameInput"));
|
||||||
}, 500).observes("nameInput"),
|
}, 500).observes("nameInput"),
|
||||||
|
|
||||||
|
@ -1,6 +1,25 @@
|
|||||||
|
const _customizations = {};
|
||||||
|
|
||||||
|
export function getCustomHTML(key) {
|
||||||
|
const c = _customizations[key];
|
||||||
|
if (c) {
|
||||||
|
return new Handlebars.SafeString(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
const html = PreloadStore.get("customHTML");
|
||||||
|
if (html && html[key] && html[key].length) {
|
||||||
|
return new Handlebars.SafeString(html[key]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set a fragment of HTML by key. It can then be looked up with `getCustomHTML(key)`.
|
||||||
|
export function setCustomHTML(key, html) {
|
||||||
|
_customizations[key] = html;
|
||||||
|
}
|
||||||
|
|
||||||
Ember.HTMLBars._registerHelper('custom-html', function(params, hash, options, env) {
|
Ember.HTMLBars._registerHelper('custom-html', function(params, hash, options, env) {
|
||||||
const name = params[0];
|
const name = params[0];
|
||||||
const html = Discourse.HTML.getCustomHTML(name);
|
const html = getCustomHTML(name);
|
||||||
if (html) { return html; }
|
if (html) { return html; }
|
||||||
|
|
||||||
const contextString = params[1];
|
const contextString = params[1];
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Discourse does some server side rendering of HTML, such as the `cooked` contents of
|
Discourse does some server side rendering of HTML, such as the `cooked` contents of
|
||||||
posts. The downside of this in an Ember app is the links will not go through the router.
|
posts. The downside of this in an Ember app is the links will not go through the router.
|
||||||
@ -28,7 +30,7 @@ export default {
|
|||||||
}
|
}
|
||||||
|
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
Discourse.URL.routeTo(href);
|
DiscourseURL.routeTo(href);
|
||||||
return false;
|
return false;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -0,0 +1,27 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
|
function proxyDep(propName, module) {
|
||||||
|
if (Discourse.hasOwnProperty(propName)) { return; }
|
||||||
|
Object.defineProperty(Discourse, propName, {
|
||||||
|
get: function() {
|
||||||
|
Ember.warn(`DEPRECATION: \`Discourse.${propName}\` is deprecated, import the module.`);
|
||||||
|
return module;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
export default {
|
||||||
|
name: 'es6-deprecations',
|
||||||
|
before: 'inject-objects',
|
||||||
|
|
||||||
|
initialize: function() {
|
||||||
|
// TODO: Once things have migrated remove these
|
||||||
|
proxyDep('computed', require('discourse/lib/computed'));
|
||||||
|
proxyDep('Formatter', require('discourse/lib/formatter'));
|
||||||
|
proxyDep('URL', DiscourseURL);
|
||||||
|
proxyDep('Quote', Quote);
|
||||||
|
proxyDep('debounce', debounce);
|
||||||
|
}
|
||||||
|
};
|
@ -1,6 +1,7 @@
|
|||||||
import Session from 'discourse/models/session';
|
import Session from 'discourse/models/session';
|
||||||
import AppEvents from 'discourse/lib/app-events';
|
import AppEvents from 'discourse/lib/app-events';
|
||||||
import Store from 'discourse/models/store';
|
import Store from 'discourse/models/store';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
function inject() {
|
function inject() {
|
||||||
const app = arguments[0],
|
const app = arguments[0],
|
||||||
@ -22,7 +23,7 @@ export default {
|
|||||||
const appEvents = AppEvents.create();
|
const appEvents = AppEvents.create();
|
||||||
app.register('app-events:main', appEvents, { instantiate: false });
|
app.register('app-events:main', appEvents, { instantiate: false });
|
||||||
injectAll(app, 'appEvents');
|
injectAll(app, 'appEvents');
|
||||||
Discourse.URL.appEvents = appEvents;
|
DiscourseURL.appEvents = appEvents;
|
||||||
|
|
||||||
app.register('store:main', Store);
|
app.register('store:main', Store);
|
||||||
inject(app, 'store', 'route', 'controller');
|
inject(app, 'store', 'route', 'controller');
|
||||||
|
@ -1,11 +1,9 @@
|
|||||||
/*global Mousetrap:true*/
|
/*global Mousetrap:true*/
|
||||||
|
import KeyboardShortcuts from 'discourse/lib/keyboard-shortcuts';
|
||||||
|
|
||||||
/**
|
|
||||||
Initialize Global Keyboard Shortcuts
|
|
||||||
**/
|
|
||||||
export default {
|
export default {
|
||||||
name: "keyboard-shortcuts",
|
name: "keyboard-shortcuts",
|
||||||
initialize: function(container) {
|
initialize(container) {
|
||||||
Discourse.KeyboardShortcuts.bindEvents(Mousetrap, container);
|
KeyboardShortcuts.bindEvents(Mousetrap, container);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -1,11 +1,13 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
name: 'url-redirects',
|
name: 'url-redirects',
|
||||||
initialize: function() {
|
initialize: function() {
|
||||||
|
|
||||||
// URL rewrites (usually due to refactoring)
|
// URL rewrites (usually due to refactoring)
|
||||||
Discourse.URL.rewrite(/^\/category\//, "/c/");
|
DiscourseURL.rewrite(/^\/category\//, "/c/");
|
||||||
Discourse.URL.rewrite(/^\/group\//, "/groups/");
|
DiscourseURL.rewrite(/^\/group\//, "/groups/");
|
||||||
Discourse.URL.rewrite(/\/private-messages\/$/, "/messages/");
|
DiscourseURL.rewrite(/\/private-messages\/$/, "/messages/");
|
||||||
Discourse.URL.rewrite(/^\/users\/([^\/]+)\/?$/, "/users/$1/activity");
|
DiscourseURL.rewrite(/^\/users\/([^\/]+)\/?$/, "/users/$1/activity");
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
trackClick(e) {
|
trackClick(e) {
|
||||||
// cancel click if triggered as part of selection.
|
// cancel click if triggered as part of selection.
|
||||||
@ -87,7 +89,7 @@ export default {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// If we're on the same site, use the router and track via AJAX
|
// If we're on the same site, use the router and track via AJAX
|
||||||
if (Discourse.URL.isInternal(href) && !$link.hasClass('attachment')) {
|
if (DiscourseURL.isInternal(href) && !$link.hasClass('attachment')) {
|
||||||
Discourse.ajax("/clicks/track", {
|
Discourse.ajax("/clicks/track", {
|
||||||
data: {
|
data: {
|
||||||
url: href,
|
url: href,
|
||||||
@ -97,7 +99,7 @@ export default {
|
|||||||
},
|
},
|
||||||
dataType: 'html'
|
dataType: 'html'
|
||||||
});
|
});
|
||||||
Discourse.URL.routeTo(href);
|
DiscourseURL.routeTo(href);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -106,7 +108,7 @@ export default {
|
|||||||
var win = window.open(trackingUrl, '_blank');
|
var win = window.open(trackingUrl, '_blank');
|
||||||
win.focus();
|
win.focus();
|
||||||
} else {
|
} else {
|
||||||
Discourse.URL.redirectTo(trackingUrl);
|
DiscourseURL.redirectTo(trackingUrl);
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
|
@ -3,9 +3,9 @@
|
|||||||
should only be executed once (at the end of the limit counted from the last call made).
|
should only be executed once (at the end of the limit counted from the last call made).
|
||||||
Original function will be called with the context and arguments from the last call made.
|
Original function will be called with the context and arguments from the last call made.
|
||||||
**/
|
**/
|
||||||
Discourse.debounce = function(func, wait) {
|
export default function(func, wait) {
|
||||||
var self, args;
|
let self, args;
|
||||||
var later = function() {
|
const later = function() {
|
||||||
func.apply(self, args);
|
func.apply(self, args);
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -15,4 +15,4 @@ Discourse.debounce = function(func, wait) {
|
|||||||
|
|
||||||
Ember.run.debounce(null, later, wait);
|
Ember.run.debounce(null, later, wait);
|
||||||
};
|
};
|
||||||
};
|
}
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
import PageTracker from 'discourse/lib/page-tracker';
|
import PageTracker from 'discourse/lib/page-tracker';
|
||||||
|
|
||||||
let primaryTab = false;
|
let primaryTab = false;
|
||||||
@ -116,7 +117,7 @@ function onNotification(data) {
|
|||||||
});
|
});
|
||||||
|
|
||||||
function clickEventHandler() {
|
function clickEventHandler() {
|
||||||
Discourse.URL.routeTo(data.post_url);
|
DiscourseURL.routeTo(data.post_url);
|
||||||
// Cannot delay this until the page renders
|
// Cannot delay this until the page renders
|
||||||
// due to trigger-based permissions
|
// due to trigger-based permissions
|
||||||
window.focus();
|
window.focus();
|
||||||
|
@ -1,28 +0,0 @@
|
|||||||
var customizations = {};
|
|
||||||
|
|
||||||
Discourse.HTML = {
|
|
||||||
|
|
||||||
/**
|
|
||||||
Return a custom fragment of HTML by key. It can be registered via a plugin
|
|
||||||
using `setCustomHTML(key, html)`. This is used by a handlebars helper to find
|
|
||||||
the HTML content it wants. It will also check the `PreloadStore` for any server
|
|
||||||
side preloaded HTML.
|
|
||||||
**/
|
|
||||||
getCustomHTML: function(key) {
|
|
||||||
var c = customizations[key];
|
|
||||||
if (c) {
|
|
||||||
return new Handlebars.SafeString(c);
|
|
||||||
}
|
|
||||||
|
|
||||||
var html = PreloadStore.get("customHTML");
|
|
||||||
if (html && html[key] && html[key].length) {
|
|
||||||
return new Handlebars.SafeString(html[key]);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
// Set a fragment of HTML by key. It can then be looked up with `getCustomHTML(key)`.
|
|
||||||
setCustomHTML: function(key, html) {
|
|
||||||
customizations[key] = html;
|
|
||||||
}
|
|
||||||
|
|
||||||
};
|
|
@ -1,4 +1,6 @@
|
|||||||
var PATH_BINDINGS = {
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
|
const PATH_BINDINGS = {
|
||||||
'g h': '/',
|
'g h': '/',
|
||||||
'g l': '/latest',
|
'g l': '/latest',
|
||||||
'g n': '/new',
|
'g n': '/new',
|
||||||
@ -55,8 +57,8 @@ var PATH_BINDINGS = {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
export default {
|
||||||
bindEvents: function(keyTrapper, container) {
|
bindEvents(keyTrapper, container) {
|
||||||
this.keyTrapper = keyTrapper;
|
this.keyTrapper = keyTrapper;
|
||||||
this.container = container;
|
this.container = container;
|
||||||
this._stopCallback();
|
this._stopCallback();
|
||||||
@ -67,13 +69,13 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
_.each(FUNCTION_BINDINGS, this._bindToFunction, this);
|
_.each(FUNCTION_BINDINGS, this._bindToFunction, this);
|
||||||
},
|
},
|
||||||
|
|
||||||
toggleBookmark: function(){
|
toggleBookmark(){
|
||||||
this.sendToSelectedPost('toggleBookmark');
|
this.sendToSelectedPost('toggleBookmark');
|
||||||
this.sendToTopicListItemView('toggleBookmark');
|
this.sendToTopicListItemView('toggleBookmark');
|
||||||
},
|
},
|
||||||
|
|
||||||
toggleBookmarkTopic: function(){
|
toggleBookmarkTopic(){
|
||||||
var topic = this.currentTopic();
|
const topic = this.currentTopic();
|
||||||
// BIG hack, need a cleaner way
|
// BIG hack, need a cleaner way
|
||||||
if(topic && $('.posts-wrapper').length > 0) {
|
if(topic && $('.posts-wrapper').length > 0) {
|
||||||
topic.toggleBookmark();
|
topic.toggleBookmark();
|
||||||
@ -82,7 +84,7 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
quoteReply: function(){
|
quoteReply(){
|
||||||
$('.topic-post.selected button.create').click();
|
$('.topic-post.selected button.create').click();
|
||||||
// lazy but should work for now
|
// lazy but should work for now
|
||||||
setTimeout(function(){
|
setTimeout(function(){
|
||||||
@ -90,55 +92,55 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}, 500);
|
}, 500);
|
||||||
},
|
},
|
||||||
|
|
||||||
goToFirstPost: function() {
|
goToFirstPost() {
|
||||||
this._jumpTo('jumpTop');
|
this._jumpTo('jumpTop');
|
||||||
},
|
},
|
||||||
|
|
||||||
goToLastPost: function() {
|
goToLastPost() {
|
||||||
this._jumpTo('jumpBottom');
|
this._jumpTo('jumpBottom');
|
||||||
},
|
},
|
||||||
|
|
||||||
_jumpTo: function(direction) {
|
_jumpTo(direction) {
|
||||||
if ($('.container.posts').length) {
|
if ($('.container.posts').length) {
|
||||||
this.container.lookup('controller:topic-progress').send(direction);
|
this.container.lookup('controller:topic-progress').send(direction);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
replyToTopic: function() {
|
replyToTopic() {
|
||||||
this.container.lookup('controller:topic').send('replyToPost');
|
this.container.lookup('controller:topic').send('replyToPost');
|
||||||
},
|
},
|
||||||
|
|
||||||
selectDown: function() {
|
selectDown() {
|
||||||
this._moveSelection(1);
|
this._moveSelection(1);
|
||||||
},
|
},
|
||||||
|
|
||||||
selectUp: function() {
|
selectUp() {
|
||||||
this._moveSelection(-1);
|
this._moveSelection(-1);
|
||||||
},
|
},
|
||||||
|
|
||||||
goBack: function() {
|
goBack() {
|
||||||
history.back();
|
history.back();
|
||||||
},
|
},
|
||||||
|
|
||||||
nextSection: function() {
|
nextSection() {
|
||||||
this._changeSection(1);
|
this._changeSection(1);
|
||||||
},
|
},
|
||||||
|
|
||||||
prevSection: function() {
|
prevSection() {
|
||||||
this._changeSection(-1);
|
this._changeSection(-1);
|
||||||
},
|
},
|
||||||
|
|
||||||
showBuiltinSearch: function() {
|
showBuiltinSearch() {
|
||||||
if ($('#search-dropdown').is(':visible')) {
|
if ($('#search-dropdown').is(':visible')) {
|
||||||
this._toggleSearch(false);
|
this._toggleSearch(false);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
var currentPath = this.container.lookup('controller:application').get('currentPath'),
|
const currentPath = this.container.lookup('controller:application').get('currentPath'),
|
||||||
blacklist = [ /^discovery\.categories/ ],
|
blacklist = [ /^discovery\.categories/ ],
|
||||||
whitelist = [ /^topic\./ ],
|
whitelist = [ /^topic\./ ],
|
||||||
check = function(regex) { return !!currentPath.match(regex); },
|
check = function(regex) { return !!currentPath.match(regex); };
|
||||||
showSearch = whitelist.any(check) && !blacklist.any(check);
|
let showSearch = whitelist.any(check) && !blacklist.any(check);
|
||||||
|
|
||||||
// If we're viewing a topic, only intercept search if there are cloaked posts
|
// If we're viewing a topic, only intercept search if there are cloaked posts
|
||||||
if (showSearch && currentPath.match(/^topic\./)) {
|
if (showSearch && currentPath.match(/^topic\./)) {
|
||||||
@ -153,61 +155,61 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
return true;
|
return true;
|
||||||
},
|
},
|
||||||
|
|
||||||
createTopic: function() {
|
createTopic() {
|
||||||
Discourse.__container__.lookup('controller:composer').open({action: Discourse.Composer.CREATE_TOPIC, draftKey: Discourse.Composer.CREATE_TOPIC});
|
this.container.lookup('controller:composer').open({action: Discourse.Composer.CREATE_TOPIC, draftKey: Discourse.Composer.CREATE_TOPIC});
|
||||||
},
|
},
|
||||||
|
|
||||||
pinUnpinTopic: function() {
|
pinUnpinTopic() {
|
||||||
Discourse.__container__.lookup('controller:topic').togglePinnedState();
|
this.container.lookup('controller:topic').togglePinnedState();
|
||||||
},
|
},
|
||||||
|
|
||||||
toggleProgress: function() {
|
toggleProgress() {
|
||||||
Discourse.__container__.lookup('controller:topic-progress').send('toggleExpansion', {highlight: true});
|
this.container.lookup('controller:topic-progress').send('toggleExpansion', {highlight: true});
|
||||||
},
|
},
|
||||||
|
|
||||||
showSearch: function() {
|
showSearch() {
|
||||||
this._toggleSearch(false);
|
this._toggleSearch(false);
|
||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
|
|
||||||
showSiteMap: function() {
|
showSiteMap() {
|
||||||
$('#site-map').click();
|
$('#site-map').click();
|
||||||
$('#site-map-dropdown a:first').focus();
|
$('#site-map-dropdown a:first').focus();
|
||||||
},
|
},
|
||||||
|
|
||||||
showCurrentUser: function() {
|
showCurrentUser() {
|
||||||
$('#current-user').click();
|
$('#current-user').click();
|
||||||
$('#user-dropdown a:first').focus();
|
$('#user-dropdown a:first').focus();
|
||||||
},
|
},
|
||||||
|
|
||||||
showHelpModal: function() {
|
showHelpModal() {
|
||||||
Discourse.__container__.lookup('controller:application').send('showKeyboardShortcutsHelp');
|
this.container.lookup('controller:application').send('showKeyboardShortcutsHelp');
|
||||||
},
|
},
|
||||||
|
|
||||||
sendToTopicListItemView: function(action){
|
sendToTopicListItemView(action){
|
||||||
var elem = $('tr.selected.topic-list-item.ember-view')[0];
|
const elem = $('tr.selected.topic-list-item.ember-view')[0];
|
||||||
if(elem){
|
if(elem){
|
||||||
var view = Ember.View.views[elem.id];
|
const view = Ember.View.views[elem.id];
|
||||||
view.send(action);
|
view.send(action);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
currentTopic: function(){
|
currentTopic(){
|
||||||
var topicController = this.container.lookup('controller:topic');
|
const topicController = this.container.lookup('controller:topic');
|
||||||
if(topicController) {
|
if(topicController) {
|
||||||
var topic = topicController.get('model');
|
const topic = topicController.get('model');
|
||||||
if(topic){
|
if(topic){
|
||||||
return topic;
|
return topic;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
sendToSelectedPost: function(action){
|
sendToSelectedPost(action){
|
||||||
var container = this.container;
|
const container = this.container;
|
||||||
// TODO: We should keep track of the post without a CSS class
|
// TODO: We should keep track of the post without a CSS class
|
||||||
var selectedPostId = parseInt($('.topic-post.selected article.boxed').data('post-id'), 10);
|
const selectedPostId = parseInt($('.topic-post.selected article.boxed').data('post-id'), 10);
|
||||||
if (selectedPostId) {
|
if (selectedPostId) {
|
||||||
var topicController = container.lookup('controller:topic'),
|
const topicController = container.lookup('controller:topic'),
|
||||||
post = topicController.get('model.postStream.posts').findBy('id', selectedPostId);
|
post = topicController.get('model.postStream.posts').findBy('id', selectedPostId);
|
||||||
if (post) {
|
if (post) {
|
||||||
topicController.send(action, post);
|
topicController.send(action, post);
|
||||||
@ -215,24 +217,24 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
_bindToSelectedPost: function(action, binding) {
|
_bindToSelectedPost(action, binding) {
|
||||||
var self = this;
|
const self = this;
|
||||||
|
|
||||||
this.keyTrapper.bind(binding, function() {
|
this.keyTrapper.bind(binding, function() {
|
||||||
self.sendToSelectedPost(action);
|
self.sendToSelectedPost(action);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
_bindToPath: function(path, binding) {
|
_bindToPath(path, binding) {
|
||||||
this.keyTrapper.bind(binding, function() {
|
this.keyTrapper.bind(binding, function() {
|
||||||
Discourse.URL.routeTo(path);
|
DiscourseURL.routeTo(path);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
_bindToClick: function(selector, binding) {
|
_bindToClick(selector, binding) {
|
||||||
binding = binding.split(',');
|
binding = binding.split(',');
|
||||||
this.keyTrapper.bind(binding, function(e) {
|
this.keyTrapper.bind(binding, function(e) {
|
||||||
var $sel = $(selector);
|
const $sel = $(selector);
|
||||||
|
|
||||||
// Special case: We're binding to enter.
|
// Special case: We're binding to enter.
|
||||||
if (e && e.keyCode === 13) {
|
if (e && e.keyCode === 13) {
|
||||||
@ -249,21 +251,21 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
_bindToFunction: function(func, binding) {
|
_bindToFunction(func, binding) {
|
||||||
if (typeof this[func] === 'function') {
|
if (typeof this[func] === 'function') {
|
||||||
this.keyTrapper.bind(binding, _.bind(this[func], this));
|
this.keyTrapper.bind(binding, _.bind(this[func], this));
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
_moveSelection: function(direction) {
|
_moveSelection(direction) {
|
||||||
var $articles = this._findArticles();
|
const $articles = this._findArticles();
|
||||||
|
|
||||||
if (typeof $articles === 'undefined') {
|
if (typeof $articles === 'undefined') {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var $selected = $articles.filter('.selected'),
|
const $selected = $articles.filter('.selected');
|
||||||
index = $articles.index($selected);
|
let index = $articles.index($selected);
|
||||||
|
|
||||||
if($selected.length !== 0){ //boundries check
|
if($selected.length !== 0){ //boundries check
|
||||||
// loop is not allowed
|
// loop is not allowed
|
||||||
@ -273,11 +275,11 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
|
|
||||||
// if nothing is selected go to the first post on screen
|
// if nothing is selected go to the first post on screen
|
||||||
if ($selected.length === 0) {
|
if ($selected.length === 0) {
|
||||||
var scrollTop = $(document).scrollTop();
|
const scrollTop = $(document).scrollTop();
|
||||||
|
|
||||||
index = 0;
|
index = 0;
|
||||||
$articles.each(function(){
|
$articles.each(function(){
|
||||||
var top = $(this).position().top;
|
const top = $(this).position().top;
|
||||||
if(top > scrollTop) {
|
if(top > scrollTop) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -291,7 +293,7 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
direction = 0;
|
direction = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
var $article = $articles.eq(index + direction);
|
const $article = $articles.eq(index + direction);
|
||||||
|
|
||||||
if ($article.size() > 0) {
|
if ($article.size() > 0) {
|
||||||
|
|
||||||
@ -303,7 +305,7 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
|
|
||||||
if ($article.is('.topic-post')) {
|
if ($article.is('.topic-post')) {
|
||||||
var tabLoc = $article.find('a.tabLoc');
|
let tabLoc = $article.find('a.tabLoc');
|
||||||
if (tabLoc.length === 0) {
|
if (tabLoc.length === 0) {
|
||||||
tabLoc = $('<a href class="tabLoc"></a>');
|
tabLoc = $('<a href class="tabLoc"></a>');
|
||||||
$article.prepend(tabLoc);
|
$article.prepend(tabLoc);
|
||||||
@ -315,19 +317,19 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
_scrollList: function($article) {
|
_scrollList($article) {
|
||||||
// Try to keep the article on screen
|
// Try to keep the article on screen
|
||||||
var pos = $article.offset();
|
const pos = $article.offset();
|
||||||
var height = $article.height();
|
const height = $article.height();
|
||||||
var scrollTop = $(window).scrollTop();
|
const scrollTop = $(window).scrollTop();
|
||||||
var windowHeight = $(window).height();
|
const windowHeight = $(window).height();
|
||||||
|
|
||||||
// skip if completely on screen
|
// skip if completely on screen
|
||||||
if (pos.top > scrollTop && (pos.top + height) < (scrollTop + windowHeight)) {
|
if (pos.top > scrollTop && (pos.top + height) < (scrollTop + windowHeight)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var scrollPos = (pos.top + (height/2)) - (windowHeight * 0.5);
|
let scrollPos = (pos.top + (height/2)) - (windowHeight * 0.5);
|
||||||
if (scrollPos < 0) { scrollPos = 0; }
|
if (scrollPos < 0) { scrollPos = 0; }
|
||||||
|
|
||||||
if (this._scrollAnimation) {
|
if (this._scrollAnimation) {
|
||||||
@ -337,8 +339,8 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
},
|
},
|
||||||
|
|
||||||
|
|
||||||
_findArticles: function() {
|
_findArticles() {
|
||||||
var $topicList = $('.topic-list'),
|
const $topicList = $('.topic-list'),
|
||||||
$topicArea = $('.posts-wrapper');
|
$topicArea = $('.posts-wrapper');
|
||||||
|
|
||||||
if ($topicArea.size() > 0) {
|
if ($topicArea.size() > 0) {
|
||||||
@ -349,8 +351,8 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
_changeSection: function(direction) {
|
_changeSection(direction) {
|
||||||
var $sections = $('#navigation-bar li'),
|
const $sections = $('#navigation-bar li'),
|
||||||
active = $('#navigation-bar li.active'),
|
active = $('#navigation-bar li.active'),
|
||||||
index = $sections.index(active) + direction;
|
index = $sections.index(active) + direction;
|
||||||
|
|
||||||
@ -359,8 +361,8 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
_stopCallback: function() {
|
_stopCallback() {
|
||||||
var oldStopCallback = this.keyTrapper.stopCallback;
|
const oldStopCallback = this.keyTrapper.stopCallback;
|
||||||
|
|
||||||
this.keyTrapper.stopCallback = function(e, element, combo) {
|
this.keyTrapper.stopCallback = function(e, element, combo) {
|
||||||
if ((combo === 'ctrl+f' || combo === 'command+f') && element.id === 'search-term') {
|
if ((combo === 'ctrl+f' || combo === 'command+f') && element.id === 'search-term') {
|
||||||
@ -371,10 +373,10 @@ Discourse.KeyboardShortcuts = Ember.Object.createWithMixins({
|
|||||||
};
|
};
|
||||||
},
|
},
|
||||||
|
|
||||||
_toggleSearch: function(selectContext) {
|
_toggleSearch(selectContext) {
|
||||||
$('#search-button').click();
|
$('#search-button').click();
|
||||||
if (selectContext) {
|
if (selectContext) {
|
||||||
Discourse.__container__.lookup('controller:search').set('searchContextEnabled', true);
|
this.container.lookup('controller:search').set('searchContextEnabled', true);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
});
|
};
|
@ -1,4 +1,4 @@
|
|||||||
Discourse.Quote = {
|
export default {
|
||||||
|
|
||||||
REGEXP: /\[quote=([^\]]*)\]((?:[\s\S](?!\[quote=[^\]]*\]))*?)\[\/quote\]/im,
|
REGEXP: /\[quote=([^\]]*)\]((?:[\s\S](?!\[quote=[^\]]*\]))*?)\[\/quote\]/im,
|
||||||
|
|
@ -1,3 +1,5 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
const configs = {
|
const configs = {
|
||||||
"faq": "faq_url",
|
"faq": "faq_url",
|
||||||
"tos": "tos_url",
|
"tos": "tos_url",
|
||||||
@ -14,14 +16,14 @@ export default (page) => {
|
|||||||
const configKey = configs[page];
|
const configKey = configs[page];
|
||||||
if (configKey && Discourse.SiteSettings[configKey].length > 0) {
|
if (configKey && Discourse.SiteSettings[configKey].length > 0) {
|
||||||
transition.abort();
|
transition.abort();
|
||||||
Discourse.URL.redirectTo(Discourse.SiteSettings[configKey]);
|
DiscourseURL.redirectTo(Discourse.SiteSettings[configKey]);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
activate() {
|
activate() {
|
||||||
this._super();
|
this._super();
|
||||||
// Scroll to an element if exists
|
// Scroll to an element if exists
|
||||||
Discourse.URL.scrollToId(document.location.hash);
|
DiscourseURL.scrollToId(document.location.hash);
|
||||||
},
|
},
|
||||||
|
|
||||||
model() {
|
model() {
|
||||||
|
@ -1,25 +1,25 @@
|
|||||||
/*global LockOn:true*/
|
/*global LockOn:true*/
|
||||||
var jumpScheduled = false,
|
let _jumpScheduled = false;
|
||||||
rewrites = [];
|
const rewrites = [];
|
||||||
|
|
||||||
Discourse.URL = Ember.Object.createWithMixins({
|
const DiscourseURL = Ember.Object.createWithMixins({
|
||||||
|
|
||||||
// Used for matching a topic
|
// Used for matching a topic
|
||||||
TOPIC_REGEXP: /\/t\/([^\/]+)\/(\d+)\/?(\d+)?/,
|
TOPIC_REGEXP: /\/t\/([^\/]+)\/(\d+)\/?(\d+)?/,
|
||||||
|
|
||||||
isJumpScheduled: function() {
|
isJumpScheduled: function() {
|
||||||
return jumpScheduled;
|
return _jumpScheduled;
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Jumps to a particular post in the stream
|
Jumps to a particular post in the stream
|
||||||
**/
|
**/
|
||||||
jumpToPost: function(postNumber, opts) {
|
jumpToPost: function(postNumber, opts) {
|
||||||
var holderId = '#post-cloak-' + postNumber;
|
const holderId = '#post-cloak-' + postNumber;
|
||||||
|
|
||||||
var offset = function(){
|
const offset = function(){
|
||||||
|
|
||||||
var $header = $('header'),
|
const $header = $('header'),
|
||||||
$title = $('#topic-title'),
|
$title = $('#topic-title'),
|
||||||
windowHeight = $(window).height() - $title.height(),
|
windowHeight = $(window).height() - $title.height(),
|
||||||
expectedOffset = $title.height() - $header.find('.contents').height() + (windowHeight / 5);
|
expectedOffset = $title.height() - $header.find('.contents').height() + (windowHeight / 5);
|
||||||
@ -34,13 +34,13 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var lockon = new LockOn(holderId, {offsetCalculator: offset});
|
const lockon = new LockOn(holderId, {offsetCalculator: offset});
|
||||||
var holder = $(holderId);
|
const holder = $(holderId);
|
||||||
|
|
||||||
if(holder.length > 0 && opts && opts.skipIfOnScreen){
|
if(holder.length > 0 && opts && opts.skipIfOnScreen){
|
||||||
|
|
||||||
// if we are on screen skip
|
// if we are on screen skip
|
||||||
var elementTop = lockon.elementTop(),
|
const elementTop = lockon.elementTop(),
|
||||||
scrollTop = $(window).scrollTop(),
|
scrollTop = $(window).scrollTop(),
|
||||||
windowHeight = $(window).height()-offset(),
|
windowHeight = $(window).height()-offset(),
|
||||||
height = holder.height();
|
height = holder.height();
|
||||||
@ -73,7 +73,7 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
// while URLs are loading. For example, while a topic loads it sets `currentPost`
|
// while URLs are loading. For example, while a topic loads it sets `currentPost`
|
||||||
// which triggers a replaceState even though the topic hasn't fully loaded yet!
|
// which triggers a replaceState even though the topic hasn't fully loaded yet!
|
||||||
Em.run.next(function() {
|
Em.run.next(function() {
|
||||||
var location = Discourse.URL.get('router.location');
|
const location = DiscourseURL.get('router.location');
|
||||||
if (location && location.replaceURL) {
|
if (location && location.replaceURL) {
|
||||||
location.replaceURL(path);
|
location.replaceURL(path);
|
||||||
}
|
}
|
||||||
@ -85,15 +85,15 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
scrollToId: function(id) {
|
scrollToId: function(id) {
|
||||||
if (Em.isEmpty(id)) { return; }
|
if (Em.isEmpty(id)) { return; }
|
||||||
|
|
||||||
jumpScheduled = true;
|
_jumpScheduled = true;
|
||||||
Em.run.schedule('afterRender', function() {
|
Em.run.schedule('afterRender', function() {
|
||||||
var $elem = $(id);
|
let $elem = $(id);
|
||||||
if ($elem.length === 0) {
|
if ($elem.length === 0) {
|
||||||
$elem = $("[name='" + id.replace('#', '') + "']");
|
$elem = $("[name='" + id.replace('#', '') + "']");
|
||||||
}
|
}
|
||||||
if ($elem.length > 0) {
|
if ($elem.length > 0) {
|
||||||
$('html,body').scrollTop($elem.offset().top - $('header').height() - 15);
|
$('html,body').scrollTop($elem.offset().top - $('header').height() - 15);
|
||||||
jumpScheduled = false;
|
_jumpScheduled = false;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
@ -125,19 +125,19 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
var oldPath = window.location.pathname;
|
const oldPath = window.location.pathname;
|
||||||
path = path.replace(/(https?\:)?\/\/[^\/]+/, '');
|
path = path.replace(/(https?\:)?\/\/[^\/]+/, '');
|
||||||
|
|
||||||
// handle prefixes
|
// handle prefixes
|
||||||
if (path.match(/^\//)) {
|
if (path.match(/^\//)) {
|
||||||
var rootURL = (Discourse.BaseUri === undefined ? "/" : Discourse.BaseUri);
|
let rootURL = (Discourse.BaseUri === undefined ? "/" : Discourse.BaseUri);
|
||||||
rootURL = rootURL.replace(/\/$/, '');
|
rootURL = rootURL.replace(/\/$/, '');
|
||||||
path = path.replace(rootURL, '');
|
path = path.replace(rootURL, '');
|
||||||
}
|
}
|
||||||
|
|
||||||
// Rewrite /my/* urls
|
// Rewrite /my/* urls
|
||||||
if (path.indexOf('/my/') === 0) {
|
if (path.indexOf('/my/') === 0) {
|
||||||
var currentUser = Discourse.User.current();
|
const currentUser = Discourse.User.current();
|
||||||
if (currentUser) {
|
if (currentUser) {
|
||||||
path = path.replace('/my/', '/users/' + currentUser.get('username_lower') + "/");
|
path = path.replace('/my/', '/users/' + currentUser.get('username_lower') + "/");
|
||||||
} else {
|
} else {
|
||||||
@ -203,40 +203,40 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
@param {String} path the path we're navigating to
|
@param {String} path the path we're navigating to
|
||||||
**/
|
**/
|
||||||
navigatedToPost: function(oldPath, path) {
|
navigatedToPost: function(oldPath, path) {
|
||||||
var newMatches = this.TOPIC_REGEXP.exec(path),
|
const newMatches = this.TOPIC_REGEXP.exec(path),
|
||||||
newTopicId = newMatches ? newMatches[2] : null;
|
newTopicId = newMatches ? newMatches[2] : null;
|
||||||
|
|
||||||
if (newTopicId) {
|
if (newTopicId) {
|
||||||
var oldMatches = this.TOPIC_REGEXP.exec(oldPath),
|
const oldMatches = this.TOPIC_REGEXP.exec(oldPath),
|
||||||
oldTopicId = oldMatches ? oldMatches[2] : null;
|
oldTopicId = oldMatches ? oldMatches[2] : null;
|
||||||
|
|
||||||
// If the topic_id is the same
|
// If the topic_id is the same
|
||||||
if (oldTopicId === newTopicId) {
|
if (oldTopicId === newTopicId) {
|
||||||
Discourse.URL.replaceState(path);
|
DiscourseURL.replaceState(path);
|
||||||
|
|
||||||
var container = Discourse.__container__,
|
const container = Discourse.__container__,
|
||||||
topicController = container.lookup('controller:topic'),
|
topicController = container.lookup('controller:topic'),
|
||||||
opts = {},
|
opts = {},
|
||||||
postStream = topicController.get('model.postStream');
|
postStream = topicController.get('model.postStream');
|
||||||
|
|
||||||
if (newMatches[3]) opts.nearPost = newMatches[3];
|
if (newMatches[3]) opts.nearPost = newMatches[3];
|
||||||
if (path.match(/last$/)) { opts.nearPost = topicController.get('highest_post_number'); }
|
if (path.match(/last$/)) { opts.nearPost = topicController.get('highest_post_number'); }
|
||||||
var closest = opts.nearPost || 1;
|
const closest = opts.nearPost || 1;
|
||||||
|
|
||||||
var self = this;
|
const self = this;
|
||||||
postStream.refresh(opts).then(function() {
|
postStream.refresh(opts).then(function() {
|
||||||
topicController.setProperties({
|
topicController.setProperties({
|
||||||
'model.currentPost': closest,
|
'model.currentPost': closest,
|
||||||
enteredAt: new Date().getTime().toString()
|
enteredAt: new Date().getTime().toString()
|
||||||
});
|
});
|
||||||
var closestPost = postStream.closestPostForPostNumber(closest),
|
const closestPost = postStream.closestPostForPostNumber(closest),
|
||||||
progress = postStream.progressIndexOfPost(closestPost),
|
progress = postStream.progressIndexOfPost(closestPost),
|
||||||
progressController = container.lookup('controller:topic-progress');
|
progressController = container.lookup('controller:topic-progress');
|
||||||
|
|
||||||
progressController.set('progressPosition', progress);
|
progressController.set('progressPosition', progress);
|
||||||
self.appEvents.trigger('post:highlight', closest);
|
self.appEvents.trigger('post:highlight', closest);
|
||||||
}).then(function() {
|
}).then(function() {
|
||||||
Discourse.URL.jumpToPost(closest, {skipIfOnScreen: true});
|
DiscourseURL.jumpToPost(closest, {skipIfOnScreen: true});
|
||||||
});
|
});
|
||||||
|
|
||||||
// Abort routing, we have replaced our state.
|
// Abort routing, we have replaced our state.
|
||||||
@ -256,7 +256,7 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
@param {String} path the path we're navigating to
|
@param {String} path the path we're navigating to
|
||||||
**/
|
**/
|
||||||
navigatedToHome: function(oldPath, path) {
|
navigatedToHome: function(oldPath, path) {
|
||||||
var homepage = Discourse.Utilities.defaultHomepage();
|
const homepage = Discourse.Utilities.defaultHomepage();
|
||||||
|
|
||||||
if (window.history &&
|
if (window.history &&
|
||||||
window.history.pushState &&
|
window.history.pushState &&
|
||||||
@ -269,14 +269,7 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
return false;
|
return false;
|
||||||
},
|
},
|
||||||
|
|
||||||
/**
|
// This has been extracted so it can be tested.
|
||||||
@private
|
|
||||||
|
|
||||||
Get the origin of the current location.
|
|
||||||
This has been extracted so it can be tested.
|
|
||||||
|
|
||||||
@method origin
|
|
||||||
**/
|
|
||||||
origin: function() {
|
origin: function() {
|
||||||
return window.location.origin;
|
return window.location.origin;
|
||||||
},
|
},
|
||||||
@ -293,15 +286,8 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
return Discourse.__container__.lookup('router:main');
|
return Discourse.__container__.lookup('router:main');
|
||||||
}.property().volatile(),
|
}.property().volatile(),
|
||||||
|
|
||||||
/**
|
// Get a controller. Note that currently it uses `__container__` which is not
|
||||||
@private
|
// advised but there is no other way to access the router.
|
||||||
|
|
||||||
Get a controller. Note that currently it uses `__container__` which is not
|
|
||||||
advised but there is no other way to access the router.
|
|
||||||
|
|
||||||
@method controllerFor
|
|
||||||
@param {String} name the name of the controller
|
|
||||||
**/
|
|
||||||
controllerFor: function(name) {
|
controllerFor: function(name) {
|
||||||
return Discourse.__container__.lookup('controller:' + name);
|
return Discourse.__container__.lookup('controller:' + name);
|
||||||
},
|
},
|
||||||
@ -313,7 +299,7 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
handleURL: function(path, opts) {
|
handleURL: function(path, opts) {
|
||||||
opts = opts || {};
|
opts = opts || {};
|
||||||
|
|
||||||
var router = this.get('router');
|
const router = this.get('router');
|
||||||
|
|
||||||
if (opts.replaceURL) {
|
if (opts.replaceURL) {
|
||||||
this.replaceState(path);
|
this.replaceState(path);
|
||||||
@ -321,25 +307,25 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
router.router.updateURL(path);
|
router.router.updateURL(path);
|
||||||
}
|
}
|
||||||
|
|
||||||
var split = path.split('#'),
|
const split = path.split('#');
|
||||||
elementId;
|
let elementId;
|
||||||
|
|
||||||
if (split.length === 2) {
|
if (split.length === 2) {
|
||||||
path = split[0];
|
path = split[0];
|
||||||
elementId = split[1];
|
elementId = split[1];
|
||||||
}
|
}
|
||||||
|
|
||||||
var transition = router.handleURL(path);
|
const transition = router.handleURL(path);
|
||||||
transition._discourse_intercepted = true;
|
transition._discourse_intercepted = true;
|
||||||
transition.promise.then(function() {
|
transition.promise.then(function() {
|
||||||
if (elementId) {
|
if (elementId) {
|
||||||
|
|
||||||
jumpScheduled = true;
|
_jumpScheduled = true;
|
||||||
Em.run.next('afterRender', function() {
|
Em.run.next('afterRender', function() {
|
||||||
var offset = $('#' + elementId).offset();
|
const offset = $('#' + elementId).offset();
|
||||||
if (offset && offset.top) {
|
if (offset && offset.top) {
|
||||||
$('html, body').scrollTop(offset.top - $('header').height() - 10);
|
$('html, body').scrollTop(offset.top - $('header').height() - 10);
|
||||||
jumpScheduled = false;
|
_jumpScheduled = false;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -347,3 +333,5 @@ Discourse.URL = Ember.Object.createWithMixins({
|
|||||||
}
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
export default DiscourseURL;
|
@ -1,5 +1,7 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
function scrollTop() {
|
function scrollTop() {
|
||||||
if (Discourse.URL.isJumpScheduled()) { return; }
|
if (DiscourseURL.isJumpScheduled()) { return; }
|
||||||
Ember.run.schedule('afterRender', function() {
|
Ember.run.schedule('afterRender', function() {
|
||||||
$(document).scrollTop(0);
|
$(document).scrollTop(0);
|
||||||
});
|
});
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
This object provides the DOM methods we need for our Mixin to bind to scrolling
|
This object provides the DOM methods we need for our Mixin to bind to scrolling
|
||||||
methods in the browser. By removing them from the Mixin we can test them
|
methods in the browser. By removing them from the Mixin we can test them
|
||||||
@ -34,7 +36,7 @@ const Scrolling = Ember.Mixin.create({
|
|||||||
};
|
};
|
||||||
|
|
||||||
if (opts.debounce) {
|
if (opts.debounce) {
|
||||||
onScrollMethod = Discourse.debounce(onScrollMethod, opts.debounce);
|
onScrollMethod = debounce(onScrollMethod, opts.debounce);
|
||||||
}
|
}
|
||||||
|
|
||||||
ScrollingDOMMethods.bindOnScroll(onScrollMethod, opts.name);
|
ScrollingDOMMethods.bindOnScroll(onScrollMethod, opts.name);
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
import RestModel from 'discourse/models/rest';
|
import RestModel from 'discourse/models/rest';
|
||||||
import Topic from 'discourse/models/topic';
|
import Topic from 'discourse/models/topic';
|
||||||
import { throwAjaxError } from 'discourse/lib/ajax-error';
|
import { throwAjaxError } from 'discourse/lib/ajax-error';
|
||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
|
import Draft from 'discourse/models/draft';
|
||||||
|
|
||||||
const CLOSED = 'closed',
|
const CLOSED = 'closed',
|
||||||
SAVING = 'saving',
|
SAVING = 'saving',
|
||||||
@ -274,7 +276,7 @@ const Composer = RestModel.extend({
|
|||||||
**/
|
**/
|
||||||
replyLength: function() {
|
replyLength: function() {
|
||||||
let reply = this.get('reply') || "";
|
let reply = this.get('reply') || "";
|
||||||
while (Discourse.Quote.REGEXP.test(reply)) { reply = reply.replace(Discourse.Quote.REGEXP, ""); }
|
while (Quote.REGEXP.test(reply)) { reply = reply.replace(Quote.REGEXP, ""); }
|
||||||
return reply.replace(/\s+/img, " ").trim().length;
|
return reply.replace(/\s+/img, " ").trim().length;
|
||||||
}.property('reply'),
|
}.property('reply'),
|
||||||
|
|
||||||
@ -662,7 +664,7 @@ const Composer = RestModel.extend({
|
|||||||
}
|
}
|
||||||
|
|
||||||
// try to save the draft
|
// try to save the draft
|
||||||
return Discourse.Draft.save(this.get('draftKey'), this.get('draftSequence'), data)
|
return Draft.save(this.get('draftKey'), this.get('draftSequence'), data)
|
||||||
.then(function() {
|
.then(function() {
|
||||||
composer.set('draftStatus', I18n.t('composer.saved_draft_tip'));
|
composer.set('draftStatus', I18n.t('composer.saved_draft_tip'));
|
||||||
}).catch(function() {
|
}).catch(function() {
|
||||||
@ -706,7 +708,7 @@ Composer.reopenClass({
|
|||||||
}
|
}
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
draft = null;
|
draft = null;
|
||||||
Discourse.Draft.clear(draftKey, draftSequence);
|
Draft.clear(draftKey, draftSequence);
|
||||||
}
|
}
|
||||||
if (draft && ((draft.title && draft.title !== '') || (draft.reply && draft.reply !== ''))) {
|
if (draft && ((draft.title && draft.title !== '') || (draft.reply && draft.reply !== ''))) {
|
||||||
return this.open({
|
return this.open({
|
||||||
|
@ -1,16 +1,8 @@
|
|||||||
/**
|
const Draft = Discourse.Model.extend();
|
||||||
A data model representing a draft post
|
|
||||||
|
|
||||||
@class Draft
|
Draft.reopenClass({
|
||||||
@extends Discourse.Model
|
|
||||||
@namespace Discourse
|
|
||||||
@module Discourse
|
|
||||||
**/
|
|
||||||
Discourse.Draft = Discourse.Model.extend({});
|
|
||||||
|
|
||||||
Discourse.Draft.reopenClass({
|
clear(key, sequence) {
|
||||||
|
|
||||||
clear: function(key, sequence) {
|
|
||||||
return Discourse.ajax("/draft.json", {
|
return Discourse.ajax("/draft.json", {
|
||||||
type: 'DELETE',
|
type: 'DELETE',
|
||||||
data: {
|
data: {
|
||||||
@ -20,19 +12,19 @@ Discourse.Draft.reopenClass({
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
get: function(key) {
|
get(key) {
|
||||||
return Discourse.ajax('/draft.json', {
|
return Discourse.ajax('/draft.json', {
|
||||||
data: { draft_key: key },
|
data: { draft_key: key },
|
||||||
dataType: 'json'
|
dataType: 'json'
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
getLocal: function(key, current) {
|
getLocal(key, current) {
|
||||||
// TODO: implement this
|
// TODO: implement this
|
||||||
return current;
|
return current;
|
||||||
},
|
},
|
||||||
|
|
||||||
save: function(key, sequence, data) {
|
save(key, sequence, data) {
|
||||||
data = typeof data === "string" ? data : JSON.stringify(data);
|
data = typeof data === "string" ? data : JSON.stringify(data);
|
||||||
return Discourse.ajax("/draft.json", {
|
return Discourse.ajax("/draft.json", {
|
||||||
type: 'POST',
|
type: 'POST',
|
||||||
@ -45,3 +37,5 @@ Discourse.Draft.reopenClass({
|
|||||||
}
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
export default Draft;
|
@ -1,15 +1,6 @@
|
|||||||
/**
|
const Invite = Discourse.Model.extend({
|
||||||
A data model representing an Invite
|
|
||||||
|
|
||||||
@class Invite
|
rescind() {
|
||||||
@extends Discourse.Model
|
|
||||||
@namespace Discourse
|
|
||||||
@module Discourse
|
|
||||||
**/
|
|
||||||
|
|
||||||
Discourse.Invite = Discourse.Model.extend({
|
|
||||||
|
|
||||||
rescind: function() {
|
|
||||||
Discourse.ajax('/invites', {
|
Discourse.ajax('/invites', {
|
||||||
type: 'DELETE',
|
type: 'DELETE',
|
||||||
data: { email: this.get('email') }
|
data: { email: this.get('email') }
|
||||||
@ -17,7 +8,7 @@ Discourse.Invite = Discourse.Model.extend({
|
|||||||
this.set('rescinded', true);
|
this.set('rescinded', true);
|
||||||
},
|
},
|
||||||
|
|
||||||
reinvite: function() {
|
reinvite() {
|
||||||
Discourse.ajax('/invites/reinvite', {
|
Discourse.ajax('/invites/reinvite', {
|
||||||
type: 'POST',
|
type: 'POST',
|
||||||
data: { email: this.get('email') }
|
data: { email: this.get('email') }
|
||||||
@ -27,9 +18,9 @@ Discourse.Invite = Discourse.Model.extend({
|
|||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
Discourse.Invite.reopenClass({
|
Invite.reopenClass({
|
||||||
|
|
||||||
create: function() {
|
create() {
|
||||||
var result = this._super.apply(this, arguments);
|
var result = this._super.apply(this, arguments);
|
||||||
if (result.user) {
|
if (result.user) {
|
||||||
result.user = Discourse.User.create(result.user);
|
result.user = Discourse.User.create(result.user);
|
||||||
@ -37,7 +28,7 @@ Discourse.Invite.reopenClass({
|
|||||||
return result;
|
return result;
|
||||||
},
|
},
|
||||||
|
|
||||||
findInvitedBy: function(user, filter, search, offset) {
|
findInvitedBy(user, filter, search, offset) {
|
||||||
if (!user) { return Em.RSVP.resolve(); }
|
if (!user) { return Em.RSVP.resolve(); }
|
||||||
|
|
||||||
var data = {};
|
var data = {};
|
||||||
@ -45,9 +36,9 @@ Discourse.Invite.reopenClass({
|
|||||||
if (!Em.isNone(search)) { data.search = search; }
|
if (!Em.isNone(search)) { data.search = search; }
|
||||||
data.offset = offset || 0;
|
data.offset = offset || 0;
|
||||||
|
|
||||||
return Discourse.ajax("/users/" + user.get('username_lower') + "/invited.json", {data: data}).then(function (result) {
|
return Discourse.ajax("/users/" + user.get('username_lower') + "/invited.json", {data}).then(function (result) {
|
||||||
result.invites = result.invites.map(function (i) {
|
result.invites = result.invites.map(function (i) {
|
||||||
return Discourse.Invite.create(i);
|
return Invite.create(i);
|
||||||
});
|
});
|
||||||
|
|
||||||
return Em.Object.create(result);
|
return Em.Object.create(result);
|
||||||
@ -55,3 +46,5 @@ Discourse.Invite.reopenClass({
|
|||||||
}
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
|
|
||||||
|
export default Invite;
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
import RestModel from 'discourse/models/rest';
|
import RestModel from 'discourse/models/rest';
|
||||||
|
|
||||||
function calcDayDiff(p1, p2) {
|
function calcDayDiff(p1, p2) {
|
||||||
@ -159,7 +160,7 @@ const PostStream = RestModel.extend({
|
|||||||
const posts = this.get('posts');
|
const posts = this.get('posts');
|
||||||
if (posts.length > 1) {
|
if (posts.length > 1) {
|
||||||
const secondPostNum = posts[1].get('post_number');
|
const secondPostNum = posts[1].get('post_number');
|
||||||
Discourse.URL.jumpToPost(secondPostNum);
|
DiscourseURL.jumpToPost(secondPostNum);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@ import RestModel from 'discourse/models/rest';
|
|||||||
import { popupAjaxError } from 'discourse/lib/ajax-error';
|
import { popupAjaxError } from 'discourse/lib/ajax-error';
|
||||||
import ActionSummary from 'discourse/models/action-summary';
|
import ActionSummary from 'discourse/models/action-summary';
|
||||||
import { url, fmt, propertyEqual } from 'discourse/lib/computed';
|
import { url, fmt, propertyEqual } from 'discourse/lib/computed';
|
||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
|
|
||||||
const Post = RestModel.extend({
|
const Post = RestModel.extend({
|
||||||
|
|
||||||
@ -418,7 +419,7 @@ Post.reopenClass({
|
|||||||
loadQuote(postId) {
|
loadQuote(postId) {
|
||||||
return Discourse.ajax("/posts/" + postId + ".json").then(function (result) {
|
return Discourse.ajax("/posts/" + postId + ".json").then(function (result) {
|
||||||
const post = Discourse.Post.create(result);
|
const post = Discourse.Post.create(result);
|
||||||
return Discourse.Quote.build(post, post.get('raw'), {raw: true, full: true});
|
return Quote.build(post, post.get('raw'), {raw: true, full: true});
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -1,35 +0,0 @@
|
|||||||
// this allows you to track the selected item in an array, ghetto for now
|
|
||||||
Discourse.SelectableArray = Em.ArrayProxy.extend({
|
|
||||||
|
|
||||||
init: function() {
|
|
||||||
this.content = [];
|
|
||||||
this._super();
|
|
||||||
},
|
|
||||||
|
|
||||||
selectIndex: function(index){
|
|
||||||
this.select(this[index]);
|
|
||||||
},
|
|
||||||
|
|
||||||
select: function(selected){
|
|
||||||
_.each(this.content,function(item){
|
|
||||||
if(item === selected){
|
|
||||||
Em.set(item, "active", true);
|
|
||||||
} else {
|
|
||||||
if (item.get("active")) {
|
|
||||||
Em.set(item, "active", false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
this.set("active", selected);
|
|
||||||
},
|
|
||||||
|
|
||||||
removeObject: function(object) {
|
|
||||||
if(object === this.get("active")){
|
|
||||||
this.set("active", null);
|
|
||||||
Em.set(object, "active", false);
|
|
||||||
}
|
|
||||||
|
|
||||||
this._super(object);
|
|
||||||
}
|
|
||||||
|
|
||||||
});
|
|
@ -1,4 +1,5 @@
|
|||||||
import Topic from 'discourse/models/topic';
|
import Topic from 'discourse/models/topic';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
export default Discourse.Route.extend({
|
export default Discourse.Route.extend({
|
||||||
model: function(params) {
|
model: function(params) {
|
||||||
@ -6,6 +7,6 @@ export default Discourse.Route.extend({
|
|||||||
},
|
},
|
||||||
|
|
||||||
afterModel: function(result) {
|
afterModel: function(result) {
|
||||||
Discourse.URL.routeTo(result.url, { replaceURL: true });
|
DiscourseURL.routeTo(result.url, { replaceURL: true });
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
@ -1,3 +1,6 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
import Draft from 'discourse/models/draft';
|
||||||
|
|
||||||
// This route is used for retrieving a topic based on params
|
// This route is used for retrieving a topic based on params
|
||||||
export default Discourse.Route.extend({
|
export default Discourse.Route.extend({
|
||||||
|
|
||||||
@ -43,12 +46,11 @@ export default Discourse.Route.extend({
|
|||||||
Ember.run.scheduleOnce('afterRender', function() {
|
Ember.run.scheduleOnce('afterRender', function() {
|
||||||
self.appEvents.trigger('post:highlight', closest);
|
self.appEvents.trigger('post:highlight', closest);
|
||||||
});
|
});
|
||||||
|
DiscourseURL.jumpToPost(closest);
|
||||||
Discourse.URL.jumpToPost(closest);
|
|
||||||
|
|
||||||
if (topic.present('draft')) {
|
if (topic.present('draft')) {
|
||||||
composerController.open({
|
composerController.open({
|
||||||
draft: Discourse.Draft.getLocal(topic.get('draft_key'), topic.get('draft')),
|
draft: Draft.getLocal(topic.get('draft_key'), topic.get('draft')),
|
||||||
draftKey: topic.get('draft_key'),
|
draftKey: topic.get('draft_key'),
|
||||||
draftSequence: topic.get('draft_sequence'),
|
draftSequence: topic.get('draft_sequence'),
|
||||||
topic: topic,
|
topic: topic,
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
import ScreenTrack from 'discourse/lib/screen-track';
|
import ScreenTrack from 'discourse/lib/screen-track';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
let isTransitioning = false,
|
let isTransitioning = false,
|
||||||
scheduledReplace = null,
|
scheduledReplace = null,
|
||||||
@ -128,7 +129,7 @@ const TopicRoute = Discourse.Route.extend({
|
|||||||
_replaceUnlessScrolling(url) {
|
_replaceUnlessScrolling(url) {
|
||||||
const currentPos = parseInt($(document).scrollTop(), 10);
|
const currentPos = parseInt($(document).scrollTop(), 10);
|
||||||
if (currentPos === lastScrollPos) {
|
if (currentPos === lastScrollPos) {
|
||||||
Discourse.URL.replaceState(url);
|
DiscourseURL.replaceState(url);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
lastScrollPos = currentPos;
|
lastScrollPos = currentPos;
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import Draft from 'discourse/models/draft';
|
||||||
|
|
||||||
export default Discourse.Route.extend({
|
export default Discourse.Route.extend({
|
||||||
model() {
|
model() {
|
||||||
return this.modelFor("user");
|
return this.modelFor("user");
|
||||||
@ -10,7 +12,7 @@ export default Discourse.Route.extend({
|
|||||||
const composerController = this.controllerFor("composer");
|
const composerController = this.controllerFor("composer");
|
||||||
controller.set("model", user);
|
controller.set("model", user);
|
||||||
if (this.currentUser) {
|
if (this.currentUser) {
|
||||||
Discourse.Draft.get("new_private_message").then(function(data) {
|
Draft.get("new_private_message").then(function(data) {
|
||||||
if (data.draft) {
|
if (data.draft) {
|
||||||
composerController.open({
|
composerController.open({
|
||||||
draft: data.draft,
|
draft: data.draft,
|
||||||
|
@ -1,10 +1,11 @@
|
|||||||
|
import Invite from 'discourse/models/invite';
|
||||||
import showModal from "discourse/lib/show-modal";
|
import showModal from "discourse/lib/show-modal";
|
||||||
|
|
||||||
export default Discourse.Route.extend({
|
export default Discourse.Route.extend({
|
||||||
|
|
||||||
model(params) {
|
model(params) {
|
||||||
this.inviteFilter = params.filter;
|
this.inviteFilter = params.filter;
|
||||||
return Discourse.Invite.findInvitedBy(this.modelFor("user"), params.filter);
|
return Invite.findInvitedBy(this.modelFor("user"), params.filter);
|
||||||
},
|
},
|
||||||
|
|
||||||
afterModel(model) {
|
afterModel(model) {
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import searchForTerm from 'discourse/lib/search-for-term';
|
import searchForTerm from 'discourse/lib/search-for-term';
|
||||||
|
|
||||||
export default Discourse.View.extend({
|
export default Discourse.View.extend({
|
||||||
@ -18,7 +19,7 @@ export default Discourse.View.extend({
|
|||||||
this.set('loading', false);
|
this.set('loading', false);
|
||||||
}.observes('topics'),
|
}.observes('topics'),
|
||||||
|
|
||||||
search: Discourse.debounce(function(title) {
|
search: debounce(function(title) {
|
||||||
var self = this;
|
var self = this;
|
||||||
if (Em.isEmpty(title)) {
|
if (Em.isEmpty(title)) {
|
||||||
self.setProperties({ topics: null, loading: false });
|
self.setProperties({ topics: null, loading: false });
|
||||||
|
@ -3,6 +3,7 @@ import afterTransition from 'discourse/lib/after-transition';
|
|||||||
import loadScript from 'discourse/lib/load-script';
|
import loadScript from 'discourse/lib/load-script';
|
||||||
import avatarTemplate from 'discourse/lib/avatar-template';
|
import avatarTemplate from 'discourse/lib/avatar-template';
|
||||||
import positioningWorkaround from 'discourse/lib/safari-hacks';
|
import positioningWorkaround from 'discourse/lib/safari-hacks';
|
||||||
|
import debounce from 'discourse/lib/debounce';
|
||||||
import { linkSeenMentions, fetchUnseenMentions } from 'discourse/lib/link-mentions';
|
import { linkSeenMentions, fetchUnseenMentions } from 'discourse/lib/link-mentions';
|
||||||
|
|
||||||
const ComposerView = Discourse.View.extend(Ember.Evented, {
|
const ComposerView = Discourse.View.extend(Ember.Evented, {
|
||||||
@ -40,7 +41,7 @@ const ComposerView = Discourse.View.extend(Ember.Evented, {
|
|||||||
return this.present('model.createdPost') ? 'created-post' : null;
|
return this.present('model.createdPost') ? 'created-post' : null;
|
||||||
}.property('model.createdPost'),
|
}.property('model.createdPost'),
|
||||||
|
|
||||||
refreshPreview: Discourse.debounce(function() {
|
refreshPreview: debounce(function() {
|
||||||
if (this.editor) {
|
if (this.editor) {
|
||||||
this.editor.refreshPreview();
|
this.editor.refreshPreview();
|
||||||
}
|
}
|
||||||
@ -279,7 +280,7 @@ const ComposerView = Discourse.View.extend(Ember.Evented, {
|
|||||||
this.set('editor', this.editor);
|
this.set('editor', this.editor);
|
||||||
this.loadingChanged();
|
this.loadingChanged();
|
||||||
|
|
||||||
const saveDraft = Discourse.debounce((function() {
|
const saveDraft = debounce((function() {
|
||||||
return self.get('controller').saveDraft();
|
return self.get('controller').saveDraft();
|
||||||
}), 2000);
|
}), 2000);
|
||||||
|
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import ScreenTrack from 'discourse/lib/screen-track';
|
import ScreenTrack from 'discourse/lib/screen-track';
|
||||||
import { number } from 'discourse/lib/formatter';
|
import { number } from 'discourse/lib/formatter';
|
||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
const DAY = 60 * 50 * 1000;
|
const DAY = 60 * 50 * 1000;
|
||||||
|
|
||||||
@ -199,7 +200,7 @@ const PostView = Discourse.GroupedView.extend(Ember.Evented, {
|
|||||||
self = this;
|
self = this;
|
||||||
|
|
||||||
if (Discourse.Mobile.mobileView) {
|
if (Discourse.Mobile.mobileView) {
|
||||||
Discourse.URL.routeTo(this.get('post.topic').urlForPostNumber(replyPostNumber));
|
DiscourseURL.routeTo(this.get('post.topic').urlForPostNumber(replyPostNumber));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -9,6 +9,9 @@
|
|||||||
//= require ./discourse/lib/notification-levels
|
//= require ./discourse/lib/notification-levels
|
||||||
//= require ./discourse/lib/app-events
|
//= require ./discourse/lib/app-events
|
||||||
//= require ./discourse/lib/avatar-template
|
//= require ./discourse/lib/avatar-template
|
||||||
|
//= require ./discourse/lib/url
|
||||||
|
//= require ./discourse/lib/debounce
|
||||||
|
//= require ./discourse/lib/quote
|
||||||
//= require ./discourse/helpers/i18n
|
//= require ./discourse/helpers/i18n
|
||||||
//= require ./discourse/helpers/fa-icon
|
//= require ./discourse/helpers/fa-icon
|
||||||
//= require ./discourse/helpers/register-unbound
|
//= require ./discourse/helpers/register-unbound
|
||||||
@ -41,7 +44,9 @@
|
|||||||
//= require ./discourse/models/topic-details
|
//= require ./discourse/models/topic-details
|
||||||
//= require ./discourse/models/topic
|
//= require ./discourse/models/topic
|
||||||
//= require ./discourse/models/user-action
|
//= require ./discourse/models/user-action
|
||||||
|
//= require ./discourse/models/draft
|
||||||
//= require ./discourse/models/composer
|
//= require ./discourse/models/composer
|
||||||
|
//= require ./discourse/models/invite
|
||||||
//= require ./discourse/controllers/controller
|
//= require ./discourse/controllers/controller
|
||||||
//= require ./discourse/controllers/discovery-sortable
|
//= require ./discourse/controllers/discovery-sortable
|
||||||
//= require ./discourse/controllers/object
|
//= require ./discourse/controllers/object
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
//= require logster
|
//= require logster
|
||||||
//= require ./env
|
//= require ./env
|
||||||
//= require ./discourse/lib/probes.js
|
//= require probes.js
|
||||||
|
|
||||||
//= require handlebars.js
|
//= require handlebars.js
|
||||||
//= require jquery_include.js
|
//= require jquery_include.js
|
||||||
@ -19,6 +19,8 @@
|
|||||||
//= require bootstrap-modal.js
|
//= require bootstrap-modal.js
|
||||||
//= require bootstrap-transition.js
|
//= require bootstrap-transition.js
|
||||||
//= require select2.js
|
//= require select2.js
|
||||||
|
//= require div_resizer
|
||||||
|
//= require caret_position
|
||||||
//= require favcount.js
|
//= require favcount.js
|
||||||
//= require jquery.ba-replacetext.js
|
//= require jquery.ba-replacetext.js
|
||||||
//= require jquery.ba-resize.min.js
|
//= require jquery.ba-resize.min.js
|
||||||
|
@ -80,7 +80,6 @@ module PrettyText
|
|||||||
"app/assets/javascripts/defer/html-sanitizer-bundle.js",
|
"app/assets/javascripts/defer/html-sanitizer-bundle.js",
|
||||||
"app/assets/javascripts/discourse/dialects/dialect.js",
|
"app/assets/javascripts/discourse/dialects/dialect.js",
|
||||||
"app/assets/javascripts/discourse/lib/utilities.js",
|
"app/assets/javascripts/discourse/lib/utilities.js",
|
||||||
"app/assets/javascripts/discourse/lib/html.js",
|
|
||||||
"app/assets/javascripts/discourse/lib/markdown.js",
|
"app/assets/javascripts/discourse/lib/markdown.js",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
import { acceptance } from "helpers/qunit-helpers";
|
import { acceptance } from "helpers/qunit-helpers";
|
||||||
|
|
||||||
acceptance("Category Edit", { loggedIn: true });
|
acceptance("Category Edit", { loggedIn: true });
|
||||||
@ -24,7 +25,7 @@ test("Change the category color", (assert) => {
|
|||||||
click('#save-category');
|
click('#save-category');
|
||||||
andThen(() => {
|
andThen(() => {
|
||||||
assert.ok(!visible('#discourse-modal'), 'it closes the modal');
|
assert.ok(!visible('#discourse-modal'), 'it closes the modal');
|
||||||
assert.equal(Discourse.URL.redirectedTo, '/c/bug', 'it does one of the rare full page redirects');
|
assert.equal(DiscourseURL.redirectedTo, '/c/bug', 'it does one of the rare full page redirects');
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -37,6 +38,6 @@ test("Change the topic template", (assert) => {
|
|||||||
click('#save-category');
|
click('#save-category');
|
||||||
andThen(() => {
|
andThen(() => {
|
||||||
assert.ok(!visible('#discourse-modal'), 'it closes the modal');
|
assert.ok(!visible('#discourse-modal'), 'it closes the modal');
|
||||||
assert.equal(Discourse.URL.redirectedTo, '/c/bug', 'it does one of the rare full page redirects');
|
assert.equal(DiscourseURL.redirectedTo, '/c/bug', 'it does one of the rare full page redirects');
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
@ -1,6 +1,9 @@
|
|||||||
var testMouseTrap;
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
module("Discourse.KeyboardShortcuts", {
|
var testMouseTrap;
|
||||||
|
import KeyboardShortcuts from 'discourse/lib/keyboard-shortcuts';
|
||||||
|
|
||||||
|
module("lib:keyboard-shortcuts", {
|
||||||
setup: function() {
|
setup: function() {
|
||||||
var _bindings = {};
|
var _bindings = {};
|
||||||
|
|
||||||
@ -23,7 +26,7 @@ module("Discourse.KeyboardShortcuts", {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
sandbox.stub(Discourse.URL, "routeTo");
|
sandbox.stub(DiscourseURL, "routeTo");
|
||||||
|
|
||||||
$("#qunit-fixture").html([
|
$("#qunit-fixture").html([
|
||||||
"<article class='topic-post selected'>",
|
"<article class='topic-post selected'>",
|
||||||
@ -64,20 +67,20 @@ module("Discourse.KeyboardShortcuts", {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
var pathBindings = Discourse.KeyboardShortcuts.PATH_BINDINGS;
|
var pathBindings = KeyboardShortcuts.PATH_BINDINGS;
|
||||||
|
|
||||||
_.each(pathBindings, function(path, binding) {
|
_.each(pathBindings, function(path, binding) {
|
||||||
var testName = binding + " goes to " + path;
|
var testName = binding + " goes to " + path;
|
||||||
|
|
||||||
test(testName, function() {
|
test(testName, function() {
|
||||||
Discourse.KeyboardShortcuts.bindEvents(testMouseTrap);
|
KeyboardShortcuts.bindEvents(testMouseTrap);
|
||||||
testMouseTrap.trigger(binding);
|
testMouseTrap.trigger(binding);
|
||||||
|
|
||||||
ok(Discourse.URL.routeTo.calledWith(path));
|
ok(DiscourseURL.routeTo.calledWith(path));
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
var clickBindings = Discourse.KeyboardShortcuts.CLICK_BINDINGS;
|
var clickBindings = KeyboardShortcuts.CLICK_BINDINGS;
|
||||||
|
|
||||||
_.each(clickBindings, function(selector, binding) {
|
_.each(clickBindings, function(selector, binding) {
|
||||||
var bindings = binding.split(",");
|
var bindings = binding.split(",");
|
||||||
@ -85,7 +88,7 @@ _.each(clickBindings, function(selector, binding) {
|
|||||||
var testName = binding + " clicks on " + selector;
|
var testName = binding + " clicks on " + selector;
|
||||||
|
|
||||||
test(testName, function() {
|
test(testName, function() {
|
||||||
Discourse.KeyboardShortcuts.bindEvents(testMouseTrap);
|
KeyboardShortcuts.bindEvents(testMouseTrap);
|
||||||
$(selector).on("click", function() {
|
$(selector).on("click", function() {
|
||||||
ok(true, selector + " was clicked");
|
ok(true, selector + " was clicked");
|
||||||
});
|
});
|
||||||
@ -96,32 +99,32 @@ _.each(clickBindings, function(selector, binding) {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
var functionBindings = Discourse.KeyboardShortcuts.FUNCTION_BINDINGS;
|
var functionBindings = KeyboardShortcuts.FUNCTION_BINDINGS;
|
||||||
|
|
||||||
_.each(functionBindings, function(func, binding) {
|
_.each(functionBindings, function(func, binding) {
|
||||||
var testName = binding + " calls " + func;
|
var testName = binding + " calls " + func;
|
||||||
|
|
||||||
test(testName, function() {
|
test(testName, function() {
|
||||||
sandbox.stub(Discourse.KeyboardShortcuts, func, function() {
|
sandbox.stub(KeyboardShortcuts, func, function() {
|
||||||
ok(true, func + " is called when " + binding + " is triggered");
|
ok(true, func + " is called when " + binding + " is triggered");
|
||||||
});
|
});
|
||||||
Discourse.KeyboardShortcuts.bindEvents(testMouseTrap);
|
KeyboardShortcuts.bindEvents(testMouseTrap);
|
||||||
|
|
||||||
testMouseTrap.trigger(binding);
|
testMouseTrap.trigger(binding);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
test("selectDown calls _moveSelection with 1", function() {
|
test("selectDown calls _moveSelection with 1", function() {
|
||||||
var spy = sandbox.spy(Discourse.KeyboardShortcuts, '_moveSelection');
|
var spy = sandbox.spy(KeyboardShortcuts, '_moveSelection');
|
||||||
|
|
||||||
Discourse.KeyboardShortcuts.selectDown();
|
KeyboardShortcuts.selectDown();
|
||||||
ok(spy.calledWith(1), "_moveSelection is called with 1");
|
ok(spy.calledWith(1), "_moveSelection is called with 1");
|
||||||
});
|
});
|
||||||
|
|
||||||
test("selectUp calls _moveSelection with -1", function() {
|
test("selectUp calls _moveSelection with -1", function() {
|
||||||
var spy = sandbox.spy(Discourse.KeyboardShortcuts, '_moveSelection');
|
var spy = sandbox.spy(KeyboardShortcuts, '_moveSelection');
|
||||||
|
|
||||||
Discourse.KeyboardShortcuts.selectUp();
|
KeyboardShortcuts.selectUp();
|
||||||
ok(spy.calledWith(-1), "_moveSelection is called with -1");
|
ok(spy.calledWith(-1), "_moveSelection is called with -1");
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -131,20 +134,20 @@ test("goBack calls history.back", function() {
|
|||||||
called = true;
|
called = true;
|
||||||
});
|
});
|
||||||
|
|
||||||
Discourse.KeyboardShortcuts.goBack();
|
KeyboardShortcuts.goBack();
|
||||||
ok(called, "history.back is called");
|
ok(called, "history.back is called");
|
||||||
});
|
});
|
||||||
|
|
||||||
test("nextSection calls _changeSection with 1", function() {
|
test("nextSection calls _changeSection with 1", function() {
|
||||||
var spy = sandbox.spy(Discourse.KeyboardShortcuts, '_changeSection');
|
var spy = sandbox.spy(KeyboardShortcuts, '_changeSection');
|
||||||
|
|
||||||
Discourse.KeyboardShortcuts.nextSection();
|
KeyboardShortcuts.nextSection();
|
||||||
ok(spy.calledWith(1), "_changeSection is called with 1");
|
ok(spy.calledWith(1), "_changeSection is called with 1");
|
||||||
});
|
});
|
||||||
|
|
||||||
test("prevSection calls _changeSection with -1", function() {
|
test("prevSection calls _changeSection with -1", function() {
|
||||||
var spy = sandbox.spy(Discourse.KeyboardShortcuts, '_changeSection');
|
var spy = sandbox.spy(KeyboardShortcuts, '_changeSection');
|
||||||
|
|
||||||
Discourse.KeyboardShortcuts.prevSection();
|
KeyboardShortcuts.prevSection();
|
||||||
ok(spy.calledWith(-1), "_changeSection is called with -1");
|
ok(spy.calledWith(-1), "_changeSection is called with -1");
|
||||||
});
|
});
|
||||||
|
14
test/javascripts/helpers/custom-html-test.js.es6
Normal file
14
test/javascripts/helpers/custom-html-test.js.es6
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
module("helper:custom-html");
|
||||||
|
|
||||||
|
import { getCustomHTML, setCustomHTML } from 'discourse/helpers/custom-html';
|
||||||
|
|
||||||
|
test("customHTML", function() {
|
||||||
|
blank(getCustomHTML('evil'), "there is no custom HTML for a key by default");
|
||||||
|
|
||||||
|
setCustomHTML('evil', 'trout');
|
||||||
|
equal(getCustomHTML('evil'), 'trout', 'it retrieves the custom html');
|
||||||
|
|
||||||
|
PreloadStore.store('customHTML', {cookie: 'monster'});
|
||||||
|
equal(getCustomHTML('cookie'), 'monster', 'it returns HTML fragments from the PreloadStore');
|
||||||
|
|
||||||
|
});
|
8
test/javascripts/helpers/parse-html.js.es6
Normal file
8
test/javascripts/helpers/parse-html.js.es6
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
/* global Tautologistics */
|
||||||
|
export default function parseHTML(rawHtml) {
|
||||||
|
const builder = new Tautologistics.NodeHtmlParser.HtmlBuilder();
|
||||||
|
const parser = new Tautologistics.NodeHtmlParser.Parser(builder);
|
||||||
|
|
||||||
|
parser.parseComplete(rawHtml);
|
||||||
|
return builder.dom;
|
||||||
|
}
|
@ -1,9 +0,0 @@
|
|||||||
/* global Tautologistics */
|
|
||||||
/* exported parseHTML */
|
|
||||||
function parseHTML(rawHtml) {
|
|
||||||
var builder = new Tautologistics.NodeHtmlParser.HtmlBuilder(),
|
|
||||||
parser = new Tautologistics.NodeHtmlParser.Parser(builder);
|
|
||||||
|
|
||||||
parser.parseComplete(rawHtml);
|
|
||||||
return builder.dom;
|
|
||||||
}
|
|
@ -1,3 +1,5 @@
|
|||||||
|
import Quote from 'discourse/lib/quote';
|
||||||
|
|
||||||
module("Discourse.BBCode");
|
module("Discourse.BBCode");
|
||||||
|
|
||||||
var format = function(input, expected, text) {
|
var format = function(input, expected, text) {
|
||||||
@ -90,7 +92,7 @@ test("quotes", function() {
|
|||||||
});
|
});
|
||||||
|
|
||||||
var formatQuote = function(val, expected, text) {
|
var formatQuote = function(val, expected, text) {
|
||||||
equal(Discourse.Quote.build(post, val), expected, text);
|
equal(Quote.build(post, val), expected, text);
|
||||||
};
|
};
|
||||||
|
|
||||||
formatQuote(undefined, "", "empty string for undefined content");
|
formatQuote(undefined, "", "empty string for undefined content");
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
module("lib:category-link");
|
module("lib:category-link");
|
||||||
|
|
||||||
|
import parseHTML from 'helpers/parse-html';
|
||||||
import { categoryBadgeHTML } from "discourse/helpers/category-link";
|
import { categoryBadgeHTML } from "discourse/helpers/category-link";
|
||||||
|
|
||||||
test("categoryBadge without a category", function() {
|
test("categoryBadge without a category", function() {
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import DiscourseURL from "discourse/lib/url";
|
||||||
import ClickTrack from "discourse/lib/click-track";
|
import ClickTrack from "discourse/lib/click-track";
|
||||||
|
|
||||||
var windowOpen,
|
var windowOpen,
|
||||||
@ -9,7 +10,7 @@ module("lib:click-track", {
|
|||||||
|
|
||||||
// Prevent any of these tests from navigating away
|
// Prevent any of these tests from navigating away
|
||||||
win = {focus: function() { } };
|
win = {focus: function() { } };
|
||||||
redirectTo = sandbox.stub(Discourse.URL, "redirectTo");
|
redirectTo = sandbox.stub(DiscourseURL, "redirectTo");
|
||||||
sandbox.stub(Discourse, "ajax");
|
sandbox.stub(Discourse, "ajax");
|
||||||
windowOpen = sandbox.stub(window, "open").returns(win);
|
windowOpen = sandbox.stub(window, "open").returns(win);
|
||||||
sandbox.stub(win, "focus");
|
sandbox.stub(win, "focus");
|
||||||
@ -51,7 +52,7 @@ test("it calls preventDefault when clicking on an a", function() {
|
|||||||
sandbox.stub(clickEvent, "preventDefault");
|
sandbox.stub(clickEvent, "preventDefault");
|
||||||
track(clickEvent);
|
track(clickEvent);
|
||||||
ok(clickEvent.preventDefault.calledOnce);
|
ok(clickEvent.preventDefault.calledOnce);
|
||||||
ok(Discourse.URL.redirectTo.calledOnce);
|
ok(DiscourseURL.redirectTo.calledOnce);
|
||||||
});
|
});
|
||||||
|
|
||||||
test("does not track clicks on back buttons", function() {
|
test("does not track clicks on back buttons", function() {
|
||||||
@ -70,7 +71,7 @@ test("removes the href and put it as a data attribute", function() {
|
|||||||
equal($link.data('href'), 'http://www.google.com');
|
equal($link.data('href'), 'http://www.google.com');
|
||||||
blank($link.attr('href'));
|
blank($link.attr('href'));
|
||||||
ok($link.data('auto-route'));
|
ok($link.data('auto-route'));
|
||||||
ok(Discourse.URL.redirectTo.calledOnce);
|
ok(DiscourseURL.redirectTo.calledOnce);
|
||||||
});
|
});
|
||||||
|
|
||||||
asyncTest("restores the href after a while", function() {
|
asyncTest("restores the href after a while", function() {
|
||||||
@ -159,20 +160,20 @@ testOpenInANewTab("it opens in a new tab on middle click", function(clickEvent)
|
|||||||
});
|
});
|
||||||
|
|
||||||
test("tracks via AJAX if we're on the same site", function() {
|
test("tracks via AJAX if we're on the same site", function() {
|
||||||
sandbox.stub(Discourse.URL, "routeTo");
|
sandbox.stub(DiscourseURL, "routeTo");
|
||||||
sandbox.stub(Discourse.URL, "origin").returns("http://discuss.domain.com");
|
sandbox.stub(DiscourseURL, "origin").returns("http://discuss.domain.com");
|
||||||
|
|
||||||
ok(!track(generateClickEventOn('#same-site')));
|
ok(!track(generateClickEventOn('#same-site')));
|
||||||
ok(Discourse.ajax.calledOnce);
|
ok(Discourse.ajax.calledOnce);
|
||||||
ok(Discourse.URL.routeTo.calledOnce);
|
ok(DiscourseURL.routeTo.calledOnce);
|
||||||
});
|
});
|
||||||
|
|
||||||
test("does not track via AJAX for attachments", function() {
|
test("does not track via AJAX for attachments", function() {
|
||||||
sandbox.stub(Discourse.URL, "routeTo");
|
sandbox.stub(DiscourseURL, "routeTo");
|
||||||
sandbox.stub(Discourse.URL, "origin").returns("http://discuss.domain.com");
|
sandbox.stub(DiscourseURL, "origin").returns("http://discuss.domain.com");
|
||||||
|
|
||||||
ok(!track(generateClickEventOn('.attachment')));
|
ok(!track(generateClickEventOn('.attachment')));
|
||||||
ok(Discourse.URL.redirectTo.calledOnce);
|
ok(DiscourseURL.redirectTo.calledOnce);
|
||||||
});
|
});
|
||||||
|
|
||||||
test("tracks custom urls when opening in another window", function() {
|
test("tracks custom urls when opening in another window", function() {
|
||||||
|
@ -1,14 +0,0 @@
|
|||||||
module("Discourse.HTML");
|
|
||||||
|
|
||||||
var html = Discourse.HTML;
|
|
||||||
|
|
||||||
test("customHTML", function() {
|
|
||||||
blank(html.getCustomHTML('evil'), "there is no custom HTML for a key by default");
|
|
||||||
|
|
||||||
html.setCustomHTML('evil', 'trout');
|
|
||||||
equal(html.getCustomHTML('evil'), 'trout', 'it retrieves the custom html');
|
|
||||||
|
|
||||||
PreloadStore.store('customHTML', {cookie: 'monster'});
|
|
||||||
equal(html.getCustomHTML('cookie'), 'monster', 'it returns HTML fragments from the PreloadStore');
|
|
||||||
|
|
||||||
});
|
|
@ -1,16 +1,18 @@
|
|||||||
module("Discourse.URL");
|
import DiscourseURL from 'discourse/lib/url';
|
||||||
|
|
||||||
|
module("lib:url");
|
||||||
|
|
||||||
test("isInternal with a HTTP url", function() {
|
test("isInternal with a HTTP url", function() {
|
||||||
sandbox.stub(Discourse.URL, "origin").returns("http://eviltrout.com");
|
sandbox.stub(DiscourseURL, "origin").returns("http://eviltrout.com");
|
||||||
|
|
||||||
not(Discourse.URL.isInternal(null), "a blank URL is not internal");
|
not(DiscourseURL.isInternal(null), "a blank URL is not internal");
|
||||||
ok(Discourse.URL.isInternal("/test"), "relative URLs are internal");
|
ok(DiscourseURL.isInternal("/test"), "relative URLs are internal");
|
||||||
ok(Discourse.URL.isInternal("http://eviltrout.com/tophat"), "a url on the same host is internal");
|
ok(DiscourseURL.isInternal("http://eviltrout.com/tophat"), "a url on the same host is internal");
|
||||||
ok(Discourse.URL.isInternal("https://eviltrout.com/moustache"), "a url on a HTTPS of the same host is internal");
|
ok(DiscourseURL.isInternal("https://eviltrout.com/moustache"), "a url on a HTTPS of the same host is internal");
|
||||||
not(Discourse.URL.isInternal("http://twitter.com"), "a different host is not internal");
|
not(DiscourseURL.isInternal("http://twitter.com"), "a different host is not internal");
|
||||||
});
|
});
|
||||||
|
|
||||||
test("isInternal with a HTTPS url", function() {
|
test("isInternal with a HTTPS url", function() {
|
||||||
sandbox.stub(Discourse.URL, "origin").returns("https://eviltrout.com");
|
sandbox.stub(DiscourseURL, "origin").returns("https://eviltrout.com");
|
||||||
ok(Discourse.URL.isInternal("http://eviltrout.com/monocle"), "HTTPS urls match HTTP urls");
|
ok(DiscourseURL.isInternal("http://eviltrout.com/monocle"), "HTTPS urls match HTTP urls");
|
||||||
});
|
});
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
module("Discourse.Invite");
|
import Invite from 'discourse/models/invite';
|
||||||
|
|
||||||
|
module("model:invite");
|
||||||
|
|
||||||
test("create", function() {
|
test("create", function() {
|
||||||
ok(Discourse.Invite.create(), "it can be created without arguments");
|
ok(Invite.create(), "it can be created without arguments");
|
||||||
});
|
});
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
//= require ../../app/assets/javascripts/preload_store
|
//= require ../../app/assets/javascripts/preload_store
|
||||||
|
|
||||||
// probe framework first
|
// probe framework first
|
||||||
//= require ../../app/assets/javascripts/discourse/lib/probes
|
//= require probes
|
||||||
|
|
||||||
// Externals we need to load first
|
// Externals we need to load first
|
||||||
//= require jquery.debug
|
//= require jquery.debug
|
||||||
@ -80,6 +80,7 @@ var origDebounce = Ember.run.debounce,
|
|||||||
fixtures = require('fixtures/site_fixtures', null, null, false).default,
|
fixtures = require('fixtures/site_fixtures', null, null, false).default,
|
||||||
flushMap = require('discourse/models/store', null, null, false).flushMap,
|
flushMap = require('discourse/models/store', null, null, false).flushMap,
|
||||||
ScrollingDOMMethods = require('discourse/mixins/scrolling', null, null, false).ScrollingDOMMethods,
|
ScrollingDOMMethods = require('discourse/mixins/scrolling', null, null, false).ScrollingDOMMethods,
|
||||||
|
_DiscourseURL = require('discourse/lib/url', null, null, false).default,
|
||||||
server;
|
server;
|
||||||
|
|
||||||
function dup(obj) {
|
function dup(obj) {
|
||||||
@ -97,9 +98,9 @@ QUnit.testStart(function(ctx) {
|
|||||||
Discourse.User.resetCurrent();
|
Discourse.User.resetCurrent();
|
||||||
Discourse.Site.resetCurrent(Discourse.Site.create(dup(fixtures['site.json'].site)));
|
Discourse.Site.resetCurrent(Discourse.Site.create(dup(fixtures['site.json'].site)));
|
||||||
|
|
||||||
Discourse.URL.redirectedTo = null;
|
_DiscourseURL.redirectedTo = null;
|
||||||
Discourse.URL.redirectTo = function(url) {
|
_DiscourseURL.redirectTo = function(url) {
|
||||||
Discourse.URL.redirectedTo = url;
|
_DiscourseURL.redirectedTo = url;
|
||||||
};
|
};
|
||||||
|
|
||||||
PreloadStore.reset();
|
PreloadStore.reset();
|
||||||
|
Reference in New Issue
Block a user