FEATURE: Subcategory list on parent subcategory page.
This commit is contained in:
parent
4592916026
commit
462dcadd01
|
@ -29,12 +29,13 @@ export default Ember.Component.extend({
|
|||
}.property('category', 'parentCategory'),
|
||||
|
||||
childCategories: function() {
|
||||
if (this.get('hideSubcategories')) { return []; }
|
||||
var firstCategory = this.get('firstCategory');
|
||||
if (!firstCategory) { return; }
|
||||
if (!firstCategory) { return []; }
|
||||
|
||||
return this.get('categories').filter(function (c) {
|
||||
return c.get('parentCategory') === firstCategory;
|
||||
});
|
||||
}.property('firstCategory')
|
||||
}.property('firstCategory', 'hideSubcategories')
|
||||
|
||||
});
|
||||
|
|
|
@ -0,0 +1,21 @@
|
|||
export default Em.Component.extend({
|
||||
tagName: 'h3',
|
||||
|
||||
render: function(buffer) {
|
||||
var category = this.get('category'),
|
||||
logoUrl = category.get('logo_url');
|
||||
|
||||
if (category.get('read_restricted')) {
|
||||
buffer.push("<i class='fa fa-group'></i> ");
|
||||
}
|
||||
|
||||
buffer.push("<a href='" + Discourse.getURL('/category/') + Discourse.Category.slugFor(category) + "'>");
|
||||
|
||||
if (Em.isEmpty(logoUrl)) {
|
||||
buffer.push(Handlebars.Utils.escapeExpression(category.get('name')));
|
||||
} else {
|
||||
buffer.push("<img src='" + logoUrl + "' class='category-logo'>");
|
||||
}
|
||||
buffer.push("</a>");
|
||||
}
|
||||
});
|
|
@ -1,3 +1,3 @@
|
|||
import NavigationDefaultController from 'discourse/controllers/navigation/default';
|
||||
|
||||
export default NavigationDefaultController.extend({});
|
||||
export default NavigationDefaultController.extend();
|
||||
|
|
|
@ -1,7 +1,12 @@
|
|||
import NavigationDefaultController from 'discourse/controllers/navigation/default';
|
||||
|
||||
export default NavigationDefaultController.extend({
|
||||
subcategoryListSetting: Discourse.computed.setting('show_subcategory_list'),
|
||||
showingParentCategory: Em.computed.none('category.parentCategory'),
|
||||
showingSubcategoryList: Em.computed.and('subcategoryListSetting', 'showingParentCategory'),
|
||||
|
||||
navItems: function() {
|
||||
if (this.get('showingSubcategoryList')) { return []; }
|
||||
return Discourse.NavItem.buildList(this.get('category'), { noSubcategories: this.get('noSubcategories') });
|
||||
}.property('category', 'noSubcategories')
|
||||
});
|
||||
|
|
|
@ -77,6 +77,10 @@ Discourse.Resolver = Ember.DefaultResolver.extend({
|
|||
return this.customResolve(parsedName) || this._super(parsedName);
|
||||
},
|
||||
|
||||
resolveRoute: function(parsedName) {
|
||||
return this.customResolve(parsedName) || this._super(parsedName);
|
||||
},
|
||||
|
||||
/**
|
||||
Attaches a view and wires up the container properly
|
||||
|
||||
|
|
|
@ -3,6 +3,7 @@ import buildTopicRoute from 'discourse/routes/build-topic-route';
|
|||
|
||||
export default {
|
||||
name: 'dynamic-route-builders',
|
||||
after: 'register-discourse-location',
|
||||
|
||||
initialize: function(container, app) {
|
||||
app.DiscoveryCategoryRoute = buildCategoryRoute('latest');
|
||||
|
|
|
@ -7,7 +7,6 @@
|
|||
@module Discourse
|
||||
**/
|
||||
Discourse.CategoryList = Ember.ArrayProxy.extend({
|
||||
|
||||
init: function() {
|
||||
this.content = [];
|
||||
this._super();
|
||||
|
@ -22,7 +21,6 @@ Discourse.CategoryList = Ember.ArrayProxy.extend({
|
|||
});
|
||||
|
||||
Discourse.CategoryList.reopenClass({
|
||||
|
||||
categoriesFrom: function(result) {
|
||||
var categories = Discourse.CategoryList.create(),
|
||||
users = Discourse.Model.extractByKey(result.featured_users, Discourse.User),
|
||||
|
@ -55,6 +53,15 @@ Discourse.CategoryList.reopenClass({
|
|||
return categories;
|
||||
},
|
||||
|
||||
listForParent: function(category) {
|
||||
var self = this;
|
||||
return Discourse.ajax('/categories.json?parent_category_id=' + category.get('id')).then(function(result) {
|
||||
return Discourse.CategoryList.create({
|
||||
categories: self.categoriesFrom(result)
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
list: function() {
|
||||
var self = this;
|
||||
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
// A helper function to create a category route with parameters
|
||||
export default function(filter, params) {
|
||||
return Discourse.Route.extend({
|
||||
model: function(params) {
|
||||
return Discourse.Category.findBySlug(params.slug, params.parentSlug);
|
||||
model: function(modelParams) {
|
||||
return Discourse.Category.findBySlug(modelParams.slug, modelParams.parentSlug);
|
||||
},
|
||||
|
||||
afterModel: function(model, transaction) {
|
||||
|
@ -11,21 +11,44 @@ export default function(filter, params) {
|
|||
return;
|
||||
}
|
||||
|
||||
var self = this,
|
||||
noSubcategories = params && !!params.no_subcategories,
|
||||
filterMode = "category/" + Discourse.Category.slugFor(model) + (noSubcategories ? "/none" : "") + "/l/" + filter,
|
||||
listFilter = "category/" + Discourse.Category.slugFor(model) + "/l/" + filter;
|
||||
|
||||
this.controllerFor('search').set('searchContext', model.get('searchContext'));
|
||||
this._setupNavigation(model);
|
||||
return Em.RSVP.all([this._createSubcategoryList(model),
|
||||
this._retrieveTopicList(model, transaction)]);
|
||||
},
|
||||
|
||||
var opts = { category: model, filterMode: filterMode };
|
||||
opts.noSubcategories = params && params.no_subcategories;
|
||||
opts.canEditCategory = Discourse.User.currentProp('staff');
|
||||
_setupNavigation: function(model) {
|
||||
var noSubcategories = params && !!params.no_subcategories,
|
||||
filterMode = "category/" + Discourse.Category.slugFor(model) + (noSubcategories ? "/none" : "") + "/l/" + filter;
|
||||
|
||||
opts.canChangeCategoryNotificationLevel = Discourse.User.current();
|
||||
this.controllerFor('navigation/category').setProperties(opts);
|
||||
this.controllerFor('navigation/category').setProperties({
|
||||
category: model,
|
||||
filterMode: filterMode,
|
||||
noSubcategories: params && params.no_subcategories,
|
||||
canEditCategory: Discourse.User.currentProp('staff'),
|
||||
canChangeCategoryNotificationLevel: Discourse.User.current()
|
||||
});
|
||||
},
|
||||
|
||||
_createSubcategoryList: function(model) {
|
||||
this._categoryList = null;
|
||||
if (Em.isNone(model.get('parentCategory')) && Discourse.SiteSettings.show_subcategory_list) {
|
||||
var self = this;
|
||||
return Discourse.CategoryList.listForParent(model).then(function(list) {
|
||||
console.log('loaded list');
|
||||
self._categoryList = list;
|
||||
});
|
||||
}
|
||||
|
||||
// If we're not loading a subcategory list just resolve
|
||||
return Em.RSVP.resolve();
|
||||
},
|
||||
|
||||
_retrieveTopicList: function(model, transaction) {
|
||||
var queryParams = transaction.queryParams,
|
||||
listFilter = "category/" + Discourse.Category.slugFor(model) + "/l/" + filter,
|
||||
self = this;
|
||||
|
||||
var queryParams = transaction.queryParams;
|
||||
params = params || {};
|
||||
|
||||
if (queryParams && queryParams.order) { params.order = queryParams.order; }
|
||||
|
@ -67,6 +90,10 @@ export default function(filter, params) {
|
|||
|
||||
renderTemplate: function() {
|
||||
this.render('navigation/category', { outlet: 'navigation-bar' });
|
||||
|
||||
if (this._categoryList) {
|
||||
this.render('discovery/categories', { outlet: 'header-list-container', model: this._categoryList });
|
||||
}
|
||||
this.render('discovery/topics', { controller: 'discovery/topics', outlet: 'list-container' });
|
||||
},
|
||||
|
||||
|
|
|
@ -14,7 +14,16 @@
|
|||
<div class='spinner'>{{i18n loading}}</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div {{bind-attr class=":container :list-container loadingSpinner:hidden"}}>
|
||||
<div class="row">
|
||||
<div class="full-width">
|
||||
<div id='header-list-area'>
|
||||
{{outlet header-list-container}}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row">
|
||||
<div class="full-width">
|
||||
<div id='list-area'>
|
||||
|
|
|
@ -20,16 +20,7 @@
|
|||
<div>
|
||||
<div class="pull-left">
|
||||
{{#if controller.ordering}}<i class="fa fa-bars"></i>{{/if}}
|
||||
<h3>
|
||||
{{#if read_restricted}}<i class='fa fa-group'></i>{{/if}}
|
||||
{{#link-to 'discovery.parentCategory' this}}
|
||||
{{#if logo_url}}
|
||||
<img src="{{unbound logo_url}}" class='category-logo'>
|
||||
{{else}}
|
||||
{{unbound name}}
|
||||
{{/if}}
|
||||
{{/link-to}}
|
||||
</h3>
|
||||
{{category-title-link category=this}}
|
||||
{{#if unreadTopics}}
|
||||
<a href={{unbound unreadUrl}} class='badge new-posts badge-notification' title='{{i18n topic.unread_topics count="unreadTopics"}}'>{{unbound unreadTopics}}</a>
|
||||
{{/if}}
|
||||
|
|
|
@ -1,4 +1,7 @@
|
|||
{{bread-crumbs categories=categories category=category noSubcategories=noSubcategories}}
|
||||
{{bread-crumbs categories=categories
|
||||
category=category
|
||||
noSubcategories=noSubcategories
|
||||
hideSubcategories=showingSubcategoryList}}
|
||||
|
||||
<ul class="nav nav-pills" id='navigation-bar'>
|
||||
{{#each navItem in navItems}}
|
||||
|
|
|
@ -11,8 +11,9 @@ class CategoriesController < ApplicationController
|
|||
|
||||
options = {}
|
||||
options[:latest_posts] = params[:latest_posts] || SiteSetting.category_featured_topics
|
||||
options[:parent_category_id] = params[:parent_category_id]
|
||||
|
||||
@list = CategoryList.new(guardian,options)
|
||||
@list = CategoryList.new(guardian, options)
|
||||
@list.draft_key = Draft::NEW_TOPIC
|
||||
@list.draft_sequence = DraftSequence.current(current_user, Draft::NEW_TOPIC)
|
||||
@list.draft = Draft.get(current_user, @list.draft_key, @list.draft_sequence) if current_user
|
||||
|
|
|
@ -58,6 +58,10 @@ class CategoryList
|
|||
.includes(:featured_users, subcategories: [:topic_only_relative_url])
|
||||
.secured(@guardian)
|
||||
|
||||
if @options[:parent_category_id].present?
|
||||
@categories = @categories.where('categories.parent_category_id = ?', @options[:parent_category_id].to_i)
|
||||
end
|
||||
|
||||
if SiteSetting.fixed_category_positions
|
||||
@categories = @categories.order('position ASC').order('id ASC')
|
||||
else
|
||||
|
@ -72,21 +76,23 @@ class CategoryList
|
|||
end
|
||||
|
||||
@categories = @categories.to_a
|
||||
subcategories = {}
|
||||
to_delete = Set.new
|
||||
@categories.each do |c|
|
||||
if c.parent_category_id.present?
|
||||
subcategories[c.parent_category_id] ||= []
|
||||
subcategories[c.parent_category_id] << c.id
|
||||
to_delete << c
|
||||
end
|
||||
end
|
||||
|
||||
if subcategories.present?
|
||||
if @options[:parent_category_id].blank?
|
||||
subcategories = {}
|
||||
to_delete = Set.new
|
||||
@categories.each do |c|
|
||||
c.subcategory_ids = subcategories[c.id]
|
||||
if c.parent_category_id.present?
|
||||
subcategories[c.parent_category_id] ||= []
|
||||
subcategories[c.parent_category_id] << c.id
|
||||
to_delete << c
|
||||
end
|
||||
end
|
||||
|
||||
if subcategories.present?
|
||||
@categories.each do |c|
|
||||
c.subcategory_ids = subcategories[c.id]
|
||||
end
|
||||
@categories.delete_if {|c| to_delete.include?(c) }
|
||||
end
|
||||
@categories.delete_if {|c| to_delete.include?(c) }
|
||||
end
|
||||
|
||||
if latest_post_only?
|
||||
|
|
Loading…
Reference in New Issue