1
0
mirror of https://github.com/flarum/core.git synced 2025-08-13 11:54:32 +02:00

Update for new API

This commit is contained in:
Toby Zerner
2015-07-23 16:40:54 +09:30
parent 5ea3579f76
commit 3729a91be3
34 changed files with 712 additions and 406 deletions

View File

@@ -1,93 +0,0 @@
import { extend, override } from 'flarum/extension-utils';
import app from 'flarum/app';
import Model from 'flarum/model';
import Component from 'flarum/component';
import Discussion from 'flarum/models/discussion';
import Badge from 'flarum/components/badge';
import ActionButton from 'flarum/components/action-button';
import SettingsPage from 'flarum/components/settings-page';
import DiscussionPage from 'flarum/components/discussion-page';
import IndexPage from 'flarum/components/index-page';
import IndexNavItem from 'flarum/components/index-nav-item';
import DiscussionList from 'flarum/components/discussion-list';
import icon from 'flarum/helpers/icon';
import SubscriptionMenu from 'flarum-subscriptions/components/subscription-menu';
import NewPostNotification from 'flarum-subscriptions/components/new-post-notification';
app.initializers.add('flarum-subscriptions', function() {
app.notificationComponentRegistry['newPost'] = NewPostNotification;
Discussion.prototype.subscription = Model.prop('subscription');
// Add subscription badges to discussions.
extend(Discussion.prototype, 'badges', function(badges) {
var badge;
switch (this.subscription()) {
case 'follow':
badge = Badge.component({ label: 'Following', icon: 'star', className: 'badge-follow' });
break;
case 'ignore':
badge = Badge.component({ label: 'Ignoring', icon: 'eye-slash', className: 'badge-ignore' });
}
if (badge) {
badges.add('subscription', badge);
}
});
extend(Discussion.prototype, 'userControls', function(items, context) {
if (app.session.user() && !(context instanceof DiscussionPage)) {
var states = {
none: {label: 'Follow', icon: 'star', save: 'follow'},
follow: {label: 'Unfollow', icon: 'star-o', save: false},
ignore: {label: 'Unignore', icon: 'eye', save: false}
};
var subscription = this.subscription() || 'none';
items.add('subscription', ActionButton.component({
label: states[subscription].label,
icon: states[subscription].icon,
onclick: this.save.bind(this, {subscription: states[subscription].save})
}));
}
});
extend(DiscussionPage.prototype, 'sidebarItems', function(items) {
if (app.session.user()) {
var discussion = this.discussion();
items.add('subscription', SubscriptionMenu.component({discussion}), {after: 'controls'});
}
});
extend(IndexPage.prototype, 'navItems', function(items) {
if (app.session.user()) {
var params = this.stickyParams();
params.filter = 'following';
items.add('following', IndexNavItem.component({
href: app.route('index.filter', params),
label: 'Following',
icon: 'star'
}), {after: 'allDiscussions'});
}
});
extend(DiscussionList.prototype, 'params', function(params) {
if (params.filter === 'following') {
params.q = (params.q || '')+' is:following';
}
});
// Add a notification preference.
extend(SettingsPage.prototype, 'notificationTypes', function(items) {
items.add('newPost', {
name: 'newPost',
label: [icon('star'), " Someone posts in a discussion I'm following"]
});
});
});

View File

@@ -1,5 +1,5 @@
var gulp = require('flarum-gulp');
gulp({
modulePrefix: 'flarum-subscriptions'
modulePrefix: 'subscriptions'
});

View File

@@ -0,0 +1,34 @@
import { extend } from 'flarum/extend';
import Discussion from 'flarum/models/Discussion';
import Badge from 'flarum/components/Badge';
export default function addSubscriptionBadge() {
extend(Discussion.prototype, 'badges', function(badges) {
let badge;
switch (this.subscription()) {
case 'follow':
badge = Badge.component({
label: app.trans('subscriptions.following'),
icon: 'star',
type: 'following'
});
break;
case 'ignore':
badge = Badge.component({
label: app.trans('subscriptions.ignoring'),
icon: 'eye-slash',
type: 'ignoring'
});
break;
default:
// no default
}
if (badge) {
badges.add('subscription', badge);
}
});
}

View File

@@ -0,0 +1,34 @@
import { extend } from 'flarum/extend';
import Button from 'flarum/components/Button';
import DiscussionPage from 'flarum/components/DiscussionPage';
import DiscussionControls from 'flarum/utils/DiscussionControls';
import SubscriptionMenu from 'subscriptions/components/SubscriptionMenu';
export default function addSubscriptionControls() {
extend(DiscussionControls, 'userControls', function(items, discussion, context) {
if (app.session.user && !(context instanceof DiscussionPage)) {
const states = {
none: {label: app.trans('subscriptions.follow'), icon: 'star', save: 'follow'},
follow: {label: app.trans('subscriptions.unfollow'), icon: 'star-o', save: false},
ignore: {label: app.trans('subscriptions.unignore'), icon: 'eye', save: false}
};
const subscription = discussion.subscription() || 'none';
items.add('subscription', Button.component({
children: states[subscription].label,
icon: states[subscription].icon,
onclick: discussion.save.bind(discussion, {subscription: states[subscription].save})
}));
}
});
extend(DiscussionPage.prototype, 'sidebarItems', function(items) {
if (app.session.user) {
const discussion = this.discussion;
items.add('subscription', SubscriptionMenu.component({discussion}));
}
});
}

View File

@@ -0,0 +1,26 @@
import { extend } from 'flarum/extend';
import LinkButton from 'flarum/components/LinkButton';
import IndexPage from 'flarum/components/IndexPage';
import DiscussionList from 'flarum/components/DiscussionList';
export default function addSubscriptionControls() {
extend(IndexPage.prototype, 'navItems', function(items) {
if (app.session.user) {
const params = this.stickyParams();
params.filter = 'following';
items.add('following', LinkButton.component({
href: app.route('index.filter', params),
children: app.trans('subscriptions.following'),
icon: 'star'
}), 50);
}
});
extend(DiscussionList.prototype, 'requestParams', function(params) {
if (params.filter === 'following') {
params.q = (params.q || '') + ' is:following';
}
});
}

View File

@@ -0,0 +1,20 @@
import Notification from 'flarum/components/Notification';
import username from 'flarum/helpers/username';
export default class NewPostNotification extends Notification {
icon() {
return 'star';
}
href() {
const notification = this.props.notification;
const discussion = notification.subject();
const content = notification.content() || {};
return app.route.discussion(discussion, content.postNumber);
}
content() {
return app.trans('subscriptions.new_post_notification', {user: this.props.notification.sender()});
}
}

View File

@@ -0,0 +1,80 @@
import Component from 'flarum/Component';
import Button from 'flarum/components/Button';
import icon from 'flarum/helpers/icon';
import SubscriptionMenuItem from 'subscriptions/components/SubscriptionMenuItem';
export default class SubscriptionMenu extends Component {
view() {
const discussion = this.props.discussion;
const subscription = discussion.subscription();
let buttonLabel = app.trans('subscriptions.follow');
let buttonIcon = 'star-o';
const buttonClass = 'SubscriptionMenu-button--' + subscription;
switch (subscription) {
case 'follow':
buttonLabel = app.trans('subscriptions.following');
buttonIcon = 'star';
break;
case 'ignore':
buttonLabel = app.trans('subscriptions.ignoring');
buttonIcon = 'eye-slash';
break;
default:
// no default
}
const options = [
{
subscription: false,
icon: 'star-o',
label: app.trans('subscriptions.not_following'),
description: app.trans('subscriptions.not_following_description')
},
{
subscription: 'follow',
icon: 'star',
label: app.trans('subscriptions.following'),
description: app.trans('subscriptions.following_description')
},
{
subscription: 'ignore',
icon: 'eye-slash',
label: app.trans('subscriptions.ignoring'),
description: app.trans('subscriptions.ignoring_description')
}
];
return (
<div className="Dropdown ButtonGroup SubscriptionMenu">
{Button.component({
className: 'Button SubscriptionMenu-button ' + buttonClass,
icon: buttonIcon,
children: buttonLabel,
onclick: this.saveSubscription.bind(this, discussion, ['follow', 'ignore'].indexOf(subscription) !== -1 ? false : 'follow')
})}
<button className={'Dropdown-toggle Button Button--icon ' + buttonClass} data-toggle="dropdown">
{icon('caret-down', {className: 'Button-icon'})}
</button>
<ul className="Dropdown-menu dropdown-menu Dropdown-menu--right">
{options.map(props => {
props.onclick = this.saveSubscription.bind(this, discussion, props.subscription);
props.active = subscription === props.subscription;
return <li>{SubscriptionMenuItem.component(props)}</li>;
})}
</ul>
</div>
);
}
saveSubscription(discussion, subscription) {
discussion.save({subscription});
}
}

View File

@@ -0,0 +1,17 @@
import Component from 'flarum/Component';
import icon from 'flarum/helpers/icon';
export default class SubscriptionMenuItem extends Component {
view() {
return (
<button className="SubscriptionMenuItem hasIcon" onclick={this.props.onclick}>
{this.props.active ? icon('check', {className: 'Button-icon'}) : ''}
<span className="SubscriptionMenuItem-label">
{icon(this.props.icon, {className: 'Button-icon'})}
<strong>{this.props.label}</strong>
<span className="SubscriptionMenuItem-description">{this.props.description}</span>
</span>
</button>
);
}
}

View File

@@ -0,0 +1,28 @@
import { extend } from 'flarum/extend';
import app from 'flarum/app';
import Model from 'flarum/Model';
import Discussion from 'flarum/models/Discussion';
import NotificationGrid from 'flarum/components/NotificationGrid';
import addSubscriptionBadge from 'subscriptions/addSubscriptionBadge';
import addSubscriptionControls from 'subscriptions/addSubscriptionControls';
import addSubscriptionFilter from 'subscriptions/addSubscriptionFilter';
import NewPostNotification from 'subscriptions/components/NewPostNotification';
app.initializers.add('subscriptions', function() {
app.notificationComponents.newPost = NewPostNotification;
Discussion.prototype.subscription = Model.attribute('subscription');
addSubscriptionBadge();
addSubscriptionControls();
addSubscriptionFilter();
extend(NotificationGrid.prototype, 'notificationTypes', function(items) {
items.add('newPost', {
name: 'newPost',
icon: 'star',
label: app.trans('subscriptions.notify_new_post')
});
});
});

View File

@@ -1,16 +0,0 @@
import Notification from 'flarum/components/notification';
import username from 'flarum/helpers/username';
export default class NewPostNotification extends Notification {
view() {
var notification = this.props.notification;
var discussion = notification.subject();
var content = notification.content() || {};
return super.view({
href: app.route.discussion(discussion, content.postNumber),
icon: 'star',
content: [username(notification.sender()), ' posted']
});
}
}

View File

@@ -1,17 +0,0 @@
import Component from 'flarum/component';
import icon from 'flarum/helpers/icon';
export default class SubscriptionMenuItem extends Component {
view() {
return m('a.subscription-menu-item.has-icon[href=javascript:;]', {
onclick: this.props.onclick
}, [
this.props.active ? icon('check icon') : '',
m('span.label',
icon(this.props.icon+' icon'),
m('strong', this.props.label),
m('span.description', this.props.description)
)
]);
}
}

View File

@@ -1,54 +0,0 @@
import Component from 'flarum/component';
import ActionButton from 'flarum/components/action-button';
import icon from 'flarum/helpers/icon';
import SubscriptionMenuItem from 'flarum-subscriptions/components/subscription-menu-item';
export default class SubscriptionMenu extends Component {
view() {
var discussion = this.props.discussion;
var subscription = discussion.subscription();
var buttonLabel = 'Follow';
var buttonIcon = 'star-o';
var buttonClass = 'btn-subscription-'+subscription;
switch (subscription) {
case 'follow':
buttonLabel = 'Following';
buttonIcon = 'star';
break;
case 'ignore':
buttonLabel = 'Ignoring';
buttonIcon = 'eye-slash';
}
var options = [
{subscription: false, icon: 'star-o', label: 'Not Following', description: 'Be notified when @mentioned.'},
{subscription: 'follow', icon: 'star', label: 'Following', description: 'Be notified of all replies.'},
{subscription: 'ignore', icon: 'eye-slash', label: 'Ignoring', description: 'Never be notified. Hide from the discussion list.'}
];
return m('div.dropdown.btn-group.subscription-menu', [
ActionButton.component({
className: 'btn btn-default '+buttonClass,
icon: buttonIcon,
label: buttonLabel,
onclick: this.saveSubscription.bind(this, discussion, ['follow', 'ignore'].indexOf(subscription) !== -1 ? false : 'follow')
}),
m('a.dropdown-toggle.btn.btn-default.btn-icon[href=javascript:;][data-toggle=dropdown]', {className: buttonClass}, icon('caret-down icon-caret')),
m('ul.dropdown-menu.pull-right', options.map(props => {
props.onclick = this.saveSubscription.bind(this, discussion, props.subscription);
props.active = subscription === props.subscription;
return m('li', SubscriptionMenuItem.component(props));
}))
]);
}
saveSubscription(discussion, subscription) {
discussion.save({subscription});
}
}