diff --git a/app/coffee/modules/controllerMixins.coffee b/app/coffee/modules/controllerMixins.coffee
index ee02dc8a..90e7807c 100644
--- a/app/coffee/modules/controllerMixins.coffee
+++ b/app/coffee/modules/controllerMixins.coffee
@@ -22,6 +22,9 @@
taiga = @.taiga
groupBy = @.taiga.groupBy
+joinStr = @.taiga.joinStr
+trim = @.taiga.trim
+toString = @.taiga.toString
class PageMixin
@@ -52,9 +55,8 @@ class FiltersMixin
selectFilter: (name, value, load=false) ->
params = @location.search()
if params[name] != undefined and name != "page"
- existing = _.map(params[name].split(","), trim)
- existing.push(value)
-
+ existing = _.map(taiga.toString(params[name]).split(","), trim)
+ existing.push(taiga.toString(value))
value = joinStr(",", _.uniq(existing))
location = if load then @location else @location.noreload(@scope)
@@ -69,8 +71,8 @@ class FiltersMixin
if value is undefined or value is null
delete params[name]
- parsedValues = _.map(params[name].split(","), trim)
- newValues = _.reject(parsedValues, (x) -> x == toString(value))
+ parsedValues = _.map(taiga.toString(params[name]).split(","), trim)
+ newValues = _.reject(parsedValues, (x) -> x == taiga.toString(value))
if _.isEmpty(newValues)
value = null
diff --git a/app/coffee/modules/issues/list.coffee b/app/coffee/modules/issues/list.coffee
index 7430dff2..435431cf 100644
--- a/app/coffee/modules/issues/list.coffee
+++ b/app/coffee/modules/issues/list.coffee
@@ -55,9 +55,48 @@ class IssuesController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fi
console.log "FAIL" #TODO
loadFilters: ->
- defered = @q.defer()
- defered.resolve()
- return defered.promise
+ return @rs.issues.filtersData(@scope.projectId).then (data) =>
+ console.log data
+
+ # Build selected filters (from url) fast lookup data structure
+ searchdata = {}
+ for name, value of @.getFilters()
+ if name == "page"
+ continue
+
+ if not searchdata[name]?
+ searchdata[name] = {}
+
+ for val in value.split(",")
+ searchdata[name][val] = true
+
+ isSelected = (type, id) ->
+ if searchdata[type]? and searchdata[type][id]
+ return true
+ return false
+
+ console.log "2222", searchdata
+
+ # Build filters data structure
+ filters = {}
+ filters.tags = _.map data.tags, (t) =>
+ obj = {id:t[0], name:t[0], count: t[1], type:"tags"}
+ obj.selected = true if isSelected("tags", obj.id)
+ return obj
+
+ filters.priorities = _.map data.priorities, (t) =>
+ obj = {id:t[0], name:@scope.priorityById[t[0]].name, count:t[1], type:"priorities"}
+ obj.selected = true if isSelected("priorities", obj.id)
+ return obj
+
+ filters.severities = _.map data.severities, (t) =>
+ obj = {id:t[0], name:@scope.severityById[t[0]].name, count:t[1], type:"severities"}
+ obj.selected = true if isSelected("severities", obj.id)
+ return obj
+
+ @scope.filters = filters
+ @rootscope.$broadcast("filters:loaded", filters)
+ return data
loadProject: ->
return @rs.projects.get(@scope.projectId).then (project) =>
@@ -69,12 +108,31 @@ class IssuesController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fi
return project
getFilters: ->
- filters = _.pick(@location.search(), "page", "tags", "status", "type")
+ filters = _.pick(@location.search(), "page", "tags", "status", "type",
+ "severities", "priorities")
filters.page = 1 if not filters.page
return filters
+ # Convert stored filters to http parameters
+ # ready filters (the name difference exists
+ # because of some automatic lookups and is
+ # the simplest way todo it without adding
+ # additional complexity to code.
+ prepareFilters: ->
+ filters = {}
+
+ for name, values of @.getFilters()
+ if name == "severities"
+ name = "severity"
+ else if name == "priorities"
+ name = "priority"
+
+ filters[name] = values
+ return filters
+
loadIssues: ->
- filters = @.getFilters()
+ filters = @.prepareFilters()
+ console.log filters
promise = @rs.issues.list(@scope.projectId, filters).then (data) =>
@scope.issues = data.models
@@ -221,7 +279,8 @@ IssuesDirective = ($log, $location) ->
#########################
linkFilters = ($scope, $el, $attrs, $ctrl) ->
- $log.debug "IssuesDirective:linkFilters"
+ $scope.filters = {}
+ $scope.selectedFilters = []
#########################
## Issues Link
@@ -235,4 +294,125 @@ IssuesDirective = ($log, $location) ->
return {link:link}
+
+IssuesFiltersDirective = ($log, $location) ->
+ template = _.template("""
+ <% _.each(filters, function(f) { %>
+ <% if (f.selected) { %>
+
+ <%- f.name %>
+ <%- f.count %>
+
+ <% } else { %>
+
+ <%- f.name %>
+ <%- f.count %>
+
+ <% } %>
+ <% }) %>
+ """)
+
+ templateSelected = _.template("""
+ <% _.each(filters, function(f) { %>
+
+ <%- f.name %>
+
+
+ <% }) %>
+ """)
+
+ selectedFilters = []
+
+ showFilters = ($el) ->
+ $el.find(".filters-cats").hide()
+ $el.find(".filter-list").show()
+
+ showCategories = ($el) ->
+ $el.find(".filters-cats").show()
+ $el.find(".filter-list").hide()
+
+ initializeSelectedFilters = ($el, filters) ->
+ for name, values of filters
+ for val in values
+ console.log "klkk", val.selected
+ selectedFilters.push(val) if val.selected
+
+ renderSelectedFilters($el)
+
+ renderSelectedFilters = ($el) ->
+ html = templateSelected({filters:selectedFilters})
+ $el.find(".filters-applied").html(html)
+
+ renderFilters = ($el, filters) ->
+ html = template({filters:filters})
+ $el.find(".filter-list").html(html)
+
+ link = ($scope, $el, $attrs) ->
+ $ctrl = $el.closest(".wrapper").controller()
+
+ $scope.$on "filters:loaded", (ctx, filters) ->
+ initializeSelectedFilters($el, filters)
+
+ toggleFilterSelection = (type, id) ->
+ filters = $scope.filters[type]
+ filter = _.find(filters, {id:id})
+ filter.selected = (not filter.selected)
+ if filter.selected
+ selectedFilters.push(filter)
+ $scope.$apply ->
+ $ctrl.selectFilter(type, id)
+ $ctrl.selectFilter("page", 1)
+ $ctrl.loadIssues()
+ else
+ selectedFilters = _.reject(selectedFilters, filter)
+ $scope.$apply ->
+ $ctrl.unselectFilter(type, id)
+ $ctrl.selectFilter("page", 1)
+ $ctrl.loadIssues()
+
+ renderSelectedFilters($el, selectedFilters)
+ renderFilters($el, filters)
+
+ $el.on "click", ".filters-cats > ul > li > a", (event) ->
+ event.preventDefault()
+ target = angular.element(event.currentTarget)
+ tags = $scope.filters[target.data("type")]
+
+ renderFilters($el, tags)
+ showFilters($el)
+
+ $el.on "click", ".filters-inner > h1 > a.title", (event) ->
+ event.preventDefault()
+ showCategories($el)
+
+ $el.on "click", ".filters-applied a", (event) ->
+ event.preventDefault()
+ target = angular.element(event.currentTarget)
+
+ id = target.data("id")
+ type = target.data("type")
+ toggleFilterSelection(type, id)
+
+ $el.on "click", ".filter-list .single-filter", (event) ->
+ event.preventDefault()
+ target = angular.element(event.currentTarget)
+ if target.hasClass("active")
+ target.removeClass("active")
+ # target.css("background-color")
+ else
+ target.addClass("active")
+
+ id = target.data("id")
+ type = target.data("type")
+ toggleFilterSelection(type, id)
+
+ return {link:link}
+
+module.directive("tgIssuesFilters", ["$log", "$tgLocation", IssuesFiltersDirective])
module.directive("tgIssues", ["$log", "$tgLocation", IssuesDirective])
diff --git a/app/coffee/modules/resources/issues.coffee b/app/coffee/modules/resources/issues.coffee
index cf0966e5..f06ea9e3 100644
--- a/app/coffee/modules/resources/issues.coffee
+++ b/app/coffee/modules/resources/issues.coffee
@@ -37,7 +37,7 @@ resourceProvider = ($repo) ->
return $repo.queryOneRaw("projects", "#{projectId}/issues_stats")
service.filtersData = (projectId) ->
- return $repo.queryOneRaw("projects", "#{projectId}/issues_filters_data")
+ return $repo.queryOneRaw("projects", "#{projectId}/issue_filters_data")
return (instance) ->
instance.issues = service
diff --git a/app/partials/issues.jade b/app/partials/issues.jade
index fddd0899..870fd4ec 100644
--- a/app/partials/issues.jade
+++ b/app/partials/issues.jade
@@ -5,7 +5,7 @@ block head
block content
div.wrapper.issues(tg-issues, ng-controller="IssuesController as ctrl", ng-init="section='issues'")
- sidebar.menu-secondary.extrabar.filters-bar
+ sidebar.menu-secondary.extrabar.filters-bar(tg-issues-filters)
include views/modules/filters
section.main.issues-page
@@ -20,5 +20,6 @@ block content
div.hidden.lightbox.lightbox_add-issue
include views/modules/lightbox_add-issue
- div.lightbox.lightbox_add-bulk.hidden
+
+ div.hidden.lightbox.lightbox_add-bulk
include views/modules/lightbox_add-bulk
diff --git a/app/partials/views/modules/filters.jade b/app/partials/views/modules/filters.jade
index 4795019e..a74e6beb 100644
--- a/app/partials/views/modules/filters.jade
+++ b/app/partials/views/modules/filters.jade
@@ -7,37 +7,38 @@ section.filters
span status
form
fieldset
- input(type="text", placeholder="Filter Filters", ng-model="filters.subject")
+ input(type="text", placeholder="Search by subject...", ng-model="filters.subject")
a.icon.icon-search(href="", title="search")
//- First step for selecting category
div.filters-step-cat
//- $(.filters-applied) only visible when filters are being applied
div.filters-applied
- a.single-filter.selected
- span.name Filter23
- span.icon.icon-delete
+ // a.single-filter.selected
+ // span.name Filter23
+ // span.icon.icon-delete
div.filters-cats
ul
+ // li
+ // a(href="", title="Status", data-type="status")
+ // span.title Status
+ // span.icon.icon-arrow-right
+ // li
+ // a(href="", title="Type", data-type="types")
+ // span.title Type
+ // span.icon.icon-arrow-right
li
- a(href="", title="status")
- span Status
+ a(href="", title="Severity", data-type="severities")
+ span.title Severity
span.icon.icon-arrow-right
li
- a(href="", title="type")
- span Type
+ a(href="", title="Priorities", data-type="priorities")
+ span.title Priorities
span.icon.icon-arrow-right
li
- a(href="", title="Severity")
- span Severity
- span.icon.icon-arrow-right
- li
- a(href="", title="blablabla")
- span Blablabla
+ a(href="", title="Tags", data-type="tags")
+ span.title Tags
span.icon.icon-arrow-right
//- Second step for selecting single filters to apply
- div.filter-list
- a.single-filter(ng-repeat="tag in filters.tags|filter:filtersSearch:strict" ng-class="{selected: tag.selected}")
- span.name(tg-bo-html="tag.name")
- span.number(tg-bo-html="tag.count")
+ div.filter-list.hidden