diff --git a/assets/javascripts/discourse-assign/connectors/category-custom-settings/assign-settings.hbs b/assets/javascripts/discourse-assign/connectors/category-custom-settings/assign-settings.hbs new file mode 100644 index 0000000..0ee2383 --- /dev/null +++ b/assets/javascripts/discourse-assign/connectors/category-custom-settings/assign-settings.hbs @@ -0,0 +1,13 @@ +

{{i18n 'discourse_assign.assign.title'}}

+
+
+ +
+
diff --git a/assets/javascripts/discourse-assign/connectors/category-custom-settings/assign-settings.js.es6 b/assets/javascripts/discourse-assign/connectors/category-custom-settings/assign-settings.js.es6 new file mode 100644 index 0000000..dcd2b94 --- /dev/null +++ b/assets/javascripts/discourse-assign/connectors/category-custom-settings/assign-settings.js.es6 @@ -0,0 +1,10 @@ +export default { + actions: { + onChangeSetting(value) { + this.set( + "category.custom_fields.enable_unassigned_filter", + value ? "true" : "false" + ); + } + } +}; diff --git a/assets/javascripts/discourse-assign/initializers/extend-for-assigns.js.es6 b/assets/javascripts/discourse-assign/initializers/extend-for-assigns.js.es6 index ea262d9..6a57abb 100644 --- a/assets/javascripts/discourse-assign/initializers/extend-for-assigns.js.es6 +++ b/assets/javascripts/discourse-assign/initializers/extend-for-assigns.js.es6 @@ -5,6 +5,7 @@ import { h } from "virtual-dom"; import { iconHTML } from "discourse-common/lib/icon-library"; import { queryRegistry } from "discourse/widgets/widget"; import { getOwner } from "discourse-common/lib/get-owner"; +import NavItem from "discourse/models/nav-item"; function registerTopicFooterButtons(api) { api.registerTopicFooterButton({ @@ -55,6 +56,65 @@ function registerTopicFooterButtons(api) { } function initialize(api) { + + // START TEMPORARY HACK + // + // NavItem does not allow for proper customisation currently. + // The router sets "filterMode" which only includes partial data about the route + // This is the only information a nav item has when deciding if to highlight a route + // or not. + // Additionally short of monkey patching there is no way to insert a nav item prior to + // Top. + // + // This hack will be nuked when we add a new api like registerTopicFooterButtons for nav + + api.modifyClass("route:discovery.latestParentCategory", { + _retrieveTopicList(category, transition) { + const params = transition.to.queryParams; + if (params && params["assigned"] === "nobody") { + this.controllerFor("navigation/category").setProperties({ + filterMode: "Unassigned" + }); + } + return this._super(category, transition); + } + }); + + const UnassignedNavItem = NavItem.extend({ + @computed() + filterMode() { + return "Unassigned"; + }, + @computed("filterMode", "category") + href(filterMode, category) { + return Discourse.getURL( + "/c/" + + Discourse.Category.slugFor(category) + + "/l/latest?status=open&assigned=nobody" + ); + } + }); + + api.modifyClass("component:d-navigation", { + @computed("filterMode", "category", "noSubcategories") + navItems(filterMode, category, noSubcategories) { + filterMode = "Unassigned"; + let items = this._super(filterMode, category, noSubcategories); + if (category && category.enable_unassigned_filter) { + const args = { + name: "unassigned", + hasIcon: false, + category: category + }; + const newItem = UnassignedNavItem.create(args); + items.splice(items.length - 1, 0, newItem); + } + return items; + } + }); + + // END TEMPORARY HACK + // You can't act on flags claimed by another user api.modifyClass( "component:flagged-post", diff --git a/assets/javascripts/discourse-assign/pre-initializers/extend-category-for-assign.js.es6 b/assets/javascripts/discourse-assign/pre-initializers/extend-category-for-assign.js.es6 new file mode 100644 index 0000000..3bb263e --- /dev/null +++ b/assets/javascripts/discourse-assign/pre-initializers/extend-category-for-assign.js.es6 @@ -0,0 +1,20 @@ +import Category from "discourse/models/category"; + +export default { + name: "extend-category-for-assign", + + before: "inject-discourse-objects", + + initialize() { + Category.reopen({ + enable_unassigned_filter: Ember.computed( + "custom_fields.enable_unassigned_filter", + { + get(fieldName) { + return Ember.get(this.custom_fields, fieldName) === "true"; + } + } + ) + }); + } +}; diff --git a/config/locales/client.en.yml b/config/locales/client.en.yml index c09e9be..76fd663 100644 --- a/config/locales/client.en.yml +++ b/config/locales/client.en.yml @@ -1,9 +1,14 @@ en: js: + filters: + unassigned: + title: "Unassigned" + help: "Unassigned topics" action_codes: assigned: "assigned %{who} %{when}" unassigned: "unassigned %{who} %{when}" discourse_assign: + add_unassigned_filter: "Add 'unassigned' filter to category" cant_act: "You cannot act on flags that have been assigned to other users" cant_act_unclaimed: "You must claim this topic before acting on flags." assigned: "Assigned" diff --git a/plugin.rb b/plugin.rb index cc59d97..425d733 100644 --- a/plugin.rb +++ b/plugin.rb @@ -100,6 +100,7 @@ after_initialize do end TopicList.preloaded_custom_fields << TopicAssigner::ASSIGNED_TO_ID + Site.preloaded_category_custom_fields << "enable_unassigned_filter" if Site.respond_to? :preloaded_category_custom_fields TopicList.on_preload do |topics, topic_list| if SiteSetting.assign_enabled?