From 370f0a0303e584a459d58f69b58fb55d8d83b852 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 29 Jan 2015 12:13:08 +0100 Subject: [PATCH 001/207] fix #2057 - firefox flex blox, direction column issue --- app/styles/modules/common/.#projects-nav.scss | 1 + app/styles/modules/common/projects-nav.scss | 1 + 2 files changed, 2 insertions(+) create mode 120000 app/styles/modules/common/.#projects-nav.scss diff --git a/app/styles/modules/common/.#projects-nav.scss b/app/styles/modules/common/.#projects-nav.scss new file mode 120000 index 00000000..46d27ea5 --- /dev/null +++ b/app/styles/modules/common/.#projects-nav.scss @@ -0,0 +1 @@ +juanfran@juanfran.5837:1422512236 \ No newline at end of file diff --git a/app/styles/modules/common/projects-nav.scss b/app/styles/modules/common/projects-nav.scss index 4949a0d3..e2375709 100644 --- a/app/styles/modules/common/projects-nav.scss +++ b/app/styles/modules/common/projects-nav.scss @@ -41,6 +41,7 @@ display: flex; flex-direction: column; margin-top: 1rem; + min-height: 1px; //firefox bug } .create-project-button-wrapper { display: flex; From 2e2a3849e2dbda773f4027b3ef39e2b7a234a856 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 29 Jan 2015 12:26:58 +0100 Subject: [PATCH 002/207] deleted tmp file --- app/styles/modules/common/.#projects-nav.scss | 1 - app/styles/modules/common/projects-nav.scss | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) delete mode 120000 app/styles/modules/common/.#projects-nav.scss diff --git a/app/styles/modules/common/.#projects-nav.scss b/app/styles/modules/common/.#projects-nav.scss deleted file mode 120000 index 46d27ea5..00000000 --- a/app/styles/modules/common/.#projects-nav.scss +++ /dev/null @@ -1 +0,0 @@ -juanfran@juanfran.5837:1422512236 \ No newline at end of file diff --git a/app/styles/modules/common/projects-nav.scss b/app/styles/modules/common/projects-nav.scss index e2375709..d922ff23 100644 --- a/app/styles/modules/common/projects-nav.scss +++ b/app/styles/modules/common/projects-nav.scss @@ -41,7 +41,7 @@ display: flex; flex-direction: column; margin-top: 1rem; - min-height: 1px; //firefox bug + min-height: 1px; //firefox bug #2057 } .create-project-button-wrapper { display: flex; From d59b481b5822d325b53153f29b2efdbcd932a5a3 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 29 Jan 2015 14:04:27 +0100 Subject: [PATCH 003/207] fix project overflow --- app/styles/modules/home-projects-list.scss | 1 + 1 file changed, 1 insertion(+) diff --git a/app/styles/modules/home-projects-list.scss b/app/styles/modules/home-projects-list.scss index c8ccc6ef..40962a31 100644 --- a/app/styles/modules/home-projects-list.scss +++ b/app/styles/modules/home-projects-list.scss @@ -75,6 +75,7 @@ height: 130px; margin-bottom: 1rem; margin-right: 1rem; + overflow: hidden; position: relative; transition: background-color .3s linear; width: 23.5%; From 10ab601d5258ff06b7de4808fbb4081c5edad431 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 29 Jan 2015 14:53:07 +0100 Subject: [PATCH 004/207] fix issue subject overflow --- app/styles/modules/issues/issues-table.scss | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/app/styles/modules/issues/issues-table.scss b/app/styles/modules/issues/issues-table.scss index 4b8bd88a..3e358adf 100644 --- a/app/styles/modules/issues/issues-table.scss +++ b/app/styles/modules/issues/issues-table.scss @@ -55,20 +55,17 @@ flex-basis: 300px; flex-grow: 7; flex-shrink: 0; + overflow: hidden; padding-right: 1rem; a { - white-space: nowrap; + @include ellipsis(100%); + display: block; } span { vertical-align: middle; &:first-child { margin-right: .5rem; } - &:last-child { - @include ellipsis(100%); - display: inline-block; - padding-right: 2rem; - } } } .issue-field, From 29de1cf20aedbd8f0bc752a0f7293060dd4f2665 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Thu, 29 Jan 2015 19:34:38 +0100 Subject: [PATCH 005/207] Small fix on imported comments from import --- app/coffee/modules/common/history.coffee | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/common/history.coffee b/app/coffee/modules/common/history.coffee index 39540efa..08c34fda 100644 --- a/app/coffee/modules/common/history.coffee +++ b/app/coffee/modules/common/history.coffee @@ -191,9 +191,9 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> return "Made #{size} changes" # TODO: i18n renderComment = (comment) -> - if (comment.delete_comment_date or comment.delete_comment_user) + if (comment.delete_comment_date or comment.delete_comment_user?.name) return templateDeletedComment({ - deleteCommentDate: moment(comment.delete_comment_date).format("DD MMM YYYY HH:mm") + deleteCommentDate: moment(comment.delete_comment_date).format("DD MMM YYYY HH:mm") if comment.delete_comment_date deleteCommentUser: comment.delete_comment_user.name deleteComment: comment.comment_html activityId: comment.id From 0bc94b2a79aab6c03345fdc07a8b034a9a259067 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Fri, 30 Jan 2015 00:57:03 +0100 Subject: [PATCH 006/207] Fix #300: Fix a typo --- app/partials/includes/modules/backlog-table.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/includes/modules/backlog-table.jade b/app/partials/includes/modules/backlog-table.jade index 4ba4b854..95375e3c 100644 --- a/app/partials/includes/modules/backlog-table.jade +++ b/app/partials/includes/modules/backlog-table.jade @@ -1,6 +1,6 @@ div.backlog-table-header div.row.backlog-table-title - div.user-stories User Storiess + div.user-stories User Stories div.status Status div.points(tg-us-role-points-selector, title="Select view per Role") span.header-points Points From 5969049de191b348a898198a2ce6926424f00137 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 07:43:56 +0100 Subject: [PATCH 007/207] Removed unnecesary vendor prefixes --- app/styles/layout/animation.scss | 15 ++++----------- 1 file changed, 4 insertions(+), 11 deletions(-) diff --git a/app/styles/layout/animation.scss b/app/styles/layout/animation.scss index e47897df..978ec66b 100644 --- a/app/styles/layout/animation.scss +++ b/app/styles/layout/animation.scss @@ -1,5 +1,5 @@ //Loading -@include keyframes(loading) { +@keyframes loading { 0% { filter: blur(5px); opacity: 0; @@ -10,21 +10,14 @@ } } -//Spin -@-webkit-keyframes rotate { +@keyframes rotate { 50% { filter: invert(1); transform: rotate(360deg); } } -@keyframes rotate { - 50% { - transform: rotate(360deg); - } -} - -@include keyframes(formSlide) { +@keyframes formSlide { 0% { filter: blur(5px); opacity: 0; @@ -40,7 +33,7 @@ } //Bar loading -@include keyframes(loadBar) { +@keyframes loadBar { 0% { flex: 1; } From f89dc4022e45a91f3c33127be58fafc6bd977941 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 30 Jan 2015 07:50:01 +0100 Subject: [PATCH 008/207] fix assigned to issues overflow --- app/styles/modules/issues/issues-table.scss | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/app/styles/modules/issues/issues-table.scss b/app/styles/modules/issues/issues-table.scss index 3e358adf..9ff1a1fc 100644 --- a/app/styles/modules/issues/issues-table.scss +++ b/app/styles/modules/issues/issues-table.scss @@ -52,11 +52,9 @@ width: 75px; } .subject { - flex-basis: 300px; - flex-grow: 7; - flex-shrink: 0; overflow: hidden; padding-right: 1rem; + width: 100%; a { @include ellipsis(100%); display: block; @@ -72,13 +70,17 @@ .assigned-field, .created-field , .assigned-field { - flex-basis: 120px; + flex-basis: 140px; flex-grow: 1; flex-shrink: 0; padding: 0 1rem; position: relative; text-align: left; } + .assigned-field { + flex: 0 0 160px; + max-width: 160px; + } .issue-assignedto { cursor: pointer; position: relative; From 7dd1302525c05a022e920b16be56c6a731b2ddb4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 07:58:07 +0100 Subject: [PATCH 009/207] Fix role name size. TG-2113 #ready-for-test --- app/partials/includes/modules/admin-submenu-roles.jade | 3 ++- app/styles/modules/admin/admin-submenu-roles.scss | 4 ++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/app/partials/includes/modules/admin-submenu-roles.jade b/app/partials/includes/modules/admin-submenu-roles.jade index e4c2455d..b4ee5663 100644 --- a/app/partials/includes/modules/admin-submenu-roles.jade +++ b/app/partials/includes/modules/admin-submenu-roles.jade @@ -5,7 +5,8 @@ section.admin-submenu-roles nav ul li(ng-repeat="item in roles") - a(href="" ng-click="ctrl.setRole(item)", ng-class="{active: role.id == item.id}") {{ item.name }} + a(href="" ng-click="ctrl.setRole(item)", ng-class="{active: role.id == item.id}") + span.single-role {{ item.name }} span.icon.icon-arrow-right div(tg-new-role) diff --git a/app/styles/modules/admin/admin-submenu-roles.scss b/app/styles/modules/admin/admin-submenu-roles.scss index b43cc4bb..d0b6b5bc 100644 --- a/app/styles/modules/admin/admin-submenu-roles.scss +++ b/app/styles/modules/admin/admin-submenu-roles.scss @@ -25,6 +25,10 @@ } } } + .single-role { + @include ellipsis(175px); + display: inline-block; + } .icon { color: $white; float: right; From b631aef22d8c93e4a52ebb82646a0dbd0e6d710a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 08:16:29 +0100 Subject: [PATCH 010/207] Redesign role points selector --- app/styles/layout/us-detail.scss | 25 ++++++++++++++----------- 1 file changed, 14 insertions(+), 11 deletions(-) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index 174e1322..67853687 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -263,23 +263,27 @@ .points-per-role { display: flex; + flex-wrap: wrap; position: relative; > li { - border-right: 1px solid rgba($grayer, .3); + background: rgba($gray-light, .1); + border-radius: 2px; color: rgba($grayer, .3); - display: inline-block; - flex-basis: 18%; + flex-basis: 80px; flex-grow: 1; - margin: .5rem .1rem; + flex-shrink: 0; + margin: .1rem; + padding: .5rem; position: relative; text-align: center; transition: color .3s linear; - width: 18%; &.active { - color: rgba($green-taiga, 1); + background: rgba($fresh-taiga, .9); + color: $whitish; } &:first-child { - opacity: 1; + background: rgba($grayer, .5); + color: $whitish; } &:last-child { border: 0; @@ -289,15 +293,14 @@ @extend %xlarge; @extend %title; display: block; + margin-bottom: .3rem; text-align: center; } .role { + @include ellipsis(90%); display: inline-block; - max-width: 90%; - overflow: hidden; + line-height: .8rem; text-align: center; - text-overflow: ellipsis; - white-space: nowrap; } .popover { @include popover(200px, $top: 105%, $left: 35%, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 10px); From 427e078c7b1caaed8f6b9f7d0ab028de78a7f36b Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 30 Jan 2015 09:36:31 +0100 Subject: [PATCH 011/207] fix paginator margin --- app/styles/components/paginator.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/styles/components/paginator.scss b/app/styles/components/paginator.scss index 6cfaaf04..7d4ec1e3 100644 --- a/app/styles/components/paginator.scss +++ b/app/styles/components/paginator.scss @@ -1,17 +1,17 @@ .paginator { margin: 2rem 0; ul { + display: flex; margin-left: 1rem; } li { - display: inline-block; + margin-right: .4rem; } a, .active span, .dots { background: $gray-light; color: $white; - margin-right: .1rem; padding: .5rem 1rem; transition: all .3s linear; } From dbed5cc1813f53e15e2d566ae015d5af16194ecb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 12:30:49 +0100 Subject: [PATCH 012/207] Excluded plugins from lint and necessary qualiying elements --- scsslint.yml | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/scsslint.yml b/scsslint.yml index 77f808be..e8543b80 100644 --- a/scsslint.yml +++ b/scsslint.yml @@ -1,3 +1,8 @@ +exclude: + - 'app/styles/components/markitup.scss' + - 'app/styles/bourbon/**' + - 'app/styles/vendor/**' + linters: BorderZero: enabled: true @@ -77,6 +82,15 @@ linters: enabled: true extra_properties: [] + QualifyingElement: + enabled: true + allow_element_with_attribute: true + exclude: + - 'app/styles/components/buttons.scss' + - 'app/styles/layout/forms.scss' + - 'app/styles/components/help-notion-button.scss' + - 'app/styles/components/markdown-help.scss' + SelectorDepth: enabled: true max_depth: 4 From 8cacf4e82406a14da165f3bbc74f741ad75bacfb Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 30 Jan 2015 12:51:59 +0100 Subject: [PATCH 013/207] Fixing config in navurls --- app/coffee/modules/base/urls.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/base/urls.coffee b/app/coffee/modules/base/urls.coffee index f6d9e061..c542476a 100644 --- a/app/coffee/modules/base/urls.coffee +++ b/app/coffee/modules/base/urls.coffee @@ -30,7 +30,7 @@ class UrlsService extends taiga.Service constructor: (@config) -> @.urls = {} - @.mainUrl = config.get("api") + @.mainUrl = @config.get("api") update: (urls) -> @.urls = _.merge(@.urls, urls) From c9a6d1df8ee08554abeb6075dbeb41f00c8eb626 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 2 Feb 2015 08:42:21 +0100 Subject: [PATCH 014/207] tranform submits to buttons --- app/coffee/modules/admin/lightboxes.coffee | 1 - app/coffee/modules/admin/project-profile.coffee | 2 -- app/coffee/modules/admin/third-parties.coffee | 3 --- app/coffee/modules/auth.coffee | 5 ----- app/coffee/modules/backlog/lightboxes.coffee | 1 - app/coffee/modules/common/lightboxes.coffee | 2 -- app/coffee/modules/feedback.coffee | 1 - app/coffee/modules/issues/lightboxes.coffee | 2 -- app/coffee/modules/projects/lightboxes.coffee | 1 - app/coffee/modules/search.coffee | 1 - app/coffee/modules/taskboard/lightboxes.coffee | 2 -- .../modules/user-settings/change-password.coffee | 1 - app/coffee/modules/user-settings/main.coffee | 2 -- app/partials/admin/admin-project-modules.jade | 3 +-- app/partials/admin/admin-project-profile.jade | 3 +-- app/partials/admin/admin-third-parties-bitbucket.jade | 4 +--- app/partials/admin/admin-third-parties-github.jade | 4 +--- app/partials/admin/admin-third-parties-gitlab.jade | 3 +-- .../includes/modules/admin/default-values.jade | 3 +-- .../modules/change-password-from-recovery-form.jade | 3 +-- app/partials/includes/modules/forgot-form.jade | 3 +-- .../includes/modules/invitation-login-form.jade | 3 +-- .../includes/modules/invitation-register-form.jade | 3 +-- .../includes/modules/lightbox-add-member.jade | 5 +---- .../includes/modules/lightbox-create-issue.jade | 4 +--- app/partials/includes/modules/lightbox-feedback.jade | 4 +--- .../includes/modules/lightbox-issue-bulk.jade | 3 +-- app/partials/includes/modules/lightbox-search.jade | 3 +-- .../includes/modules/lightbox-sprint-add-edit.jade | 4 +--- app/partials/includes/modules/lightbox-task-bulk.jade | 3 +-- .../includes/modules/lightbox-task-create-edit.jade | 4 +--- app/partials/includes/modules/lightbox-us-bulk.jade | 3 +-- .../includes/modules/lightbox-us-create-edit.jade | 3 +-- app/partials/includes/modules/login-form.jade | 3 +-- app/partials/includes/modules/register-form.jade | 3 +-- .../includes/modules/wizard-create-project.jade | 2 +- app/partials/user/user-change-password.jade | 3 +-- app/partials/user/user-profile.jade | 3 +-- app/styles/components/buttons.scss | 11 ++++++++++- 39 files changed, 35 insertions(+), 82 deletions(-) diff --git a/app/coffee/modules/admin/lightboxes.coffee b/app/coffee/modules/admin/lightboxes.coffee index 6ad67d99..76cfec07 100644 --- a/app/coffee/modules/admin/lightboxes.coffee +++ b/app/coffee/modules/admin/lightboxes.coffee @@ -150,7 +150,6 @@ CreateMembersDirective = ($rs, $rootScope, $confirm, $loading ,lightboxService) submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link: link} diff --git a/app/coffee/modules/admin/project-profile.coffee b/app/coffee/modules/admin/project-profile.coffee index fcdca9f4..2cc35374 100644 --- a/app/coffee/modules/admin/project-profile.coffee +++ b/app/coffee/modules/admin/project-profile.coffee @@ -120,7 +120,6 @@ ProjectProfileDirective = ($repo, $confirm, $loading, $navurls, $location) -> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -154,7 +153,6 @@ ProjectDefaultValuesDirective = ($repo, $confirm, $loading) -> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "$destroy", -> $el.off() diff --git a/app/coffee/modules/admin/third-parties.coffee b/app/coffee/modules/admin/third-parties.coffee index 3e611b46..dd4055e0 100644 --- a/app/coffee/modules/admin/third-parties.coffee +++ b/app/coffee/modules/admin/third-parties.coffee @@ -445,7 +445,6 @@ GithubWebhooksDirective = ($repo, $confirm, $loading) -> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -481,7 +480,6 @@ GitlabWebhooksDirective = ($repo, $confirm, $loading) -> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -517,7 +515,6 @@ BitbucketWebhooksDirective = ($repo, $confirm, $loading) -> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} diff --git a/app/coffee/modules/auth.coffee b/app/coffee/modules/auth.coffee index 9086f1eb..5e260cea 100644 --- a/app/coffee/modules/auth.coffee +++ b/app/coffee/modules/auth.coffee @@ -201,7 +201,6 @@ LoginDirective = ($auth, $confirm, $location, $config, $routeParams, $navUrls, $ return promise.then(onSuccess, onError) $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -242,7 +241,6 @@ RegisterDirective = ($auth, $confirm, $location, $navUrls, $config, $analytics) promise.then(onSuccessSubmit, onErrorSubmit) $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -279,7 +277,6 @@ ForgotPasswordDirective = ($auth, $confirm, $location, $navUrls) -> promise.then(onSuccessSubmit, onErrorSubmit) $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -321,7 +318,6 @@ ChangePasswordFromRecoveryDirective = ($auth, $confirm, $location, $params, $nav promise.then(onSuccessSubmit, onErrorSubmit) $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -471,7 +467,6 @@ CancelAccountDirective = ($repo, $model, $auth, $confirm, $location, $params, $n promise.then(onSuccessSubmit, onErrorSubmit) $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} diff --git a/app/coffee/modules/backlog/lightboxes.coffee b/app/coffee/modules/backlog/lightboxes.coffee index 9f620178..0965fa7e 100644 --- a/app/coffee/modules/backlog/lightboxes.coffee +++ b/app/coffee/modules/backlog/lightboxes.coffee @@ -158,7 +158,6 @@ CreateEditSprint = ($repo, $confirm, $rs, $rootscope, lightboxService, $loading) submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $el.on "click", ".delete-sprint .icon-delete", (event) -> event.preventDefault() diff --git a/app/coffee/modules/common/lightboxes.coffee b/app/coffee/modules/common/lightboxes.coffee index db59fc1c..a72dddbe 100644 --- a/app/coffee/modules/common/lightboxes.coffee +++ b/app/coffee/modules/common/lightboxes.coffee @@ -329,7 +329,6 @@ CreateEditUserstoryDirective = ($repo, $model, $rs, $rootScope, lightboxService, submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $el.on "click", ".close", (event) -> event.preventDefault() @@ -398,7 +397,6 @@ CreateBulkUserstoriesDirective = ($repo, $rs, $rootscope, lightboxService, $load submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "$destroy", -> $el.off() diff --git a/app/coffee/modules/feedback.coffee b/app/coffee/modules/feedback.coffee index 781f6ddc..403b46da 100644 --- a/app/coffee/modules/feedback.coffee +++ b/app/coffee/modules/feedback.coffee @@ -55,7 +55,6 @@ FeedbackDirective = ($lightboxService, $repo, $confirm, $loading)-> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "feedback:show", -> $scope.$apply -> diff --git a/app/coffee/modules/issues/lightboxes.coffee b/app/coffee/modules/issues/lightboxes.coffee index 1195954c..f05f2caf 100644 --- a/app/coffee/modules/issues/lightboxes.coffee +++ b/app/coffee/modules/issues/lightboxes.coffee @@ -75,7 +75,6 @@ CreateIssueDirective = ($repo, $confirm, $rootscope, lightboxService, $loading) submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} @@ -123,7 +122,6 @@ CreateBulkIssuesDirective = ($repo, $rs, $confirm, $rootscope, $loading, lightbo submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "$destroy", -> $el.off() diff --git a/app/coffee/modules/projects/lightboxes.coffee b/app/coffee/modules/projects/lightboxes.coffee index 91497caf..c38afbc8 100644 --- a/app/coffee/modules/projects/lightboxes.coffee +++ b/app/coffee/modules/projects/lightboxes.coffee @@ -118,7 +118,6 @@ CreateProject = ($rootscope, $repo, $confirm, $location, $navurls, $rs, $project submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $el.on "click", ".close", (event) -> event.preventDefault() diff --git a/app/coffee/modules/search.coffee b/app/coffee/modules/search.coffee index 69724468..a863f7ff 100644 --- a/app/coffee/modules/search.coffee +++ b/app/coffee/modules/search.coffee @@ -134,7 +134,6 @@ SearchBoxDirective = ($lightboxService, $navurls, $location, $route)-> $el.find("#search-text").val("") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit return {link:link} diff --git a/app/coffee/modules/taskboard/lightboxes.coffee b/app/coffee/modules/taskboard/lightboxes.coffee index dc8a8fe7..fbdfa1c4 100644 --- a/app/coffee/modules/taskboard/lightboxes.coffee +++ b/app/coffee/modules/taskboard/lightboxes.coffee @@ -83,7 +83,6 @@ CreateEditTaskDirective = ($repo, $model, $rs, $rootscope, $loading, lightboxSer $rootscope.$broadcast(broadcastEvent, data) $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "$destroy", -> $el.off() @@ -127,7 +126,6 @@ CreateBulkTasksDirective = ($repo, $rs, $rootscope, $loading, lightboxService) - submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "$destroy", -> $el.off() diff --git a/app/coffee/modules/user-settings/change-password.coffee b/app/coffee/modules/user-settings/change-password.coffee index 4dc9fa28..d8df8ddd 100644 --- a/app/coffee/modules/user-settings/change-password.coffee +++ b/app/coffee/modules/user-settings/change-password.coffee @@ -97,7 +97,6 @@ UserChangePasswordDirective = ($rs, $confirm, $loading) -> submitButton = $el.find(".submit-button") $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit $scope.$on "$destroy", -> $el.off() diff --git a/app/coffee/modules/user-settings/main.coffee b/app/coffee/modules/user-settings/main.coffee index 7edb8eb1..8a10d312 100644 --- a/app/coffee/modules/user-settings/main.coffee +++ b/app/coffee/modules/user-settings/main.coffee @@ -107,8 +107,6 @@ UserProfileDirective = ($confirm, $auth, $repo) -> $el.on "submit", "form", submit - $el.on "click", ".submit-button", submit - $scope.$on "$destroy", -> $el.off() diff --git a/app/partials/admin/admin-project-modules.jade b/app/partials/admin/admin-project-modules.jade index 21e1be00..82ee7cab 100644 --- a/app/partials/admin/admin-project-modules.jade +++ b/app/partials/admin/admin-project-modules.jade @@ -87,5 +87,4 @@ div.wrapper(tg-project-modules, ng-controller="ProjectProfileController as ctrl" option(value="") Select a videoconference system input(type="text", ng-model="project.videoconferences_salt", placeholder="If you want you can append a salt code to the name of the chat room") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Sign in") Sign in diff --git a/app/partials/admin/admin-project-profile.jade b/app/partials/admin/admin-project-profile.jade index a2e93726..4b8010c7 100644 --- a/app/partials/admin/admin-project-profile.jade +++ b/app/partials/admin/admin-project-profile.jade @@ -48,8 +48,7 @@ div.wrapper(tg-project-profile, ng-controller="ProjectProfileController as ctrl" p All projects are private during Taiga's beta period. - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") Save a.delete-project(href="", title="Delete this project", ng-click="ctrl.openDeleteLightbox()") Delete this project div.lightbox.lightbox-delete-project(tg-lb-delete-project) diff --git a/app/partials/admin/admin-third-parties-bitbucket.jade b/app/partials/admin/admin-third-parties-bitbucket.jade index e2a1f05c..0fb33c63 100644 --- a/app/partials/admin/admin-third-parties-bitbucket.jade +++ b/app/partials/admin/admin-third-parties-bitbucket.jade @@ -27,9 +27,7 @@ div.wrapper.roles(tg-bitbucket-webhooks, ng-controller="BitbucketController as c label(for="valid-origin-ips") Valid origin ips (separated by ,) input(type="text", name="valid-origin-ips", tg-valid-origin-ips, ng-model="bitbucket.valid_origin_ips", placeholder="Bitbucket requests are not signed so the best way of verifying the origin is by IP. If the field is empty there will be no IP validation.", id="valid-origin-ips") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save - + button.button-green.submit-button(type="submit", title="Save") Save a.help-button(href="https://taiga.io/support/bitbucket-integration/", target="_blank") span.icon.icon-help diff --git a/app/partials/admin/admin-third-parties-github.jade b/app/partials/admin/admin-third-parties-github.jade index ae92c1fa..c9ce5e8d 100644 --- a/app/partials/admin/admin-third-parties-github.jade +++ b/app/partials/admin/admin-third-parties-github.jade @@ -23,9 +23,7 @@ div.wrapper.roles(tg-github-webhooks, ng-controller="GithubController as ctrl", .icon.icon-copy .help-copy Copy to clipboard: Ctrl+C - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save - + button.button-green.submit-button(type="submit", title="Save") Save a.help-button(href="https://taiga.io/support/github-integration/", target="_blank") span.icon.icon-help diff --git a/app/partials/admin/admin-third-parties-gitlab.jade b/app/partials/admin/admin-third-parties-gitlab.jade index dc89117f..6ce05ce2 100644 --- a/app/partials/admin/admin-third-parties-gitlab.jade +++ b/app/partials/admin/admin-third-parties-gitlab.jade @@ -31,8 +31,7 @@ block content label(for="valid-origin-ips") Valid origin ips (separated by ,) input(type="text", name="valid-origin-ips", tg-valid-origin-ips, ng-model="gitlab.valid_origin_ips", placeholder="Gitlab requests are not signed so the best way of verifying the origin is by IP. If the field is empty there will be no IP validation.", id="valid-origin-ips") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") Save a.help-button(href="https://taiga.io/support/gitlab-integration/", target="_blank") span.icon.icon-help diff --git a/app/partials/includes/modules/admin/default-values.jade b/app/partials/includes/modules/admin/default-values.jade index c2d74b2c..d0e91e80 100644 --- a/app/partials/includes/modules/admin/default-values.jade +++ b/app/partials/includes/modules/admin/default-values.jade @@ -36,5 +36,4 @@ section.default-values ng-options="s.id as s.name for s in issueStatusList") fieldset - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") Save diff --git a/app/partials/includes/modules/change-password-from-recovery-form.jade b/app/partials/includes/modules/change-password-from-recovery-form.jade index 8a2e36a7..22f527df 100644 --- a/app/partials/includes/modules/change-password-from-recovery-form.jade +++ b/app/partials/includes/modules/change-password-from-recovery-form.jade @@ -16,5 +16,4 @@ div.change-password-form-container(tg-change-password-from-recovery) input(type="password", name="password2", id="password2", ng-model="data.password2", data-required="true", data-equalto="#password", placeholder="Re-type new password") fieldset - a.button.button-change-password.button-gray.submit-button(href="", title="Reset Password") Reset Password - button(type="submit", class="hidden") + button.button-change-password.button-gray.submit-button(type="submit", title="Reset Password") Reset Password diff --git a/app/partials/includes/modules/forgot-form.jade b/app/partials/includes/modules/forgot-form.jade index 074a4051..fe7b595f 100644 --- a/app/partials/includes/modules/forgot-form.jade +++ b/app/partials/includes/modules/forgot-form.jade @@ -10,7 +10,6 @@ div.forgot-form-container(tg-forgot-password) input(type="text", name="username", ng-model="data.username", data-required="true", placeholder="Username or email") fieldset - button(type="submit", class="hidden") - a.button.button-gray.submit-button.button-forgot(href="", title="Reset Password") Reset Password + button.button-gray.submit-button.button-forgot(type="submit", title="Reset Password") Reset Password a(href="", title="Login", tg-nav="login") Nah, take me back. I think I remember it. diff --git a/app/partials/includes/modules/invitation-login-form.jade b/app/partials/includes/modules/invitation-login-form.jade index d6f35ebd..f298fa5a 100644 --- a/app/partials/includes/modules/invitation-login-form.jade +++ b/app/partials/includes/modules/invitation-login-form.jade @@ -8,7 +8,6 @@ form.login-form placeholder="Password") a.forgot-pass(href="", tg-nav="forgot-password", title="Did you forgot your password?") Forgot it? fieldset - a.button.button-login.button-gray.submit-button(href="", title="Log in") Enter - button(type="submit", class="hidden") + button.button-login.button-gray.submit-button(type="submit", title="Enter") Enter fieldset(tg-github-login-button) diff --git a/app/partials/includes/modules/invitation-register-form.jade b/app/partials/includes/modules/invitation-register-form.jade index bfd4118e..04ef0fbb 100644 --- a/app/partials/includes/modules/invitation-register-form.jade +++ b/app/partials/includes/modules/invitation-register-form.jade @@ -20,7 +20,6 @@ form.register-form placeholder="Set a password") fieldset - button(type="submit", class="hidden") - a.button.button-register.button-gray.submit-button(href="", title="Sign up") Sign up + button.button-register.button-gray.submit-button(type="submit", title="Sign up") Sign up tg-terms-notice diff --git a/app/partials/includes/modules/lightbox-add-member.jade b/app/partials/includes/modules/lightbox-add-member.jade index 596c40d5..dfb3d4eb 100644 --- a/app/partials/includes/modules/lightbox-add-member.jade +++ b/app/partials/includes/modules/lightbox-add-member.jade @@ -6,9 +6,6 @@ form //- Form is set in a directive .add-member-forms - - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Create") - span Create + button.button-green.submit-button(type="submit", title="Create") Create p.help-text If users are already registered on Taiga, they will be added automatically. Otherwise they will receive an invitation. diff --git a/app/partials/includes/modules/lightbox-create-issue.jade b/app/partials/includes/modules/lightbox-create-issue.jade index 54bf1234..cf36de34 100644 --- a/app/partials/includes/modules/lightbox-create-issue.jade +++ b/app/partials/includes/modules/lightbox-create-issue.jade @@ -20,6 +20,4 @@ form textarea.description(placeholder="Description", ng-model="issue.description") // include lightbox-attachments - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") - span Create + button.button-green.submit-button(type="submit", title="Create") Create diff --git a/app/partials/includes/modules/lightbox-feedback.jade b/app/partials/includes/modules/lightbox-feedback.jade index 7003e702..1aa22336 100644 --- a/app/partials/includes/modules/lightbox-feedback.jade +++ b/app/partials/includes/modules/lightbox-feedback.jade @@ -6,6 +6,4 @@ form textarea(ng-model="feedback.comment", data-required="true", placeholder="...a bug, some suggestions, something cool... or even your worst nightmare with Taiga") fieldset - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Send feedback") - span Send feedback + button.button-green.submit-button(type="submit", title="Send feedback") Send feedback diff --git a/app/partials/includes/modules/lightbox-issue-bulk.jade b/app/partials/includes/modules/lightbox-issue-bulk.jade index 485fc429..a3d70883 100644 --- a/app/partials/includes/modules/lightbox-issue-bulk.jade +++ b/app/partials/includes/modules/lightbox-issue-bulk.jade @@ -5,5 +5,4 @@ form fieldset textarea(cols="200", wrap="off", tg-limit-line-length, tr="placeholder:common.one-item-line", ng-model="new.bulk", data-required="true", data-linewidth="200") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") Save diff --git a/app/partials/includes/modules/lightbox-search.jade b/app/partials/includes/modules/lightbox-search.jade index 592d46ce..09ef479f 100644 --- a/app/partials/includes/modules/lightbox-search.jade +++ b/app/partials/includes/modules/lightbox-search.jade @@ -5,5 +5,4 @@ form fieldset input(type="text", name="text", id="search-text", placeholder="What are you looking for?", data-required="true") fieldset - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Search") Search \ No newline at end of file + button.button-green.submit-button(type="submit", title="Search") Search \ No newline at end of file diff --git a/app/partials/includes/modules/lightbox-sprint-add-edit.jade b/app/partials/includes/modules/lightbox-sprint-add-edit.jade index 9fa21fcb..61ab85ad 100644 --- a/app/partials/includes/modules/lightbox-sprint-add-edit.jade +++ b/app/partials/includes/modules/lightbox-sprint-add-edit.jade @@ -15,9 +15,7 @@ form input.date-end(type="text", name="estimated_finish", placeholder="Estimated End", ng-model="sprint.estimated_finish", data-required="true", tg-date-selector) - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Create") - span Create + button.button-green.submit-button(type="submit", title="Create") Create div(tg-check-permission="delete_milestone") span.delete-sprint.hidden Do you want to delete this sprint? diff --git a/app/partials/includes/modules/lightbox-task-bulk.jade b/app/partials/includes/modules/lightbox-task-bulk.jade index 28b77204..8b1ef334 100644 --- a/app/partials/includes/modules/lightbox-task-bulk.jade +++ b/app/partials/includes/modules/lightbox-task-bulk.jade @@ -5,5 +5,4 @@ form fieldset textarea(cols="200", wrap="off", tg-limit-line-length, tr="placeholder:common.one-item-line", ng-model="form.data", data-required="true") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") Save diff --git a/app/partials/includes/modules/lightbox-task-create-edit.jade b/app/partials/includes/modules/lightbox-task-create-edit.jade index 770f66ac..c07b101a 100644 --- a/app/partials/includes/modules/lightbox-task-create-edit.jade +++ b/app/partials/includes/modules/lightbox-task-create-edit.jade @@ -34,6 +34,4 @@ form tg-blocking-message-input(watch="task.is_blocked", ng-model="task.blocked_note") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") - span Create + button.button-green.submit-button(type="submit", title="Create") Create diff --git a/app/partials/includes/modules/lightbox-us-bulk.jade b/app/partials/includes/modules/lightbox-us-bulk.jade index 8c92eeae..45fe85e0 100644 --- a/app/partials/includes/modules/lightbox-us-bulk.jade +++ b/app/partials/includes/modules/lightbox-us-bulk.jade @@ -5,5 +5,4 @@ form fieldset textarea(cols="200", wrap="off", tg-limit-line-length, tr="placeholder:common.one-item-line", ng-model="new.bulk", data-required="true", data-linewidth="200") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save \ No newline at end of file + button.button-green.submit-button(type="submit", title="Save") Save \ No newline at end of file diff --git a/app/partials/includes/modules/lightbox-us-create-edit.jade b/app/partials/includes/modules/lightbox-us-create-edit.jade index 817b8f54..0a6d73e7 100644 --- a/app/partials/includes/modules/lightbox-us-create-edit.jade +++ b/app/partials/includes/modules/lightbox-us-create-edit.jade @@ -36,5 +36,4 @@ form tg-blocking-message-input(watch="us.is_blocked", ng-model="us.blocked_note") - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Submit") Create + button.button-green.submit-button(type="submit", title="Create") Create diff --git a/app/partials/includes/modules/login-form.jade b/app/partials/includes/modules/login-form.jade index 9174b672..67d510bf 100644 --- a/app/partials/includes/modules/login-form.jade +++ b/app/partials/includes/modules/login-form.jade @@ -10,8 +10,7 @@ div.login-form-container(tg-login) a.forgot-pass(href="", tg-nav="forgot-password", title="Did you forgot your password?") Forgot it? fieldset - button(type="submit", class="hidden") - a.button.button-login.button-gray.submit-button(href="", title="Sign in") Sign in + button.button-green.submit-button(type="submit", title="Sign in") Sign in fieldset(tg-github-login-button) diff --git a/app/partials/includes/modules/register-form.jade b/app/partials/includes/modules/register-form.jade index 6aa4cccd..5341588a 100644 --- a/app/partials/includes/modules/register-form.jade +++ b/app/partials/includes/modules/register-form.jade @@ -21,8 +21,7 @@ div.register-form-container(tg-register) placeholder="Set a password (case sensitive)") fieldset - button(type="submit", class="hidden") - a.button.button-register.button-gray.submit-button(href="", title="Sign up") Sign up + button.button-register.button-gray.submit-button(type="submit", title="Sign up") Sign up fieldset(tg-github-login-button) diff --git a/app/partials/includes/modules/wizard-create-project.jade b/app/partials/includes/modules/wizard-create-project.jade index 3395d5ac..52075256 100644 --- a/app/partials/includes/modules/wizard-create-project.jade +++ b/app/partials/includes/modules/wizard-create-project.jade @@ -30,7 +30,7 @@ form fieldset.wizard-action div a.button-prev.button.button-gray(href="", title="Prev") Prev - a.submit-button.button.button-green(href="", title="Create") Create + button.button-green.submit-button(type="submit", title="Create") Create button(type="submit", class="hidden") diff --git a/app/partials/user/user-change-password.jade b/app/partials/user/user-change-password.jade index 5ffef696..4eb2698d 100644 --- a/app/partials/user/user-change-password.jade +++ b/app/partials/user/user-change-password.jade @@ -19,5 +19,4 @@ div.wrapper(tg-user-change-password, ng-controller="UserChangePasswordController label(for="retype-password") Retype Password input(type="password", placeholder="Retype Password", id="retype-password", ng-model="newPassword2") fieldset - button(type="submit", class="hidden") - a.button.button-green.submit-button(href="", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") Save diff --git a/app/partials/user/user-profile.jade b/app/partials/user/user-profile.jade index 5be8ae8b..9819c23e 100644 --- a/app/partials/user/user-profile.jade +++ b/app/partials/user/user-profile.jade @@ -49,8 +49,7 @@ div.wrapper(tg-user-profile, ng-controller="UserSettingsController as ctrl", ng-model="user.bio") fieldset.submit - button(type="submit", title="Save", class="hidden") - a.button.button-green.save-profile.submit-button(href="") Save + button.button-green.submit-button(type="submit", title="Save") Save a.delete-account(href="", title="Delete Taiga account", ng-click="ctrl.openDeleteLightbox()") Delete Taiga account diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index 67d55b3c..ba919eba 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -17,8 +17,17 @@ @extend %button; } -a.button-green { +button { + @extend %button; +} + +.submit-button { + width: 100%; +} + +.button-green { background: $green-taiga; + border: 0; color: $white; vertical-align: middle; &:hover, From d9028e5b520d1ebca9b9801c0a75efc7a5656161 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Mon, 2 Feb 2015 11:55:57 +0100 Subject: [PATCH 015/207] Remove :poop: --- app/partials/task/related-task-row-edit.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/task/related-task-row-edit.jade b/app/partials/task/related-task-row-edit.jade index 890f7a59..cfc4950f 100644 --- a/app/partials/task/related-task-row-edit.jade +++ b/app/partials/task/related-task-row-edit.jade @@ -1,6 +1,6 @@ .tasks .task-name - input(type='text', value!='<%- task.subject %> sdfdsf', placeholder='Type the task subject') + input(type='text', value!='<%- task.subject %>', placeholder='Type the task subject') .task-settings a.icon.icon-floppy(href='', title='Save') a.icon.icon-delete.cancel-edit(href='', title='Cancel') From 5e4c64a7f055f5c82f96f1ab8950b559359522e6 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 30 Jan 2015 07:50:01 +0100 Subject: [PATCH 016/207] fix assigned to issues overflow --- app/styles/modules/issues/issues-table.scss | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/app/styles/modules/issues/issues-table.scss b/app/styles/modules/issues/issues-table.scss index 3e358adf..9ff1a1fc 100644 --- a/app/styles/modules/issues/issues-table.scss +++ b/app/styles/modules/issues/issues-table.scss @@ -52,11 +52,9 @@ width: 75px; } .subject { - flex-basis: 300px; - flex-grow: 7; - flex-shrink: 0; overflow: hidden; padding-right: 1rem; + width: 100%; a { @include ellipsis(100%); display: block; @@ -72,13 +70,17 @@ .assigned-field, .created-field , .assigned-field { - flex-basis: 120px; + flex-basis: 140px; flex-grow: 1; flex-shrink: 0; padding: 0 1rem; position: relative; text-align: left; } + .assigned-field { + flex: 0 0 160px; + max-width: 160px; + } .issue-assignedto { cursor: pointer; position: relative; From f8b4b0130ee8855282a9fab92da0d8860ab34a62 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 30 Jan 2015 09:36:31 +0100 Subject: [PATCH 017/207] fix paginator margin --- app/styles/components/paginator.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/styles/components/paginator.scss b/app/styles/components/paginator.scss index 6cfaaf04..7d4ec1e3 100644 --- a/app/styles/components/paginator.scss +++ b/app/styles/components/paginator.scss @@ -1,17 +1,17 @@ .paginator { margin: 2rem 0; ul { + display: flex; margin-left: 1rem; } li { - display: inline-block; + margin-right: .4rem; } a, .active span, .dots { background: $gray-light; color: $white; - margin-right: .1rem; padding: .5rem 1rem; transition: all .3s linear; } From fad7819d611195a4637c4b342bdd529bc0387f86 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 12:30:49 +0100 Subject: [PATCH 018/207] Excluded plugins from lint and necessary qualiying elements --- scsslint.yml | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/scsslint.yml b/scsslint.yml index 77f808be..e8543b80 100644 --- a/scsslint.yml +++ b/scsslint.yml @@ -1,3 +1,8 @@ +exclude: + - 'app/styles/components/markitup.scss' + - 'app/styles/bourbon/**' + - 'app/styles/vendor/**' + linters: BorderZero: enabled: true @@ -77,6 +82,15 @@ linters: enabled: true extra_properties: [] + QualifyingElement: + enabled: true + allow_element_with_attribute: true + exclude: + - 'app/styles/components/buttons.scss' + - 'app/styles/layout/forms.scss' + - 'app/styles/components/help-notion-button.scss' + - 'app/styles/components/markdown-help.scss' + SelectorDepth: enabled: true max_depth: 4 From 61c97358bfa450a06137c54e2094bc681ef6b45c Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 30 Jan 2015 12:51:59 +0100 Subject: [PATCH 019/207] Fixing config in navurls --- app/coffee/modules/base/urls.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/base/urls.coffee b/app/coffee/modules/base/urls.coffee index f6d9e061..c542476a 100644 --- a/app/coffee/modules/base/urls.coffee +++ b/app/coffee/modules/base/urls.coffee @@ -30,7 +30,7 @@ class UrlsService extends taiga.Service constructor: (@config) -> @.urls = {} - @.mainUrl = config.get("api") + @.mainUrl = @config.get("api") update: (urls) -> @.urls = _.merge(@.urls, urls) From ed3536157e9045bc22efd99687317e236df13957 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Feb 2015 14:02:05 +0100 Subject: [PATCH 020/207] Fix line-height and font-size --- app/styles/layout/us-detail.scss | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index 67853687..4730efae 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -297,9 +297,10 @@ text-align: center; } .role { + @extend %small; @include ellipsis(90%); display: inline-block; - line-height: .8rem; + line-height: 1rem; text-align: center; } .popover { From 9f2abee00809dd53f2ec355b109affe023ad47e7 Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Mon, 2 Feb 2015 15:05:12 +0100 Subject: [PATCH 021/207] Add tooltip for points per role --- .../common/estimation/us-estimation-points-per-role.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/common/estimation/us-estimation-points-per-role.jade b/app/partials/common/estimation/us-estimation-points-per-role.jade index e905cf6b..7491d5a8 100644 --- a/app/partials/common/estimation/us-estimation-points-per-role.jade +++ b/app/partials/common/estimation/us-estimation-points-per-role.jade @@ -3,7 +3,7 @@ ul.points-per-role span.points <%- totalPoints %> span.role total <% _.each(roles, function(role) { %> - li(class!="total <% if(editable){ %>clickable<% } %>", data-role-id!="<%- role.id %>") + li(class!="total <% if(editable){ %>clickable<% } %>", data-role-id!="<%- role.id %>", title!="<%- role.name %>") span.points <%- role.points %> span.role <%- role.name %> <% }); %> From 11328a0805e74bc0cf71f0ed8c761a4a32249765 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 29 Jan 2015 11:38:23 +0100 Subject: [PATCH 022/207] Kanban drag icon removed --- app/partials/includes/components/kanban-task.jade | 1 - app/partials/includes/components/taskboard-task.jade | 3 --- app/partials/kanban/kanban-task.jade | 1 - 3 files changed, 5 deletions(-) diff --git a/app/partials/includes/components/kanban-task.jade b/app/partials/includes/components/kanban-task.jade index 8431c184..df075a13 100644 --- a/app/partials/includes/components/kanban-task.jade +++ b/app/partials/includes/components/kanban-task.jade @@ -20,4 +20,3 @@ div.kanban-task-inner(ng-class="{'task-archived': us.isArchived}") p Drag & drop again to undo a.icon.icon-edit(tg-check-permission="modify_us", href="", title="Edit", ng-hide="us.isArchived") - a.icon.icon-drag-h(tg-check-permission="modify_us", href="", title="Drag&Drop", ng-hide="us.isArchived") diff --git a/app/partials/includes/components/taskboard-task.jade b/app/partials/includes/components/taskboard-task.jade index 29311f7c..0dd6bbdf 100644 --- a/app/partials/includes/components/taskboard-task.jade +++ b/app/partials/includes/components/taskboard-task.jade @@ -9,6 +9,3 @@ div.taskboard-task-inner tg-nav="project-tasks-detail:project=project.slug,ref=task.ref") a.icon.icon-edit(tg-check-permission="modify_task", href="", title="Edit task") - - a.icon.icon-drag-h(tg-check-permission="modify_task", - href="", title="Drag&Drop") diff --git a/app/partials/kanban/kanban-task.jade b/app/partials/kanban/kanban-task.jade index 8431c184..df075a13 100644 --- a/app/partials/kanban/kanban-task.jade +++ b/app/partials/kanban/kanban-task.jade @@ -20,4 +20,3 @@ div.kanban-task-inner(ng-class="{'task-archived': us.isArchived}") p Drag & drop again to undo a.icon.icon-edit(tg-check-permission="modify_us", href="", title="Edit", ng-hide="us.isArchived") - a.icon.icon-drag-h(tg-check-permission="modify_us", href="", title="Drag&Drop", ng-hide="us.isArchived") From cb654b238ebd3ec53c0688035ff727e04021dcb1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 29 Jan 2015 11:38:54 +0100 Subject: [PATCH 023/207] Improved secondary card text legibility --- app/styles/dependencies/colors.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/dependencies/colors.scss b/app/styles/dependencies/colors.scss index e5f37455..6b73babd 100755 --- a/app/styles/dependencies/colors.scss +++ b/app/styles/dependencies/colors.scss @@ -31,4 +31,4 @@ $button-gray-hover: #879b89; $postit: #fff8e4; $postit-hover: #f1e8cd; -$postit-dark-hover: #e4d6ad; +$postit-dark-hover: #cfc29b; From ab8b5efd3bd4ca1221419da0c22525d955aea55c Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 2 Feb 2015 12:51:57 +0100 Subject: [PATCH 024/207] remove duplicated & unused jade files --- .../includes/components/kanban-task.jade | 22 --------- app/partials/includes/modules/nav.jade | 48 ------------------- .../modules/search-result-issues-table.jade | 15 ------ app/partials/issue/issues-status-display.jade | 9 ---- 4 files changed, 94 deletions(-) delete mode 100644 app/partials/includes/components/kanban-task.jade delete mode 100644 app/partials/includes/modules/nav.jade delete mode 100644 app/partials/includes/modules/search-result-issues-table.jade delete mode 100644 app/partials/issue/issues-status-display.jade diff --git a/app/partials/includes/components/kanban-task.jade b/app/partials/includes/components/kanban-task.jade deleted file mode 100644 index df075a13..00000000 --- a/app/partials/includes/components/kanban-task.jade +++ /dev/null @@ -1,22 +0,0 @@ -div.kanban-tagline(tg-colorize-tags="us.tags", tg-colorize-tags-type="kanban", ng-hide="us.isArchived") -div.kanban-task-inner(ng-class="{'task-archived': us.isArchived}") - div.avatar-wrapper(tg-kanban-user-avatar="us.assigned_to", ng-model="us", ng-hide="us.isArchived") - div.task-text(ng-hide="us.isArchived") - a.task-assigned(href="", title="Assign User Story") - span.task-num(tg-bo-ref="us.ref") - a.task-name(href="", title="See user story detail", ng-bind="us.subject", - tg-nav="project-userstories-detail:project=project.slug,ref=us.ref") - - p.task-points(href="", title="Total Us points") - span(ng-if="us.total_points !== null", ng-bind="us.total_points") - span(ng-if="us.total_points !== null") points - span(ng-if="us.total_points === null") Not estimated - - div.task-archived-text(ng-show="us.isArchived") - p You have archived - p - span.task-num(tg-bo-ref="us.ref") - span.task-name(ng-bind="us.subject") - p Drag & drop again to undo - - a.icon.icon-edit(tg-check-permission="modify_us", href="", title="Edit", ng-hide="us.isArchived") diff --git a/app/partials/includes/modules/nav.jade b/app/partials/includes/modules/nav.jade deleted file mode 100644 index 738da6e4..00000000 --- a/app/partials/includes/modules/nav.jade +++ /dev/null @@ -1,48 +0,0 @@ -// This menu is deprecated and it is only available -// for correct not integrated pages. -// The compiled version of this is embedded in coffescript -// due to mandatory tricky hacks related to scope resolution. -// Check base.coffee for the JS template -nav.menu - h1.logo - a(href="", title="Home") - img(src="/images/logo.png", alt="Taiga") - ul.main-nav - li(data-name="search") - a(href="", title="Search", tg-nav="project-search:project=project.slug") - span.icon.icon-search - span.item Search - li(data-name="backlog", tg-nav="project-backlog:project=project.slug") - a.active(href="", title="Backlog") - span.icon.icon-backlog - span.item Backlog - li(data-name="kanban") - a(href="", title="Kanban") - span.icon.icon-kanban - span.item Kanban - li(data-name="issues") - a(href="", title="Issues", tg-nav="project-issues:project=project.slug") - span.icon.icon-issues - span.item Issues - li(data-name="wiki") - a(href="", title="Wiki") - span.icon.icon-wiki - span.item Wiki - li(data-name="video") - a(href="", title="Meet Up") - span.icon.icon-video - span.item Meet Up - div.user - div.user-settings - ul.popover - li - a(href="", title="Account settings") Account settings - li - a(href="", title="Logout") Logout - a.avatar(href="", title="User preferences") - img(src="http://thecodeplayer.com/u/uifaces/12.jpg", alt="username") - - div.settings - a(href="", title="User preferences") Pilar - a(href="", title="Site preferences") - span.icon.icon-settings diff --git a/app/partials/includes/modules/search-result-issues-table.jade b/app/partials/includes/modules/search-result-issues-table.jade deleted file mode 100644 index b9ce175b..00000000 --- a/app/partials/includes/modules/search-result-issues-table.jade +++ /dev/null @@ -1,15 +0,0 @@ -section.search-result-table.basic-table - div.row.title - div.user-stories.width-6 Issue - div.status.width-2 Status - div.points.width-1 Assigned to - - for (var x = 0; x < 50; x++) - div.row.table-main - div.user-stories.width-6 - div.user-story-name - a(href="") Crear el perfil de usuario Senior en el admin - div.status.width-2 Status - div.points.width-1 - figure.avatar - img(src="http://thecodeplayer.com/u/uifaces/12.jpg", alt="username") - figcaption Pilar \ No newline at end of file diff --git a/app/partials/issue/issues-status-display.jade b/app/partials/issue/issues-status-display.jade deleted file mode 100644 index fd283835..00000000 --- a/app/partials/issue/issues-status-display.jade +++ /dev/null @@ -1,9 +0,0 @@ -span - <% if (status.is_closed) { %> - | Closed - <% } else { %> - | Open - <% } %> - -span(class="us-detail-status", style!="color:<%- status.color %>") - | <%- status.name %> From e992eabf359b096160b232b96a7ee4d75006886d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Mon, 2 Feb 2015 12:57:32 +0100 Subject: [PATCH 025/207] Fix #tg-2147: set focus to the search input when assigned-to/watchers lightbox is opened --- app/coffee/modules/common/lightboxes.coffee | 25 +++++++++++++-------- 1 file changed, 16 insertions(+), 9 deletions(-) diff --git a/app/coffee/modules/common/lightboxes.coffee b/app/coffee/modules/common/lightboxes.coffee index db59fc1c..667edf39 100644 --- a/app/coffee/modules/common/lightboxes.coffee +++ b/app/coffee/modules/common/lightboxes.coffee @@ -31,9 +31,11 @@ debounce = @.taiga.debounce # the lightboxContent hide/show doesn't have sense because is an IE hack class LightboxService extends taiga.Service - constructor: (@animationFrame) -> + constructor: (@animationFrame, @q) -> open: ($el) -> + defered = @q.defer() + lightboxContent = $el.children().not(".close") lightboxContent.hide() @@ -44,12 +46,15 @@ class LightboxService extends taiga.Service @animationFrame.add => $el.addClass("open") lightboxContent.show() + defered.resolve() docEl = angular.element(document) docEl.on "keydown.lightbox", (e) => code = if e.keyCode then e.keyCode else e.which @.close($el) if code == 27 + return defered.promise + close: ($el) -> docEl = angular.element(document) docEl.off(".lightbox") @@ -66,7 +71,7 @@ class LightboxService extends taiga.Service @.close($(lightboxEl)) -module.service("lightboxService", ["animationFrame", LightboxService]) +module.service("lightboxService", ["animationFrame", "$q", LightboxService]) class LightboxKeyboardNavigationService extends taiga.Service @@ -442,8 +447,6 @@ AssignedToLightboxDirective = (lightboxService, lightboxKeyboardNavigationServic return _.contains(username, text) render = (selected, text) -> - $el.find("input").focus() - users = _.clone($scope.activeUsers, true) users = _.reject(users, {"id": selected.id}) if selected? users = _.filter(users, _.partial(filterUsers, text)) if text? @@ -468,11 +471,14 @@ AssignedToLightboxDirective = (lightboxService, lightboxKeyboardNavigationServic selectedUser = $scope.usersById[assignedToId] render(selectedUser) - lightboxService.open($el) - $el.find('input').focus() + lightboxService.open($el).then -> + $el.find('input').focus() + $scope.$watch "usersSearch", (searchingText) -> - render(selectedUser, searchingText) if searchingText? + if searchingText? + render(selectedUser, searchingText) + $el.find('input').focus() $el.on "click", ".watcher-single", (event) -> event.preventDefault() @@ -540,7 +546,6 @@ WatchersLightboxDirective = ($repo, lightboxService, lightboxKeyboardNavigationS # Render the specific list of users. render = (users) -> - $el.find("input").focus() ctx = { selected: false users: _.first(users, 5) @@ -560,7 +565,8 @@ WatchersLightboxDirective = ($repo, lightboxService, lightboxKeyboardNavigationS users = getFilteredUsers() render(users) - lightboxService.open($el) + lightboxService.open($el).then -> + $el.find("input").focus() lightboxKeyboardNavigationService.init($el) $scope.$watch "usersSearch", (searchingText) -> @@ -569,6 +575,7 @@ WatchersLightboxDirective = ($repo, lightboxService, lightboxKeyboardNavigationS users = getFilteredUsers(searchingText) render(users) + $el.find("input").focus() $el.on "click", ".watcher-single", debounce 2000, (event) -> closeLightbox() From 8934861cc7df76d8cc22888836c173921557c4e9 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Tue, 3 Feb 2015 08:33:29 +0100 Subject: [PATCH 026/207] Adding max text length to invitation text --- app/coffee/modules/admin/lightboxes.coffee | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/lightboxes.coffee b/app/coffee/modules/admin/lightboxes.coffee index 6ad67d99..cadaf42e 100644 --- a/app/coffee/modules/admin/lightboxes.coffee +++ b/app/coffee/modules/admin/lightboxes.coffee @@ -33,7 +33,9 @@ MAX_MEMBERSHIP_FIELDSETS = 4 CreateMembersDirective = ($rs, $rootScope, $confirm, $loading ,lightboxService) -> extraTextTemplate = """
- +
""" From b62978080462aa4f488657e53b7c0eedd7cecb2e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 3 Feb 2015 08:39:41 +0100 Subject: [PATCH 027/207] Fixed width and height --- app/styles/layout/us-detail.scss | 1 + 1 file changed, 1 insertion(+) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index 4730efae..ebf4b7e3 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -273,6 +273,7 @@ flex-grow: 1; flex-shrink: 0; margin: .1rem; + max-width: 50%; padding: .5rem; position: relative; text-align: center; From 09235a9bc5f49c19047ec784132beb99868f9a82 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 3 Feb 2015 09:04:38 +0100 Subject: [PATCH 028/207] Fix padding --- app/styles/layout/us-detail.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index ebf4b7e3..bbc26169 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -274,7 +274,7 @@ flex-shrink: 0; margin: .1rem; max-width: 50%; - padding: .5rem; + padding: .5rem 0 .1rem; position: relative; text-align: center; transition: color .3s linear; From f69d9ad604151a2d3839dc949716fe896fe76883 Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Tue, 3 Feb 2015 10:07:58 +0100 Subject: [PATCH 029/207] Fix task completed title width --- app/partials/us/us-task-progress.jade | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/partials/us/us-task-progress.jade b/app/partials/us/us-task-progress.jade index 804b154c..8ced2ed5 100644 --- a/app/partials/us/us-task-progress.jade +++ b/app/partials/us/us-task-progress.jade @@ -1,3 +1,3 @@ .current-progress(style!='width:<%- progress %>%') - span.tasks-completed - | <%- totalClosedTasks %>/<%- totalTasks %> tasks completed \ No newline at end of file +div.tasks-completed + | <%- totalClosedTasks %>/<%- totalTasks %> tasks completed \ No newline at end of file From e62c84a76f7f1ac9268c588efea754f209a26f44 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Mon, 2 Feb 2015 21:39:19 +0100 Subject: [PATCH 030/207] Fix Issue #2072: I can't add comments after the role points are edited. :sparkles: rolepoints reparo!!! :sparkles: --- app/coffee/modules/common/estimation.coffee | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/app/coffee/modules/common/estimation.coffee b/app/coffee/modules/common/estimation.coffee index 6965bd24..c3067fd9 100644 --- a/app/coffee/modules/common/estimation.coffee +++ b/app/coffee/modules/common/estimation.coffee @@ -156,7 +156,7 @@ UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> return $scope.project.my_permissions.indexOf("modify_us") != -1 render = (us) -> - totalPoints = if us.total_points? then us.total_points else "?" + totalPoints = calculateTotalPoints(us.points) or "?" computableRoles = _.filter($scope.project.roles, "computable") roles = _.map computableRoles, (role) -> @@ -204,8 +204,8 @@ UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> $el.find(".pop-points-open").show() - calculateTotalPoints = (us) -> - values = _.map(us.points, (v, k) -> $scope.pointsById[v]?.value) + calculateTotalPoints = (points) -> + values = _.map(points, (v, k) -> $scope.pointsById[v]?.value) if values.length == 0 return "0" @@ -218,15 +218,12 @@ UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> save = $qqueue.bindAdd (roleId, pointId) => $el.find(".popover").popover().close() - # Hell starts here - us = angular.copy($model.$modelValue) points = _.clone($model.$modelValue.points, true) points[roleId] = pointId - us.setAttr('points', points) + + us = $model.$modelValue.clone() us.points = points - us.total_points = calculateTotalPoints(us) $model.$setViewValue(us) - # Hell ends here onSuccess = -> $confirm.notify("success") @@ -236,7 +233,7 @@ UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> us.revert() $model.$setViewValue(us) - $repo.save($model.$modelValue).then(onSuccess, onError) + $repo.save(us).then(onSuccess, onError) $el.on "click", ".total.clickable", (event) -> event.preventDefault() @@ -275,4 +272,5 @@ UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> require: "ngModel" } -module.directive("tgUsEstimation", ["$rootScope", "$tgRepo", "$tgConfirm", "$tgQqueue", "$tgTemplate", UsEstimationDirective]) +module.directive("tgUsEstimation", ["$rootScope", "$tgRepo", "$tgConfirm", "$tgQqueue", "$tgTemplate", + UsEstimationDirective]) From 3839ea8a8c638d1436a098800acaef84264a36dc Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Mon, 2 Feb 2015 12:56:48 +0100 Subject: [PATCH 031/207] Tasks should retain all history in their full view --- app/coffee/modules/common/history.coffee | 31 ++++++++++++++----- .../common/history/history-change-list.jade | 17 ++++++++++ 2 files changed, 41 insertions(+), 7 deletions(-) create mode 100644 app/partials/common/history/history-change-list.jade diff --git a/app/coffee/modules/common/history.coffee b/app/coffee/modules/common/history.coffee index 08c34fda..0f7651b8 100644 --- a/app/coffee/modules/common/history.coffee +++ b/app/coffee/modules/common/history.coffee @@ -51,6 +51,13 @@ class HistoryController extends taiga.Controller delete historyResult.values_diff.description_html delete historyResult.values_diff.description_diff + # If block note was modified take only the blocked_note_html field + if historyResult.values_diff.blocked_note_diff? + historyResult.values_diff.blocked_note = historyResult.values_diff.blocked_note_diff + + delete historyResult.values_diff.blocked_note_html + delete historyResult.values_diff.blocked_note_diff + @scope.history = history @scope.comments = _.filter(history, (item) -> item.comment != "") @@ -66,6 +73,7 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> templateChangePoints = $template.get("common/history/history-change-points.html", true) templateChangeGeneric = $template.get("common/history/history-change-generic.html", true) templateChangeAttachment = $template.get("common/history/history-change-attachment.html", true) + templateChangeList = $template.get("common/history/history-change-list.html", true) templateDeletedComment = $template.get("common/history/history-deleted-comment.html", true) templateActivity = $template.get("common/history/history-activity.html", true) templateBaseEntries = $template.get("common/history/history-base-entries.html", true) @@ -103,6 +111,9 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> # Attachment is_deprecated: "is deprecated" + + blocked_note: "blocked note" + is_blocked: "is blocked" } # TODO i18n return humanizedFieldNames[field] or field @@ -121,18 +132,18 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> formatChange = (change) -> if _.isArray(change) if change.length == 0 - return "nil" + return "empty" return change.join(", ") if change == "" - return "nil" + return "empty" + + if not change? or change == false + return "no" if change == true return "yes" - if change == false - return "no" - return change # Render into string (operations without mutability) @@ -164,12 +175,18 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> renderChangeEntry = (field, value) -> if field == "description" - # TODO: i18n - return templateChangeDiff({name: "description", diff: value[1]}) + return templateChangeDiff({name: getHumanizedFieldName("description"), diff: value[1]}) + else if field == "blocked_note" + return templateChangeDiff({name: getHumanizedFieldName("blocked_note"), diff: value[1]}) else if field == "points" return templateChangePoints({points: value}) else if field == "attachments" return renderAttachmentEntry(value) + else if field in ["tags", "watchers"] + name = getHumanizedFieldName(field) + removed = _.difference(value[0], value[1]) + added = _.difference(value[1], value[0]) + return templateChangeList({name:name, removed:removed, added: added}) else if field == "assigned_to" name = getHumanizedFieldName(field) from = formatChange(value[0] or "Unassigned") diff --git a/app/partials/common/history/history-change-list.jade b/app/partials/common/history/history-change-list.jade new file mode 100644 index 00000000..f11c5fa0 --- /dev/null +++ b/app/partials/common/history/history-change-list.jade @@ -0,0 +1,17 @@ +.change-entry + .activity-changed + span <%- name %> + .activity-fromto + <% if (removed.length > 0) { %> + p + strong removed + br + span <%- removed %> + <% } %> + + <% if (added.length > 0) { %> + p + strong added + br + span <%- added %> + <% } %> From 2a2129bc995cef93ee48ba8e169dabd3ce2ab321 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 3 Feb 2015 13:31:25 +0100 Subject: [PATCH 032/207] fix #2162 - fix submit modules --- app/partials/admin/admin-project-modules.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/admin/admin-project-modules.jade b/app/partials/admin/admin-project-modules.jade index 82ee7cab..5e0d19e5 100644 --- a/app/partials/admin/admin-project-modules.jade +++ b/app/partials/admin/admin-project-modules.jade @@ -87,4 +87,4 @@ div.wrapper(tg-project-modules, ng-controller="ProjectProfileController as ctrl" option(value="") Select a videoconference system input(type="text", ng-model="project.videoconferences_salt", placeholder="If you want you can append a salt code to the name of the chat room") - button.button-green.submit-button(type="submit", title="Sign in") Sign in + button.button-green.submit-button(type="submit", title="Sign in") Sign in From dfc1002d0b55e4a88e8bae8ee0319d75dc44a5e8 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 3 Feb 2015 12:49:21 +0100 Subject: [PATCH 033/207] fix backlog sort with doomline --- app/coffee/modules/backlog/sortable.coffee | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/backlog/sortable.coffee b/app/coffee/modules/backlog/sortable.coffee index d11ac1c1..ac0cc1ac 100644 --- a/app/coffee/modules/backlog/sortable.coffee +++ b/app/coffee/modules/backlog/sortable.coffee @@ -45,6 +45,9 @@ BacklogSortableDirective = ($repo, $rs, $rootscope, $tgConfirm) -> # helper-in-wrong-place-when-scrolled-down-page link = ($scope, $el, $attrs) -> + getUsIndex = (us) => + return $(us).index(".backlog-table-body .row") + bindOnce $scope, "project", (project) -> # If the user has not enough permissions we don't enable the sortable if not (project.my_permissions.indexOf("modify_us") > -1) @@ -83,7 +86,7 @@ BacklogSortableDirective = ($repo, $rs, $rootscope, $tgConfirm) -> return itemUs = ui.item.scope().us - itemIndex = ui.item.index() + itemIndex = getUsIndex(ui.item) deleteElement(ui.item) @@ -99,7 +102,7 @@ BacklogSortableDirective = ($repo, $rs, $rootscope, $tgConfirm) -> return $(item).index() index = _.min _.map items, (item) -> - return $(item).index() + return getUsIndex(item) us = _.map items, (item) -> item = $(item) From a4b10210a7f6b5d6bcb0b275d45deb6e9252024e Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 3 Feb 2015 13:45:49 +0100 Subject: [PATCH 034/207] fix modules button save text --- app/partials/admin/admin-project-modules.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/admin/admin-project-modules.jade b/app/partials/admin/admin-project-modules.jade index 5e0d19e5..0df09adf 100644 --- a/app/partials/admin/admin-project-modules.jade +++ b/app/partials/admin/admin-project-modules.jade @@ -87,4 +87,4 @@ div.wrapper(tg-project-modules, ng-controller="ProjectProfileController as ctrl" option(value="") Select a videoconference system input(type="text", ng-model="project.videoconferences_salt", placeholder="If you want you can append a salt code to the name of the chat room") - button.button-green.submit-button(type="submit", title="Sign in") Sign in + button.button-green.submit-button(type="submit", title="Save") Save From bc064f8e50e3dd39fb83b03372272e822bb6080d Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Tue, 3 Feb 2015 15:08:12 +0100 Subject: [PATCH 035/207] Fixing arrows error on hide/show sprints in backlog --- app/coffee/modules/backlog/main.coffee | 34 +++++++++++++--------- app/coffee/modules/backlog/sprints.coffee | 14 +++++---- app/partials/includes/modules/sprints.jade | 2 +- 3 files changed, 30 insertions(+), 20 deletions(-) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index dfd8336f..8bb82faa 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -59,7 +59,6 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F @scope.sectionName = "Backlog" @showTags = false @activeFilters = false - @excludeClosedSprints = true @.initializeEventHandlers() @@ -111,7 +110,8 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F @scope.$on("sprint:us:moved", @.loadSprints) @scope.$on("sprint:us:moved", @.loadProjectStats) - @scope.$on("backlog:toggle-closed-sprints-visualization", @.toggleClosedSprintsVisualization) + @scope.$on("backlog:load-closed-sprints", @.loadClosedSprints) + @scope.$on("backlog:unload-closed-sprints", @.unloadClosedSprints) initializeSubscription: -> routingKey1 = "changes.project.#{@scope.projectId}.userstories" @@ -146,11 +146,23 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F return @rs.projects.tagsColors(@scope.projectId).then (tags_colors) => @scope.project.tags_colors = tags_colors - loadSprints: -> - params = {} - if @excludeClosedSprints - params["closed"] = false + unloadClosedSprints: -> + @scope.$apply => + @scope.closedSprints = [] + @rootscope.$broadcast("closed-sprints:reloaded", []) + loadClosedSprints: -> + params = {closed: true} + return @rs.sprints.list(@scope.projectId, params).then (sprints) => + # NOTE: Fix order of USs because the filter orderBy does not work propertly in partials files + for sprint in sprints + sprint.user_stories = _.sortBy(sprint.user_stories, "sprint_order") + @scope.closedSprints = sprints + @rootscope.$broadcast("closed-sprints:reloaded", sprints) + return sprints + + loadSprints: -> + params = {closed: false} return @rs.sprints.list(@scope.projectId, params).then (sprints) => # NOTE: Fix order of USs because the filter orderBy does not work propertly in partials files for sprint in sprints @@ -158,10 +170,8 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F @scope.sprints = sprints @scope.openSprints = _.filter(sprints, (sprint) => not sprint.closed).reverse() - @scope.closedSprints = _.filter(sprints, (sprint) => sprint.closed) - if not @excludeClosedSprints - @scope.totalClosedMilestones = @scope.closedSprints.length - + @scope.closedSprints = [] + @scope.sprintsCounter = sprints.length @scope.sprintsById = groupBy(sprints, (x) -> x.id) @rootscope.$broadcast("sprints:loaded", sprints) @@ -232,10 +242,6 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F return promise.then(=> @.loadBacklog()) - toggleClosedSprintsVisualization: -> - @excludeClosedSprints = not @excludeClosedSprints - @.loadSprints() - filterVisibleUserstories: -> @scope.visibleUserstories = [] diff --git a/app/coffee/modules/backlog/sprints.coffee b/app/coffee/modules/backlog/sprints.coffee index 7a30ba9c..2ea737a4 100644 --- a/app/coffee/modules/backlog/sprints.coffee +++ b/app/coffee/modules/backlog/sprints.coffee @@ -135,23 +135,27 @@ module.directive("tgBacklogSprintHeader", ["$tgNavUrls", "$tgTemplate", BacklogS ############################################################################# ToggleExcludeClosedSprintsVisualization = ($rootscope, $loading) -> - excludeClosedSprints = false + excludeClosedSprints = true link = ($scope, $el, $attrs) -> # Event Handlers $el.on "click", "", (event) -> + excludeClosedSprints = not excludeClosedSprints + $loading.start($el.parent().siblings('.loading-spinner')) - $rootscope.$broadcast("backlog:toggle-closed-sprints-visualization") + if excludeClosedSprints + $rootscope.$broadcast("backlog:unload-closed-sprints") + else + $rootscope.$broadcast("backlog:load-closed-sprints") $scope.$on "$destroy", -> $el.off() - $scope.$on "sprints:loaded", (ctx, sprints) => - closedSprints = _.filter(sprints, (sprint) -> sprint.closed) + $scope.$on "closed-sprints:reloaded", (ctx, sprints) => $loading.finish($el.parent().siblings('.loading-spinner')) #TODO: i18n - if closedSprints.length > 0 + if sprints.length > 0 $el.text("Hide closed sprints") else $el.text("Show closed sprints") diff --git a/app/partials/includes/modules/sprints.jade b/app/partials/includes/modules/sprints.jade index 3e95cf9d..d3100acf 100644 --- a/app/partials/includes/modules/sprints.jade +++ b/app/partials/includes/modules/sprints.jade @@ -17,7 +17,7 @@ section.sprints a.filter-closed-sprints(href="", ng-show="totalClosedMilestones") span.icon.icon-archive - span(tg-backlog-toggle-closed-sprints-visualization="ctrl.excludeClosedSprints") Show closed sprints + span(tg-backlog-toggle-closed-sprints-visualization) Show closed sprints div.loading-spinner div.sprint.sprint-closed(ng-repeat="sprint in closedSprints track by sprint.id" tg-backlog-sprint="sprint", tg-sprint-sortable) From c11078d6c78b371b2a52226b44a17f16c494d7f7 Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Wed, 4 Feb 2015 07:56:19 +0100 Subject: [PATCH 036/207] Add arrow-height parameter to popover mixin --- app/styles/dependencies/mixins.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/styles/dependencies/mixins.scss b/app/styles/dependencies/mixins.scss index ad1189b7..19730da8 100644 --- a/app/styles/dependencies/mixins.scss +++ b/app/styles/dependencies/mixins.scss @@ -31,7 +31,7 @@ background: rgba($red, $green, $blue, $opacity); } -@mixin popover($width, $top: '', $left: '', $bottom: '', $right: '', $arrow-width: 0, $arrow-top: '', $arrow-left: '', $arrow-bottom: '') { +@mixin popover($width, $top: '', $left: '', $bottom: '', $right: '', $arrow-width: 0, $arrow-top: '', $arrow-left: '', $arrow-bottom: '', $arrow-height: 15px) { @extend %text; background: $blackish; bottom: #{$bottom}; @@ -67,7 +67,7 @@ background: $blackish; bottom: #{$arrow-bottom}; content: ''; - height: 15px; + height: #{$arrow-height}; left: #{$arrow-left}; position: absolute; top: #{$arrow-top}; From 1eb1a393d5ad20e147be49b465244cd161fc65f9 Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Wed, 4 Feb 2015 08:00:18 +0100 Subject: [PATCH 037/207] Fix arrow height in points-per-role --- app/styles/layout/us-detail.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index bbc26169..1ff3c9f1 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -305,7 +305,7 @@ text-align: center; } .popover { - @include popover(200px, $top: 105%, $left: 35%, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 10px); + @include popover(200px, $top: 105%, $left: 35%, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 10px, $arrow-height: 10px); li { display: inline-block; width: 23%; @@ -320,7 +320,7 @@ } } &.fix { - @include popover(200px, $top: 105%, $left: -160px, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 90%); + @include popover(200px, $top: 105%, $left: -160px, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 90%, $arrow-height: 10px); } } } From ea4d5d887f13f79b2ed55254ac928c6e752de437 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Feb 2015 08:01:57 +0100 Subject: [PATCH 038/207] replace js height calculator by displayFlex --- app/coffee/modules/kanban/main.coffee | 30 ------------------- app/coffee/modules/taskboard/main.coffee | 24 --------------- .../includes/modules/kanban-table.jade | 2 +- app/partials/kanban/kanban.jade | 3 +- app/styles/layout/kanban.scss | 6 ++++ app/styles/layout/taskboard.scss | 8 +++++ .../modules/backlog/taskboard-table.scss | 3 ++ app/styles/modules/kanban/kanban-table.scss | 3 ++ app/styles/shame/shame.scss | 12 -------- 9 files changed, 22 insertions(+), 69 deletions(-) diff --git a/app/coffee/modules/kanban/main.coffee b/app/coffee/modules/kanban/main.coffee index d82a8065..65eac846 100644 --- a/app/coffee/modules/kanban/main.coffee +++ b/app/coffee/modules/kanban/main.coffee @@ -293,36 +293,6 @@ KanbanDirective = ($repo, $rootscope) -> module.directive("tgKanban", ["$tgRepo", "$rootScope", KanbanDirective]) - -############################################################################# -## Kanban Column Height Fixer Directive -############################################################################# - -KanbanColumnHeightFixerDirective = -> - mainPadding = 32 # px - scrollPadding = 0 # px - - renderSize = ($el) -> - elementOffset = $el.parent().parent().offset().top - windowHeight = angular.element(window).height() - columnHeight = windowHeight - elementOffset - mainPadding - scrollPadding - $el.css("height", "#{columnHeight}px") - - link = ($scope, $el, $attrs) -> - timeout(500, -> renderSize($el)) - - $scope.$on "resize", -> - renderSize($el) - - $scope.$on "$destroy", -> - $el.off() - - return {link:link} - - -module.directive("tgKanbanColumnHeightFixer", KanbanColumnHeightFixerDirective) - - ############################################################################# ## Kanban Archived Status Column Header Control ############################################################################# diff --git a/app/coffee/modules/taskboard/main.coffee b/app/coffee/modules/taskboard/main.coffee index 00cef123..2bc15a7d 100644 --- a/app/coffee/modules/taskboard/main.coffee +++ b/app/coffee/modules/taskboard/main.coffee @@ -297,30 +297,6 @@ TaskboardTaskDirective = ($rootscope) -> module.directive("tgTaskboardTask", ["$rootScope", TaskboardTaskDirective]) -############################################################################# -## Taskboard Table Height Fixer Directive -############################################################################# - -TaskboardTableHeightFixerDirective = -> - mainPadding = 32 # px - - renderSize = ($el) -> - elementOffset = $el.offset().top - windowHeight = angular.element(window).height() - columnHeight = windowHeight - elementOffset - mainPadding - $el.css("height", "#{columnHeight}px") - - link = ($scope, $el, $attrs) -> - timeout(500, -> renderSize($el)) - - $scope.$on "resize", -> - renderSize($el) - - return {link:link} - - -module.directive("tgTaskboardTableHeightFixer", TaskboardTableHeightFixerDirective) - ############################################################################# ## Taskboard Squish Column Directive ############################################################################# diff --git a/app/partials/includes/modules/kanban-table.jade b/app/partials/includes/modules/kanban-table.jade index a3507eac..25f32625 100644 --- a/app/partials/includes/modules/kanban-table.jade +++ b/app/partials/includes/modules/kanban-table.jade @@ -32,7 +32,7 @@ div.kanban-table(tg-kanban-squish-column) tg-kanban-archived-status-header="s") div.kanban-table-body - div.kanban-table-inner(tg-kanban-row-width-fixer) + div.kanban-table-inner div.kanban-uses-box.task-column(ng-class='{vfold:folds[s.id]}', ng-repeat="s in usStatusList track by s.id", tg-kanban-sortable, diff --git a/app/partials/kanban/kanban.jade b/app/partials/kanban/kanban.jade index 3a010018..b8354946 100644 --- a/app/partials/kanban/kanban.jade +++ b/app/partials/kanban/kanban.jade @@ -1,8 +1,7 @@ div.wrapper(tg-kanban, ng-controller="KanbanController as ctrl" ng-init="section='kanban'") section.main.kanban - header - include ../includes/components/mainTitle + include ../includes/components/mainTitle //- div.kanban-settings //- // a.button.button-trans(href="", title="Filter") //- // span.icon.icon-filter diff --git a/app/styles/layout/kanban.scss b/app/styles/layout/kanban.scss index 41e161d9..8421f1bd 100644 --- a/app/styles/layout/kanban.scss +++ b/app/styles/layout/kanban.scss @@ -1,4 +1,10 @@ .kanban { + display: flex; + flex-direction: column; + max-height: 100vh; + header { + min-height: 70px; + } .kanban-settings { float: right; } diff --git a/app/styles/layout/taskboard.scss b/app/styles/layout/taskboard.scss index 40f80cf1..b415fc84 100644 --- a/app/styles/layout/taskboard.scss +++ b/app/styles/layout/taskboard.scss @@ -1,4 +1,12 @@ .taskboard { + display: flex; + flex-direction: column; + max-height: 100vh; + h1, + graphics-container, + .summary { + flex-shrink: 0; + } .graphics-container { @include slide(300px, hidden); } diff --git a/app/styles/modules/backlog/taskboard-table.scss b/app/styles/modules/backlog/taskboard-table.scss index 3a75204f..23900067 100644 --- a/app/styles/modules/backlog/taskboard-table.scss +++ b/app/styles/modules/backlog/taskboard-table.scss @@ -45,12 +45,15 @@ $column-margin: 0 10px 0 0; } .taskboard-table { + display: flex; + flex-direction: column; overflow: hidden; width: 100%; } .taskboard-table-header { margin-bottom: .5rem; + min-height: 40px; position: relative; width: 100%; .taskboard-table-inner { diff --git a/app/styles/modules/kanban/kanban-table.scss b/app/styles/modules/kanban/kanban-table.scss index d542a418..e5a3e588 100644 --- a/app/styles/modules/kanban/kanban-table.scss +++ b/app/styles/modules/kanban/kanban-table.scss @@ -7,6 +7,8 @@ $column-shrink: 0; $column-margin: 0 10px 0 0; .kanban-table { + display: flex; + flex-direction: column; overflow: hidden; width: 100%; .vfold { @@ -48,6 +50,7 @@ $column-margin: 0 10px 0 0; .kanban-table-header { margin-bottom: .5rem; position: relative; + min-height: 40px; width: 100%; .kanban-table-inner { display: flex; diff --git a/app/styles/shame/shame.scss b/app/styles/shame/shame.scss index 436b0a6c..43772411 100644 --- a/app/styles/shame/shame.scss +++ b/app/styles/shame/shame.scss @@ -1,17 +1,5 @@ // Shame SCSS decalrations to be refactorized -////TASKBOARD-TABLE.SCSS && TASKBOARD-TABLE.JADE//// - -//Taskboard table header brokes when added position relative and positionabsolute to its child -// No clearfix or known hack fixes it -// Could be because of flexbox? -// height of the table has been set manually, wich is ugly. -.taskboard-table-header, -.kanban-table-header { - height: 40px; -} - - _:-ms-fullscreen, :root .taskboard-table-body { .task-row { From c8952163f06108ead328755ee8eda87e90829569 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Wed, 4 Feb 2015 09:53:52 +0100 Subject: [PATCH 039/207] Update CHANGELOG --- CHANGELOG.md | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 62a7b842..8df2d197 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,15 @@ # Changelog # + +## 1.6.0 ??? (Unreleased) + +### Features +- ... + +### Misc +- Lots of small and not so small bugfixes. + + ## 1.5.0 Betula Pendula - FOSDEM 2015 (2015-01-29) ### Features From 6b06841e6448a7e92e1d789c91746bb2f9b36fff Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Feb 2015 12:00:30 +0100 Subject: [PATCH 040/207] upgrade npm dependencies --- gulpfile.coffee | 2 +- package.json | 52 ++++++++++++++++++++++++------------------------- 2 files changed, 27 insertions(+), 27 deletions(-) diff --git a/gulpfile.coffee b/gulpfile.coffee index 34be192d..8f5f7b3d 100644 --- a/gulpfile.coffee +++ b/gulpfile.coffee @@ -223,7 +223,7 @@ gulp.task "app-loader", -> gulp.task "locales", -> gulp.src("app/locales/en/app.json") - .pipe(wrap("angular.module('taigaBase').value('localesEn', <%= contents %>);")) + .pipe(wrap("angular.module('taigaBase').value('localesEn', <%= contents %>);", {}, {parse: false})) .pipe(rename("locales.en.js")) .pipe(gulp.dest(paths.tmp)) diff --git a/package.json b/package.json index 275d5241..8b00ec7e 100644 --- a/package.json +++ b/package.json @@ -17,45 +17,45 @@ } ], "devDependencies": { - "coffee-script": "^1.8.0", + "coffee-script": "^1.9.0", "del": "^1.1.1", - "express": "^4.9.5", + "express": "^4.11.2", "gulp": "^3.8.10", "gulp-angular-templatecache": "^1.5.0", - "gulp-autoprefixer": "^2.0.0", - "gulp-cached": "0.0.3", - "gulp-changed": "^0.4.0", - "gulp-clean": "^0.2.4", - "gulp-coffee": "^2.2.0", + "gulp-autoprefixer": "^2.1.0", + "gulp-cached": "1.0.2", + "gulp-changed": "^1.1.1", + "gulp-clean": "^0.3.1", + "gulp-coffee": "^2.3.1", "gulp-coffeelint": "~0.4.0", - "gulp-concat": "^2.1.7", + "gulp-concat": "^2.4.3", "gulp-csslint": "^0.1.5", "gulp-flatten": "0.0.4", "gulp-if": "^1.2.5", - "gulp-imagemin": "^2.0.0", + "gulp-imagemin": "^2.1.0", "gulp-insert": "^0.4.0", "gulp-intermediate": "^3.0.1", - "gulp-jade": "^0.5.0", - "gulp-jade-inheritance": "0.0.4", - "gulp-minify-css": "^0.3.1", - "gulp-minify-html": "^0.1.3", - "gulp-newer": "^0.3.0", - "gulp-notify": "^1.2.5", - "gulp-plumber": "^0.6.2", + "gulp-jade": "^0.11.0", + "gulp-jade-inheritance": "0.5.0", + "gulp-minify-css": "^0.4.4", + "gulp-minify-html": "^0.1.8", + "gulp-newer": "^0.5.0", + "gulp-notify": "^2.2.0", + "gulp-plumber": "^0.6.6", "gulp-rename": "^1.2.0", "gulp-ruby-sass": "^0.7.1", - "gulp-scss-lint": "0.1.4", - "gulp-sourcemaps": "^1.2.4", + "gulp-scss-lint": "0.1.6", + "gulp-sourcemaps": "^1.3.0", "gulp-styledocco": "0.0.1", - "gulp-template": "^0.1.1", - "gulp-uglify": "~0.2.0", - "gulp-util": "~2.2.14", - "gulp-watch": "^0.5.4", - "gulp-wrap": "^0.3.0", + "gulp-template": "^2.1.0", + "gulp-uglify": "~1.1.0", + "gulp-util": "~3.0.3", + "gulp-watch": "^4.1.0", + "gulp-wrap": "^0.10.1", "lazypipe": "^0.2.2", - "readable-stream": "~1.0.31", - "run-sequence": "^1.0.1", - "through2": "~0.6.1", + "readable-stream": "~1.0.33", + "run-sequence": "^1.0.2", + "through2": "~0.6.3", "gulp-replace": "^0.5.2" } } From 67e54362c79977825ba8769f677c611bd05aa276 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Feb 2015 14:43:27 +0100 Subject: [PATCH 041/207] fix closed sprints click zone --- app/coffee/modules/backlog/sprints.coffee | 11 +++++++---- app/partials/includes/modules/sprints.jade | 4 ++-- app/styles/modules/backlog/sprints.scss | 9 +++++---- 3 files changed, 14 insertions(+), 10 deletions(-) diff --git a/app/coffee/modules/backlog/sprints.coffee b/app/coffee/modules/backlog/sprints.coffee index 2ea737a4..4c32e641 100644 --- a/app/coffee/modules/backlog/sprints.coffee +++ b/app/coffee/modules/backlog/sprints.coffee @@ -139,7 +139,8 @@ ToggleExcludeClosedSprintsVisualization = ($rootscope, $loading) -> link = ($scope, $el, $attrs) -> # Event Handlers - $el.on "click", "", (event) -> + $el.on "click", (event) -> + event.preventDefault() excludeClosedSprints = not excludeClosedSprints $loading.start($el.parent().siblings('.loading-spinner')) @@ -152,13 +153,15 @@ ToggleExcludeClosedSprintsVisualization = ($rootscope, $loading) -> $el.off() $scope.$on "closed-sprints:reloaded", (ctx, sprints) => - $loading.finish($el.parent().siblings('.loading-spinner')) + $loading.finish($el.siblings('.loading-spinner')) #TODO: i18n if sprints.length > 0 - $el.text("Hide closed sprints") + text = "Hide closed sprints" else - $el.text("Show closed sprints") + text = "Show closed sprints" + + $el.find(".text").text(text) return {link: link} diff --git a/app/partials/includes/modules/sprints.jade b/app/partials/includes/modules/sprints.jade index d3100acf..836b3b34 100644 --- a/app/partials/includes/modules/sprints.jade +++ b/app/partials/includes/modules/sprints.jade @@ -15,9 +15,9 @@ section.sprints div.sprint.sprint-open(ng-repeat="sprint in openSprints track by sprint.id", tg-backlog-sprint="sprint", tg-sprint-sortable) include sprint - a.filter-closed-sprints(href="", ng-show="totalClosedMilestones") + a.filter-closed-sprints(tg-backlog-toggle-closed-sprints-visualization, href="", ng-show="totalClosedMilestones") span.icon.icon-archive - span(tg-backlog-toggle-closed-sprints-visualization) Show closed sprints + span.text Show closed sprints div.loading-spinner div.sprint.sprint-closed(ng-repeat="sprint in closedSprints track by sprint.id" tg-backlog-sprint="sprint", tg-sprint-sortable) diff --git a/app/styles/modules/backlog/sprints.scss b/app/styles/modules/backlog/sprints.scss index 05545d50..759b6a1d 100644 --- a/app/styles/modules/backlog/sprints.scss +++ b/app/styles/modules/backlog/sprints.scss @@ -17,12 +17,13 @@ } .filter-closed-sprints { @extend %small; - display: block; + align-content: center; + display: flex; + justify-content: center; padding-bottom: 1rem; - text-align: center; - .icon-kanban { + vertical-align: middle; + .icon-archive { margin-right: .3rem; - vertical-align: middle; } } .loading-spinner { From b35ddb38471f7f9c7105945f9875e7c332ed7131 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 5 Feb 2015 08:16:20 +0100 Subject: [PATCH 042/207] fix #2179 - loading always should be hidden --- app/coffee/modules/backlog/sprints.coffee | 9 +++++++-- app/coffee/modules/user-settings/main.coffee | 8 ++++---- app/partials/includes/modules/sprints.jade | 1 - app/partials/user/user-profile.jade | 2 +- app/styles/modules/backlog/sprints.scss | 4 +++- app/styles/modules/user-settings/user-profile.scss | 2 +- 6 files changed, 16 insertions(+), 10 deletions(-) diff --git a/app/coffee/modules/backlog/sprints.coffee b/app/coffee/modules/backlog/sprints.coffee index 4c32e641..21e720ee 100644 --- a/app/coffee/modules/backlog/sprints.coffee +++ b/app/coffee/modules/backlog/sprints.coffee @@ -138,12 +138,17 @@ ToggleExcludeClosedSprintsVisualization = ($rootscope, $loading) -> excludeClosedSprints = true link = ($scope, $el, $attrs) -> + # insert loading wrapper + loadingElm = $("
") + $el.after(loadingElm) + # Event Handlers $el.on "click", (event) -> event.preventDefault() excludeClosedSprints = not excludeClosedSprints - $loading.start($el.parent().siblings('.loading-spinner')) + $loading.start(loadingElm) + if excludeClosedSprints $rootscope.$broadcast("backlog:unload-closed-sprints") else @@ -153,7 +158,7 @@ ToggleExcludeClosedSprintsVisualization = ($rootscope, $loading) -> $el.off() $scope.$on "closed-sprints:reloaded", (ctx, sprints) => - $loading.finish($el.siblings('.loading-spinner')) + $loading.finish(loadingElm) #TODO: i18n if sprints.length > 0 diff --git a/app/coffee/modules/user-settings/main.coffee b/app/coffee/modules/user-settings/main.coffee index 8a10d312..3b221008 100644 --- a/app/coffee/modules/user-settings/main.coffee +++ b/app/coffee/modules/user-settings/main.coffee @@ -129,12 +129,12 @@ UserAvatarDirective = ($auth, $model, $rs, $confirm) -> $auth.setUser(user) $scope.user = user - $el.find('.overlay').hide() + $el.find('.overlay').addClass('hidden') $confirm.notify('success') onError = (response) -> showSizeInfo() if response.status == 413 - $el.find('.overlay').hide() + $el.find('.overlay').addClass('hidden') $confirm.notify('error', response.data._error_message) # Change photo @@ -143,12 +143,12 @@ UserAvatarDirective = ($auth, $model, $rs, $confirm) -> $el.on "change", "#avatar-field", (event) -> if $scope.avatarAttachment - $el.find('.overlay').css('display', 'flex') + $el.find('.overlay').removeClass('hidden') $rs.userSettings.changeAvatar($scope.avatarAttachment).then(onSuccess, onError) # Use gravatar photo $el.on "click", "a.use-gravatar", (event) -> - $el.find('.overlay').show() + $el.find('.overlay').removeClass('hidden') $rs.userSettings.removeAvatar().then(onSuccess, onError) $scope.$on "$destroy", -> diff --git a/app/partials/includes/modules/sprints.jade b/app/partials/includes/modules/sprints.jade index 836b3b34..f5b147bc 100644 --- a/app/partials/includes/modules/sprints.jade +++ b/app/partials/includes/modules/sprints.jade @@ -18,7 +18,6 @@ section.sprints a.filter-closed-sprints(tg-backlog-toggle-closed-sprints-visualization, href="", ng-show="totalClosedMilestones") span.icon.icon-archive span.text Show closed sprints - div.loading-spinner div.sprint.sprint-closed(ng-repeat="sprint in closedSprints track by sprint.id" tg-backlog-sprint="sprint", tg-sprint-sortable) include sprint diff --git a/app/partials/user/user-profile.jade b/app/partials/user/user-profile.jade index 9819c23e..2d6989e6 100644 --- a/app/partials/user/user-profile.jade +++ b/app/partials/user/user-profile.jade @@ -14,7 +14,7 @@ div.wrapper(tg-user-profile, ng-controller="UserSettingsController as ctrl", fieldset(tg-user-avatar) .image-container img.avatar(ng-src="{{user.big_photo}}" alt="avatar") - .overlay + .overlay.hidden img.loading-spinner(src="/svg/spinner-circle.svg", alt="loading...") input(type="file", id="avatar-field", class="hidden", tg-avatar-model="avatarAttachment") diff --git a/app/styles/modules/backlog/sprints.scss b/app/styles/modules/backlog/sprints.scss index 759b6a1d..cecbd7f0 100644 --- a/app/styles/modules/backlog/sprints.scss +++ b/app/styles/modules/backlog/sprints.scss @@ -26,8 +26,10 @@ margin-right: .3rem; } } + .loading { + text-align: center; + } .loading-spinner { - @extend %loading-spinner; border: 0; flex-grow: 0; margin-bottom: 1rem; diff --git a/app/styles/modules/user-settings/user-profile.scss b/app/styles/modules/user-settings/user-profile.scss index 62f39807..2deea46a 100644 --- a/app/styles/modules/user-settings/user-profile.scss +++ b/app/styles/modules/user-settings/user-profile.scss @@ -21,7 +21,7 @@ align-items: center; background: rgba($blackish, .8); bottom: 0; - display: none; + display: flex; justify-content: center; left: 0; position: absolute; From c107d143d9bc88436ec140eb297b9c4fdb7c683f Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 5 Feb 2015 08:49:06 +0100 Subject: [PATCH 043/207] add plugins jade templates in the templateCache --- gulpfile.coffee | 1 + 1 file changed, 1 insertion(+) diff --git a/gulpfile.coffee b/gulpfile.coffee index 34be192d..645f18ac 100644 --- a/gulpfile.coffee +++ b/gulpfile.coffee @@ -44,6 +44,7 @@ paths.jade = "#{paths.app}/**/*.jade" paths.htmlPartials = [ "#{paths.tmp}/partials/**/*.html", + "#{paths.tmp}/plugins/**/*.html", "!#{paths.tmp}/partials/{includes,includes/**}" ] From aa2219608d7350b8f117c8675cd31bb5a5c7cc91 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 6 Feb 2015 08:12:19 +0100 Subject: [PATCH 044/207] remove duplicated roles templates --- app/coffee/modules/backlog/main.coffee | 6 +++--- app/coffee/modules/common/estimation.coffee | 5 +++-- app/partials/backlog/us-points-popover.jade | 11 ----------- .../lb-us-estimation-points-per-role.jade | 9 --------- .../common/estimation/lb-us-estimation-points.jade | 13 ------------- .../estimation}/us-points-roles-popover.jade | 0 6 files changed, 6 insertions(+), 38 deletions(-) delete mode 100644 app/partials/backlog/us-points-popover.jade delete mode 100644 app/partials/common/estimation/lb-us-estimation-points-per-role.jade delete mode 100644 app/partials/common/estimation/lb-us-estimation-points.jade rename app/partials/{backlog => common/estimation}/us-points-roles-popover.jade (100%) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index 8bb82faa..c76c736f 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -747,8 +747,8 @@ module.directive("tgUsRolePointsSelector", ["$rootScope", "$tgTemplate", UsRoleP UsPointsDirective = ($repo, $tgTemplate) -> - rolesTemplate = $tgTemplate.get("backlog/us-points-roles-popover.html", true) - pointsTemplate = $tgTemplate.get("backlog/us-points-popover.html", true) + rolesTemplate = $tgTemplate.get("common/estimation/us-points-roles-popover.html", true) + pointsTemplate = $tgTemplate.get("common/estimation/us-estimation-points.html", true) link = ($scope, $el, $attrs) -> $ctrl = $el.controller() @@ -787,7 +787,7 @@ UsPointsDirective = ($repo, $tgTemplate) -> point.selected = if us.points[roleId] == point.id then false else true return point - html = pointsTemplate({"points": points}) + html = pointsTemplate({"points": points, "roleId": roleId}) # Remove any prevous state $el.find(".popover").popover().close() diff --git a/app/coffee/modules/common/estimation.coffee b/app/coffee/modules/common/estimation.coffee index 6965bd24..23bdec36 100644 --- a/app/coffee/modules/common/estimation.coffee +++ b/app/coffee/modules/common/estimation.coffee @@ -37,8 +37,8 @@ LbUsEstimationDirective = ($rootScope, $repo, $confirm, $template) -> # - Us object (ng-model) # - scope.project object - mainTemplate = $template.get("common/estimation/lb-us-estimation-points-per-role.html", true) - pointsTemplate = $template.get("common/estimation/lb-us-estimation-points.html", true) + mainTemplate = $template.get("common/estimation/us-estimation-points-per-role.html", true) + pointsTemplate = $template.get("common/estimation/us-estimation-points.html", true) link = ($scope, $el, $attrs, $model) -> render = (points) -> @@ -56,6 +56,7 @@ LbUsEstimationDirective = ($rootScope, $repo, $confirm, $template) -> ctx = { totalPoints: totalPoints roles: roles + editable: true } html = mainTemplate(ctx) $el.html(html) diff --git a/app/partials/backlog/us-points-popover.jade b/app/partials/backlog/us-points-popover.jade deleted file mode 100644 index 0e39c5f3..00000000 --- a/app/partials/backlog/us-points-popover.jade +++ /dev/null @@ -1,11 +0,0 @@ -ul.popover.pop-points-open - <% _.each(points, function(point) { %> - li - <% if (point.selected) { %> - a.point(href="", title!="<%- point.name %>", data-point-id!="<%- point.id %>") - | <%- point.name %> - <% } else { %> - a.point.active(href="", title!="<%- point.name %>", data-point-id!="<%- point.id %>") - | <%- point.name %> - <% } %> - <% }); %> diff --git a/app/partials/common/estimation/lb-us-estimation-points-per-role.jade b/app/partials/common/estimation/lb-us-estimation-points-per-role.jade deleted file mode 100644 index e49e6628..00000000 --- a/app/partials/common/estimation/lb-us-estimation-points-per-role.jade +++ /dev/null @@ -1,9 +0,0 @@ -ul.points-per-role - li.total - span.points <%- totalPoints %> - span.role total - <% _.each(roles, function(role) { %> - li.total.clickable(data-role-id!="<%- role.id %>") - span.points <%- role.points %> - span.role <%- role.name %> - <% }); %> diff --git a/app/partials/common/estimation/lb-us-estimation-points.jade b/app/partials/common/estimation/lb-us-estimation-points.jade deleted file mode 100644 index 04fbceaf..00000000 --- a/app/partials/common/estimation/lb-us-estimation-points.jade +++ /dev/null @@ -1,13 +0,0 @@ -ul.popover.pop-points-open - <% _.each(points, function(point) { %> - li - <% if (point.selected) { %> - a(href="", class="point", title!="<%- point.name %>", - data-point-id!="<%- point.id %>", data-role-id!="<%- roleId %>") - | <%- point.name %> - <% } else { %> - a(href="", class="point active", title!="<%- point.name %>", - data-point-id!="<%- point.id %>" data-role-id!="<%- roleId %>") - | <%- point.name %> - <% } %> - <% }); %> diff --git a/app/partials/backlog/us-points-roles-popover.jade b/app/partials/common/estimation/us-points-roles-popover.jade similarity index 100% rename from app/partials/backlog/us-points-roles-popover.jade rename to app/partials/common/estimation/us-points-roles-popover.jade From e5687d217201d050a14913cc51b8a9014d6ddfd1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 6 Feb 2015 09:09:32 +0100 Subject: [PATCH 045/207] Fix wrong class --- app/styles/layout/taskboard.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/layout/taskboard.scss b/app/styles/layout/taskboard.scss index b415fc84..71ee04c2 100644 --- a/app/styles/layout/taskboard.scss +++ b/app/styles/layout/taskboard.scss @@ -3,7 +3,7 @@ flex-direction: column; max-height: 100vh; h1, - graphics-container, + .graphics-container, .summary { flex-shrink: 0; } From 8a21dbc74d52586443cede89f31b4f6f3ef403e6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 6 Feb 2015 09:36:38 +0100 Subject: [PATCH 046/207] Add Style Guide to Changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8df2d197..dc988152 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ - ... ### Misc +- Added Taiga Style Guide to enhance open source design. - Lots of small and not so small bugfixes. From ee4ffe112a26e233cf8e979688042db13caf2e3d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 6 Feb 2015 09:38:15 +0100 Subject: [PATCH 047/207] Add support pages reference --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dc988152..8e30bff9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,7 +7,7 @@ - ... ### Misc -- Added Taiga Style Guide to enhance open source design. +- Added Taiga Style Guide in support Pages to enhance open source design. - Lots of small and not so small bugfixes. From bb631ec5bcdcbd9701c32602c7be44797661d794 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 6 Feb 2015 09:39:40 +0100 Subject: [PATCH 048/207] Fix console linter --- app/styles/modules/kanban/kanban-table.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/modules/kanban/kanban-table.scss b/app/styles/modules/kanban/kanban-table.scss index e5a3e588..8d5e75d9 100644 --- a/app/styles/modules/kanban/kanban-table.scss +++ b/app/styles/modules/kanban/kanban-table.scss @@ -49,8 +49,8 @@ $column-margin: 0 10px 0 0; .kanban-table-header { margin-bottom: .5rem; - position: relative; min-height: 40px; + position: relative; width: 100%; .kanban-table-inner { display: flex; From 89d883fbad37c3aba1abb998ef1242305f82780b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Fri, 6 Feb 2015 10:10:28 +0100 Subject: [PATCH 049/207] Update AUTHORS.rst --- AUTHORS.rst | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/AUTHORS.rst b/AUTHORS.rst index 1afd86b6..c1066e92 100644 --- a/AUTHORS.rst +++ b/AUTHORS.rst @@ -7,14 +7,22 @@ The PRIMARY AUTHORS are: - Alejandro Alonso - Anler Hernández - Juan Francisco Alcántara +- Esther Moreno Riesco -Special thanks to Kaleidos Open Source S.L. for provide time for taiga +Special thanks to Kaleidos Open Source S.L. for provide time for Taiga development. And here is an inevitably incomplete list of MUCH-APPRECIATED CONTRIBUTORS -- people who have submitted patches, reported bugs, added translations, helped -answer newbie questions, and generally made taiga that much better: +answer newbie questions, and generally made Taiga that much better: - Pilar Esteban - Guilhem Got - ... +- Ramiro Sánchez +- Miguel de la Cruz +- Andrea Stagi +- Jordan Rinke +- Wil Wade +- Daniel Koch +- Florian Bezagu +- Ryan Swanstrom From b0ccc71dbcb8651ecd2e1cbaf654a717c9ea884d Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Sun, 8 Feb 2015 01:12:29 +0100 Subject: [PATCH 050/207] Fix archive view status on userstory editing --- app/coffee/modules/kanban/main.coffee | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/kanban/main.coffee b/app/coffee/modules/kanban/main.coffee index 65eac846..196ff031 100644 --- a/app/coffee/modules/kanban/main.coffee +++ b/app/coffee/modules/kanban/main.coffee @@ -138,13 +138,20 @@ class KanbanController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fi @scope.userstories = userstories usByStatus = _.groupBy(userstories, "status") + us_archived = [] for status in @scope.usStatusList if not usByStatus[status.id]? usByStatus[status.id] = [] + if @scope.usByStatus? + for us in @scope.usByStatus[status.id] + if us.status != status.id + us_archived.push(us) # Must preserve the archived columns if loaded - if status.is_archived and @scope.usByStatus? - usByStatus[status.id] = @scope.usByStatus[status.id] + if status.is_archived and @scope.usByStatus? and @scope.usByStatus[status.id].length != 0 + for us in @scope.usByStatus[status.id].concat(us_archived) + if us.status == status.id + usByStatus[status.id].push(us) usByStatus[status.id] = _.sortBy(usByStatus[status.id], "kanban_order") From 24dc2273e4d0484f02ecaf2cf022b0e686b05c15 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 9 Feb 2015 08:12:21 +0100 Subject: [PATCH 051/207] Fix font size, color and form contrast --- app/partials/includes/modules/backlog-filters.jade | 2 +- app/partials/includes/modules/filters.jade | 2 +- app/partials/includes/modules/issues-filters.jade | 2 +- app/styles/layout/forms.scss | 5 ++--- app/styles/modules/common/attachments.scss | 2 +- app/styles/modules/common/lightbox.scss | 1 + app/styles/modules/wiki/wiki-nav.scss | 4 +++- 7 files changed, 10 insertions(+), 8 deletions(-) diff --git a/app/partials/includes/modules/backlog-filters.jade b/app/partials/includes/modules/backlog-filters.jade index 5ddd61a1..4008631b 100644 --- a/app/partials/includes/modules/backlog-filters.jade +++ b/app/partials/includes/modules/backlog-filters.jade @@ -5,7 +5,7 @@ section.filters form fieldset - input(type="text", placeholder="Search by subject or reference...", ng-model="filtersQ") + input(type="text", placeholder="Subject or reference", ng-model="filtersQ") a.icon.icon-search(href="", title="search") div.filters-step-cat diff --git a/app/partials/includes/modules/filters.jade b/app/partials/includes/modules/filters.jade index e55aff79..7f3bcde2 100644 --- a/app/partials/includes/modules/filters.jade +++ b/app/partials/includes/modules/filters.jade @@ -8,7 +8,7 @@ section.filters form fieldset - input(type="text", placeholder="Search by subject or reference...", ng-model="filtersQ") + input(type="text", placeholder="Subject or reference", ng-model="filtersQ") a.icon.icon-search(href="", title="search") h2 a.hidden(href="", title="cat-name") diff --git a/app/partials/includes/modules/issues-filters.jade b/app/partials/includes/modules/issues-filters.jade index 81873495..0de01d96 100644 --- a/app/partials/includes/modules/issues-filters.jade +++ b/app/partials/includes/modules/issues-filters.jade @@ -4,7 +4,7 @@ section.filters span.title filters form fieldset - input(type="text", placeholder="Search by subject or reference...", ng-model="filtersQ") + input(type="text", placeholder="Subject or reference", ng-model="filtersQ") a.icon.icon-search(href="", title="search") div.filters-step-cat div.filters-applied diff --git a/app/styles/layout/forms.scss b/app/styles/layout/forms.scss index 3d2b3895..8099fd98 100644 --- a/app/styles/layout/forms.scss +++ b/app/styles/layout/forms.scss @@ -19,15 +19,14 @@ input[type="date"], input[type="password"], select, textarea { - @extend %title; - background: $whitish; + background: $very-light-gray; border: 1px solid $gray-light; color: $grayer; margin: 0; padding: 8px; width: 100%; @include placeholder { - color: $gray-light; + color: darken($gray-light, 10%); } } diff --git a/app/styles/modules/common/attachments.scss b/app/styles/modules/common/attachments.scss index f5cfac80..374170ae 100644 --- a/app/styles/modules/common/attachments.scss +++ b/app/styles/modules/common/attachments.scss @@ -84,7 +84,7 @@ } } .editable-attachment-comment { - @extend %medium; + @extend %small; } .attachment-settings { flex-basis: 15%; diff --git a/app/styles/modules/common/lightbox.scss b/app/styles/modules/common/lightbox.scss index 44f3ee38..e2fa350f 100644 --- a/app/styles/modules/common/lightbox.scss +++ b/app/styles/modules/common/lightbox.scss @@ -212,6 +212,7 @@ max-width: 600px; } .last-sprint-name { + @extend %small; color: $gray; opacity: 1; position: absolute; diff --git a/app/styles/modules/wiki/wiki-nav.scss b/app/styles/modules/wiki/wiki-nav.scss index 08b7a76a..e09fd0f8 100644 --- a/app/styles/modules/wiki/wiki-nav.scss +++ b/app/styles/modules/wiki/wiki-nav.scss @@ -24,13 +24,15 @@ transition: opacity 1s linear; } input { + @extend %text; + @extend %medium; background: $grayer; color: $whitish; @include placeholder { color: $gray-light; } } - &.loading { + .loading { margin: 0; padding: 8px; text-align: center; From d1f189c25fc3b68b50f707bad3c7291761293716 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Mon, 9 Feb 2015 08:58:26 +0100 Subject: [PATCH 052/207] WIP --- app/coffee/modules/team/main.coffee | 6 +++--- app/partials/project/project-menu.jade | 2 ++ 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/team/main.coffee b/app/coffee/modules/team/main.coffee index 69830a2f..9bc9b57a 100644 --- a/app/coffee/modules/team/main.coffee +++ b/app/coffee/modules/team/main.coffee @@ -69,18 +69,18 @@ class TeamController extends mixOf(taiga.Controller, taiga.PageMixin) loadMembers: -> return @rs.memberships.list(@scope.projectId, {}, false).then (data) => currentUser = @auth.getUser() - if not currentUser.photo? + if currentUser? and not currentUser.photo? currentUser.photo = "/images/unnamed.png" @scope.currentUser = _.find data, (membership) => - return membership.user == currentUser.id + return currentUser? and membership.user == currentUser.id @scope.totals = {} _.forEach data, (membership) => @scope.totals[membership.user] = 0 @scope.memberships = _.filter data, (membership) => - if membership.user && membership.user != currentUser.id && membership.is_user_active + if membership.user && (not currentUser? or membership.user != currentUser.id) && membership.is_user_active return membership for membership in @scope.memberships diff --git a/app/partials/project/project-menu.jade b/app/partials/project/project-menu.jade index beb4a7f8..78a41e71 100644 --- a/app/partials/project/project-menu.jade +++ b/app/partials/project/project-menu.jade @@ -44,6 +44,7 @@ div(class="menu-container") span(class="icon icon-settings") span(class="item") Admin <% } %> + <% if (user) { %> div(class="user") div(class="user-settings") ul(class="popover") @@ -61,3 +62,4 @@ div(class="menu-container") a(href="" title="Logout" class="logout") Logout a(href="" title="User preferences" class="avatar" id="nav-user-settings") img(src!="<%- user.photo %>" alt!="<%- user.full_name_display %>") + <% } %> From d7c27aebd624509400cc8994551e7b6e1cbf9e76 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Mon, 9 Feb 2015 09:01:15 +0100 Subject: [PATCH 053/207] Showing remove wiki page link only when permissions are enough --- app/partials/wiki/wiki.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/wiki/wiki.jade b/app/partials/wiki/wiki.jade index 2566e557..aabca782 100644 --- a/app/partials/wiki/wiki.jade +++ b/app/partials/wiki/wiki.jade @@ -14,6 +14,6 @@ div.wrapper(ng-controller="WikiDetailController as ctrl", tg-attachments(ng-model="wiki", type="wiki_page", ng-if="wiki.id") - a.remove(href="", ng-click="ctrl.delete()", ng-if="wiki.id", title="Remove this wiki page") + a.remove(href="", ng-click="ctrl.delete()", ng-if="wiki.id", title="Remove this wiki page", tg-check-permission="delete_wiki_page") span.icon.icon-delete span Remove this wiki page From d68e2e25c8d13fac25b41f1725791df72c30ebd3 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Mon, 9 Feb 2015 09:09:52 +0100 Subject: [PATCH 054/207] Fixing bad commit --- app/coffee/modules/team/main.coffee | 6 +++--- app/partials/project/project-menu.jade | 2 -- 2 files changed, 3 insertions(+), 5 deletions(-) diff --git a/app/coffee/modules/team/main.coffee b/app/coffee/modules/team/main.coffee index 9bc9b57a..69830a2f 100644 --- a/app/coffee/modules/team/main.coffee +++ b/app/coffee/modules/team/main.coffee @@ -69,18 +69,18 @@ class TeamController extends mixOf(taiga.Controller, taiga.PageMixin) loadMembers: -> return @rs.memberships.list(@scope.projectId, {}, false).then (data) => currentUser = @auth.getUser() - if currentUser? and not currentUser.photo? + if not currentUser.photo? currentUser.photo = "/images/unnamed.png" @scope.currentUser = _.find data, (membership) => - return currentUser? and membership.user == currentUser.id + return membership.user == currentUser.id @scope.totals = {} _.forEach data, (membership) => @scope.totals[membership.user] = 0 @scope.memberships = _.filter data, (membership) => - if membership.user && (not currentUser? or membership.user != currentUser.id) && membership.is_user_active + if membership.user && membership.user != currentUser.id && membership.is_user_active return membership for membership in @scope.memberships diff --git a/app/partials/project/project-menu.jade b/app/partials/project/project-menu.jade index 78a41e71..beb4a7f8 100644 --- a/app/partials/project/project-menu.jade +++ b/app/partials/project/project-menu.jade @@ -44,7 +44,6 @@ div(class="menu-container") span(class="icon icon-settings") span(class="item") Admin <% } %> - <% if (user) { %> div(class="user") div(class="user-settings") ul(class="popover") @@ -62,4 +61,3 @@ div(class="menu-container") a(href="" title="Logout" class="logout") Logout a(href="" title="User preferences" class="avatar" id="nav-user-settings") img(src!="<%- user.photo %>" alt!="<%- user.full_name_display %>") - <% } %> From 7da3eec8e72798b51d3036fe06be017fbd03901e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 10 Feb 2015 12:24:25 +0100 Subject: [PATCH 055/207] Removed unnecesary colors --- app/styles/components/buttons.scss | 15 ++------------- app/styles/components/paginator.scss | 6 +++--- app/styles/components/select-color.scss | 2 +- app/styles/dependencies/colors.scss | 14 -------------- app/styles/layout/base.scss | 2 +- .../modules/admin/admin-membership-table.scss | 2 +- app/styles/modules/admin/admin-roles.scss | 2 +- app/styles/modules/admin/admin-submenu-roles.scss | 2 +- app/styles/modules/admin/admin-submenu.scss | 2 +- app/styles/modules/common/category-config.scss | 2 +- app/styles/modules/team/team-table.scss | 2 +- 11 files changed, 13 insertions(+), 38 deletions(-) diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index ba919eba..e340990c 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -41,7 +41,7 @@ button { .button-gray, a.button-gray { - background: $button-gray; + background: $gray; &:hover { background: $fresh-taiga; color: $white; @@ -55,7 +55,7 @@ a.button-blackish { background: $blackish; color: $whitish; &:hover { - background: $button-gray-hover; + background: $blackish; color: $white; } span { @@ -74,17 +74,6 @@ a.button-red { } } -a.button-orange { - background: $orange; - &:hover { - background: lighten($orange, 10%); - color: $white; - } - span { - color: $white; - } -} - a.button-block { background: $white; color: $red; diff --git a/app/styles/components/paginator.scss b/app/styles/components/paginator.scss index 7d4ec1e3..4d8f4ad8 100644 --- a/app/styles/components/paginator.scss +++ b/app/styles/components/paginator.scss @@ -17,7 +17,7 @@ } a { &:hover { - background: $button-gray-hover; + background: $blackish; color: $white; transition: all .3s linear; } @@ -39,7 +39,7 @@ .v-pagination-next, .v-pagination-previous { - background-color: $button-gray; + background-color: $gray; color: $whitish; display: block; padding: .1rem 0; @@ -47,7 +47,7 @@ visibility: hidden; width: 100%; &:hover { - background-color: $button-gray / 2; + background-color: $blackish; transition: background .3s linear; } } diff --git a/app/styles/components/select-color.scss b/app/styles/components/select-color.scss index d8206ea2..b2216cbb 100644 --- a/app/styles/components/select-color.scss +++ b/app/styles/components/select-color.scss @@ -26,7 +26,7 @@ input { @extend %medium; @extend %text; - background-color: $very-light-gray; + background-color: $whitish; width: 243px; @include placeholder { color: $gray; diff --git a/app/styles/dependencies/colors.scss b/app/styles/dependencies/colors.scss index 6b73babd..aeaffb2d 100755 --- a/app/styles/dependencies/colors.scss +++ b/app/styles/dependencies/colors.scss @@ -6,29 +6,15 @@ $grayer: #444; $gray: #555; $gray-light: #b8b8b8; $whitish: #f5f5f5; -$very-light-gray: #fcfcfc; $white: #fff; $green-taiga: #72a114; $fresh-taiga: #9dce0a; $dark-taiga: #879b89; -$dry-taiga: #70a87d; -$morning-taiga: #7ab987; -$dark-grayish-lime-green: #8b9e8d; - $red-light: #ff8282; $red: #f00; -$rgba-red: 240, 15, 0, .8; - -$orange: #d98a0b; - -$button-green: #699b05; -$button-green-hover: #9dce0a; -$button-gray: #585858; -$button-gray-hover: #879b89; - $postit: #fff8e4; $postit-hover: #f1e8cd; $postit-dark-hover: #cfc29b; diff --git a/app/styles/layout/base.scss b/app/styles/layout/base.scss index d192396f..7976e40e 100644 --- a/app/styles/layout/base.scss +++ b/app/styles/layout/base.scss @@ -113,7 +113,7 @@ body { } .menu-tertiary { - background-color: $dark-grayish-lime-green; + background-color: $dark-taiga; flex: 0 0 auto; min-height: 100vh; padding: 2em 1em; diff --git a/app/styles/modules/admin/admin-membership-table.scss b/app/styles/modules/admin/admin-membership-table.scss index 0b296195..820a3232 100644 --- a/app/styles/modules/admin/admin-membership-table.scss +++ b/app/styles/modules/admin/admin-membership-table.scss @@ -116,7 +116,7 @@ width: 500px; z-index: 999; + div { - background-color: $button-gray; + background-color: $gray; height: 25px; transition: all .2s linear; width: 50%; diff --git a/app/styles/modules/admin/admin-roles.scss b/app/styles/modules/admin/admin-roles.scss index 12814b17..58203d80 100644 --- a/app/styles/modules/admin/admin-roles.scss +++ b/app/styles/modules/admin/admin-roles.scss @@ -65,7 +65,7 @@ width: 500px; z-index: 999; + div { - background-color: $button-gray; + background-color: $gray; height: 25px; transition: all .2s linear; width: 50%; diff --git a/app/styles/modules/admin/admin-submenu-roles.scss b/app/styles/modules/admin/admin-submenu-roles.scss index d0b6b5bc..441df1ab 100644 --- a/app/styles/modules/admin/admin-submenu-roles.scss +++ b/app/styles/modules/admin/admin-submenu-roles.scss @@ -38,7 +38,7 @@ padding: .5rem 0; text-align: center; &:hover { - background-color: darken($button-gray-hover, 15%); + background-color: $blackish; } } } diff --git a/app/styles/modules/admin/admin-submenu.scss b/app/styles/modules/admin/admin-submenu.scss index a8524778..6865b220 100644 --- a/app/styles/modules/admin/admin-submenu.scss +++ b/app/styles/modules/admin/admin-submenu.scss @@ -34,7 +34,7 @@ padding: .5rem 0; text-align: center; &:hover { - background-color: darken($button-gray-hover, 15%); + background-color: $blackish; } } } diff --git a/app/styles/modules/common/category-config.scss b/app/styles/modules/common/category-config.scss index 63d4b125..7a9346d3 100644 --- a/app/styles/modules/common/category-config.scss +++ b/app/styles/modules/common/category-config.scss @@ -50,7 +50,7 @@ } .category-item { align-items: center; - border-bottom: 1px solid $very-light-gray; + border-bottom: 1px solid $whitish; display: flex; justify-content: space-between; padding: .5rem .5rem .5rem 2rem; diff --git a/app/styles/modules/team/team-table.scss b/app/styles/modules/team/team-table.scss index 50a9c6b1..5660a6ca 100644 --- a/app/styles/modules/team/team-table.scss +++ b/app/styles/modules/team/team-table.scss @@ -61,7 +61,7 @@ .hero { width: 100%; .row { - background: $very-light-gray; + background: $whitish; border-bottom: 0; margin: 1rem 0; } From 40eb3e11f1c139b4a97850ccc5fc2d41f1ac5218 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Feb 2015 13:22:05 +0100 Subject: [PATCH 056/207] improve gulp start performance --- gulpfile.coffee | 221 +++++++++++++++++++++++------------------------- package.json | 5 -- 2 files changed, 107 insertions(+), 119 deletions(-) diff --git a/gulpfile.coffee b/gulpfile.coffee index eab37542..c4ae3ea8 100644 --- a/gulpfile.coffee +++ b/gulpfile.coffee @@ -1,34 +1,30 @@ gulp = require("gulp") jade = require("gulp-jade") -gutil = require("gulp-util") coffee = require("gulp-coffee") concat = require("gulp-concat") uglify = require("gulp-uglify") plumber = require("gulp-plumber") wrap = require("gulp-wrap") rename = require("gulp-rename") -flatten = require('gulp-flatten') -gulpif = require('gulp-if') +flatten = require("gulp-flatten") +gulpif = require("gulp-if") replace = require("gulp-replace") - -minifyHTML = require("gulp-minify-html") sass = require("gulp-ruby-sass") csslint = require("gulp-csslint") minifyCSS = require("gulp-minify-css") -watch = require("gulp-watch") -notify = require("gulp-notify") scsslint = require("gulp-scss-lint") -newer = require("gulp-newer") cache = require("gulp-cached") -jadeInheritance = require('gulp-jade-inheritance') -sourcemaps = require('gulp-sourcemaps') +jadeInheritance = require("gulp-jade-inheritance") +sourcemaps = require("gulp-sourcemaps") insert = require("gulp-insert") -runSequence = require('run-sequence') -lazypipe = require('lazypipe') -del = require('del') -imagemin = require('gulp-imagemin') -autoprefixer = require('gulp-autoprefixer') -templateCache = require('gulp-angular-templatecache') +imagemin = require("gulp-imagemin") +autoprefixer = require("gulp-autoprefixer") +templateCache = require("gulp-angular-templatecache") +changed = require("gulp-changed") + +runSequence = require("run-sequence") +lazypipe = require("lazypipe") +del = require("del") mainSass = require("./main-sass").files @@ -36,84 +32,85 @@ paths = {} paths.app = "app/" paths.dist = "dist/" paths.tmp = "tmp/" -paths.tmpStyles = paths.tmp + "styles/" -paths.tmpStylesExtras = "#{paths.tmpStyles}/taiga-front-extras/**/*.css" paths.extras = "extras/" -paths.jade = "#{paths.app}/**/*.jade" - -paths.htmlPartials = [ - "#{paths.tmp}/partials/**/*.html", - "#{paths.tmp}/plugins/**/*.html", - "!#{paths.tmp}/partials/{includes,includes/**}" +paths.jade = [ + "#{paths.app}**/*.jade", + "!#{paths.app}partial/includes/**", ] -paths.images = paths.app + "images/**/*" -paths.svg = paths.app + "svg/**/*" -paths.css = paths.app + "styles/vendor/*.css" -paths.locales = paths.app + "locales/**/*.json" +paths.htmlPartials = [ + "#{paths.tmp}partials/**/*.html", + "#{paths.tmp}plugins/**/*.html" +] + +paths.images = "#{paths.app}images/**/*" +paths.svg = "#{paths.app}svg/**/*" +paths.css = "#{paths.app}styles/vendor/*.css" +paths.locales = "#{paths.app}locales/**/*.json" + paths.sass = [ - "#{paths.app}/styles/**/*.scss" - "#{paths.app}/plugins/**/*.scss" + "#{paths.app}**/*.scss" "!#{paths.app}/styles/bourbon/**/*.scss" "!#{paths.app}/styles/dependencies/**/*.scss" "!#{paths.app}/styles/extras/**/*.scss" ] -paths.coffee = [ - paths.app + "coffee/app.coffee", - paths.app + "coffee/*.coffee", - paths.app + "coffee/modules/controllerMixins.coffee", - paths.app + "coffee/modules/*.coffee", - paths.app + "coffee/modules/common/*.coffee", - paths.app + "coffee/modules/backlog/*.coffee", - paths.app + "coffee/modules/taskboard/*.coffee", - paths.app + "coffee/modules/kanban/*.coffee", - paths.app + "coffee/modules/issues/*.coffee", - paths.app + "coffee/modules/userstories/*.coffee", - paths.app + "coffee/modules/tasks/*.coffee", - paths.app + "coffee/modules/team/*.coffee", - paths.app + "coffee/modules/wiki/*.coffee", - paths.app + "coffee/modules/admin/*.coffee", - paths.app + "coffee/modules/projects/*.coffee", - paths.app + "coffee/modules/locales/*.coffee", - paths.app + "coffee/modules/base/*.coffee", - paths.app + "coffee/modules/resources/*.coffee", - paths.app + "coffee/modules/user-settings/*.coffee" - paths.app + "coffee/modules/integrations/*.coffee" - paths.app + "plugins/**/*.coffee" -] +paths.coffee = "#{paths.app}**/*.coffee" paths.js = [ - paths.app + "vendor/jquery/dist/jquery.js", - paths.app + "vendor/lodash/dist/lodash.js", - paths.app + "vendor/emoticons/lib/emoticons.js", - paths.app + "vendor/underscore.string/lib/underscore.string.js", - paths.app + "vendor/angular/angular.js", - paths.app + "vendor/angular-route/angular-route.js", - paths.app + "vendor/angular-sanitize/angular-sanitize.js", - paths.app + "vendor/angular-animate/angular-animate.js", - paths.app + "vendor/i18next/i18next.js", - paths.app + "vendor/moment/min/moment-with-langs.js", - paths.app + "vendor/checksley/checksley.js", - paths.app + "vendor/pikaday/pikaday.js", - paths.app + "vendor/jquery-flot/jquery.flot.js", - paths.app + "vendor/jquery-flot/jquery.flot.pie.js", - paths.app + "vendor/jquery-flot/jquery.flot.time.js", - paths.app + "vendor/flot-axislabels/jquery.flot.axislabels.js", - paths.app + "vendor/flot.tooltip/js/jquery.flot.tooltip.js", - paths.app + "vendor/jquery-textcomplete/jquery.textcomplete.js", - paths.app + "vendor/markitup-1x/markitup/jquery.markitup.js", - paths.app + "vendor/malihu-custom-scrollbar-plugin/jquery.mCustomScrollbar.concat.min.js", - paths.app + "vendor/raven-js/dist/raven.js", - paths.app + "vendor/l.js/l.js", - paths.app + "js/jquery.ui.git-custom.js", - paths.app + "js/jquery-ui.drag-multiple-custom.js", - paths.app + "js/sha1-custom.js", - paths.app + "plugins/**/*.js" + "#{paths.tmp}coffee/app.js", + "#{paths.tmp}coffee/*.js", + "#{paths.tmp}coffee/modules/controllerMixins.js", + "#{paths.tmp}coffee/modules/*.js", + "#{paths.tmp}coffee/modules/common/*.js", + "#{paths.tmp}coffee/modules/backlog/*.js", + "#{paths.tmp}coffee/modules/taskboard/*.js", + "#{paths.tmp}coffee/modules/kanban/*.js", + "#{paths.tmp}coffee/modules/issues/*.js", + "#{paths.tmp}coffee/modules/userstories/*.js", + "#{paths.tmp}coffee/modules/tasks/*.js", + "#{paths.tmp}coffee/modules/team/*.js", + "#{paths.tmp}coffee/modules/wiki/*.js", + "#{paths.tmp}coffee/modules/admin/*.js", + "#{paths.tmp}coffee/modules/projects/*.js", + "#{paths.tmp}coffee/modules/locales/*.js", + "#{paths.tmp}coffee/modules/base/*.js", + "#{paths.tmp}coffee/modules/resources/*.js", + "#{paths.tmp}coffee/modules/user-settings/*.js", + "#{paths.tmp}coffee/modules/integrations/*.js", + "#{paths.tmp}plugins/**/*.js" ] -isDeploy = process.argv[process.argv.length - 1] == 'deploy' +paths.libs = [ + "#{paths.app}vendor/jquery/dist/jquery.js", + "#{paths.app}vendor/lodash/dist/lodash.js", + "#{paths.app}vendor/emoticons/lib/emoticons.js", + "#{paths.app}vendor/underscore.string/lib/underscore.string.js", + "#{paths.app}vendor/angular/angular.js", + "#{paths.app}vendor/angular-route/angular-route.js", + "#{paths.app}vendor/angular-sanitize/angular-sanitize.js", + "#{paths.app}vendor/angular-animate/angular-animate.js", + "#{paths.app}vendor/i18next/i18next.js", + "#{paths.app}vendor/moment/min/moment-with-langs.js", + "#{paths.app}vendor/checksley/checksley.js", + "#{paths.app}vendor/pikaday/pikaday.js", + "#{paths.app}vendor/jquery-flot/jquery.flot.js", + "#{paths.app}vendor/jquery-flot/jquery.flot.pie.js", + "#{paths.app}vendor/jquery-flot/jquery.flot.time.js", + "#{paths.app}vendor/flot-axislabels/jquery.flot.axislabels.js", + "#{paths.app}vendor/flot.tooltip/js/jquery.flot.tooltip.js", + "#{paths.app}vendor/jquery-textcomplete/jquery.textcomplete.js", + "#{paths.app}vendor/markitup-1x/markitup/jquery.markitup.js", + "#{paths.app}vendor/malihu-custom-scrollbar-plugin/jquery.mCustomScrollbar.concat.min.js", + "#{paths.app}vendor/raven-js/dist/raven.js", + "#{paths.app}vendor/l.js/l.js", + "#{paths.app}js/jquery.ui.git-custom.js", + "#{paths.app}js/jquery-ui.drag-multiple-custom.js", + "#{paths.app}js/sha1-custom.js", +] + +isDeploy = process.argv[process.argv.length - 1] == "deploy" ############################################################################ # Layout/CSS Related tasks @@ -122,14 +119,14 @@ isDeploy = process.argv[process.argv.length - 1] == 'deploy' gulp.task "jade", -> gulp.src(paths.jade) .pipe(plumber()) - .pipe(cache("jade")) + .pipe(changed(paths.tmp, {extension: ".html"})) .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) .pipe(gulp.dest(paths.tmp)) gulp.task "jade-inheritance", -> gulp.src(paths.jade) .pipe(plumber()) - .pipe(cache("jade")) + .pipe(changed(paths.tmp, {extension: ".html"})) .pipe(jadeInheritance({basedir: "./app/"})) .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) .pipe(gulp.dest(paths.tmp)) @@ -153,35 +150,35 @@ gulp.task "jade-watch", (cb) -> # CSS Related tasks ############################################################################## -gulp.task "sass-lint", -> +gulp.task "scss-lint", -> gulp.src(paths.sass.concat("!#{paths.app}/styles/shame/**/*.scss")) - .pipe(cache("sasslint")) + .pipe(cache("scsslint")) .pipe(gulpif(!isDeploy, scsslint({config: "scsslint.yml"}))) -gulp.task "sass-compile", ["sass-lint"], -> +gulp.task "sass-compile", ["scss-lint"], -> gulp.src(paths.sass) .pipe(plumber()) - .pipe(cache("scss")) + .pipe(changed(paths.tmp, {extension: ".css"})) .pipe(insert.prepend('@import "dependencies";')) .pipe(sass({ - 'sourcemap=none': true, + "sourcemap=none": true, loadPath: [ "#{paths.app}styles/extras/" ] })) - .pipe(gulp.dest(paths.tmpStyles)) + .pipe(gulp.dest(paths.tmp)) csslintChannel = lazypipe() .pipe(csslint, "csslintrc.json") .pipe(csslint.reporter) gulp.task "css-lint-app", -> - gulp.src(mainSass.concat([paths.tmpStylesExtras])) + gulp.src(mainSass.concat(["#{paths.tmp}plugins/**/*.css"])) .pipe(cache("csslint")) .pipe(gulpif(!isDeploy, csslintChannel())) gulp.task "css-join", ["css-lint-app"], -> - gulp.src(mainSass.concat([paths.tmpStylesExtras])) + gulp.src(mainSass.concat(["#{paths.tmp}plugins/**/*.css"])) .pipe(concat("app.css")) .pipe(autoprefixer({ cascade: false @@ -196,7 +193,6 @@ gulp.task "css-vendor", -> .pipe(concat("vendor.css")) .pipe(gulp.dest(paths.tmp)) - gulp.task "styles", ["css-app", "css-vendor"], -> _paths = [ paths.tmp + "vendor.css", @@ -231,46 +227,44 @@ gulp.task "locales", -> gulp.task "coffee", -> gulp.src(paths.coffee) .pipe(plumber()) + .pipe(changed(paths.tmp, {extension: ".js"})) .pipe(coffee()) - .pipe(concat("app.js")) + .pipe(gulp.dest(paths.tmp)) + +gulp.task "plugins-js", -> + gulp.src("#{paths.app}plugins/**/*.js") .pipe(gulp.dest(paths.tmp)) gulp.task "jslibs-watch", -> - gulp.src(paths.js) + gulp.src(paths.libs) .pipe(plumber()) .pipe(concat("libs.js")) .pipe(gulp.dest(paths.dist + "js/")) gulp.task "jslibs-deploy", -> - gulp.src(paths.js) + gulp.src(paths.libs) .pipe(plumber()) .pipe(sourcemaps.init()) .pipe(concat("libs.js")) .pipe(uglify({mangle:false, preserveComments: false})) - .pipe(sourcemaps.write('./')) + .pipe(sourcemaps.write("./")) .pipe(gulp.dest(paths.dist + "js/")) -gulp.task "app-watch", ["coffee", "conf", "locales", "app-loader"], -> - _paths = [ - paths.tmp + "app.js", - paths.tmp + "locales.en.js" - ] +gulp.task "app-watch", ["coffee", "plugins-js", "conf", "locales", "app-loader"], -> + _paths = paths.js.concat("#{paths.tmp}locales.en.js") gulp.src(_paths) .pipe(concat("app.js")) .pipe(gulp.dest(paths.dist + "js/")) -gulp.task "app-deploy", ["coffee", "conf", "locales", "app-loader"], -> - _paths = [ - paths.tmp + "app.js", - paths.tmp + "locales.en.js" - ] +gulp.task "app-deploy", ["coffee", "plugins-js", "conf", "locales", "app-loader"], -> + _paths = paths.js.concat("#{paths.tmp}locales.en.js") gulp.src(_paths) .pipe(sourcemaps.init()) .pipe(concat("app.js")) .pipe(uglify({mangle:false, preserveComments: false})) - .pipe(sourcemaps.write('./')) + .pipe(sourcemaps.write("./")) .pipe(gulp.dest(paths.dist + "js/")) ############################################################################## @@ -278,24 +272,24 @@ gulp.task "app-deploy", ["coffee", "conf", "locales", "app-loader"], -> ############################################################################## # SVG -gulp.task "copy-svg", -> +gulp.task "copy-svg", -> gulp.src("#{paths.app}/svg/**/*") .pipe(gulp.dest("#{paths.dist}/svg/")) -gulp.task "copy-fonts", -> +gulp.task "copy-fonts", -> gulp.src("#{paths.app}/fonts/*") .pipe(gulp.dest("#{paths.dist}/fonts/")) -gulp.task "copy-images", -> +gulp.task "copy-images", -> gulp.src("#{paths.app}/images/**/*") - .pipe(imagemin({progressive: true})) + .pipe(gulpif(isDeploy, imagemin({progressive: true}))) .pipe(gulp.dest("#{paths.dist}/images/")) gulp.src("#{paths.app}/plugins/**/images/*") .pipe(flatten()) .pipe(gulp.dest("#{paths.dist}/images/")) -gulp.task "copy-plugin-templates", -> +gulp.task "copy-plugin-templates", -> gulp.src("#{paths.app}/plugins/**/templates/**/*.html") .pipe(gulp.dest("#{paths.dist}/plugins/")) @@ -303,7 +297,6 @@ gulp.task "copy-extras", -> gulp.src("#{paths.extras}/*") .pipe(gulp.dest("#{paths.dist}/")) - gulp.task "copy", ["copy-fonts", "copy-images", "copy-plugin-templates", "copy-svg", "copy-extras"] gulp.task "express", -> @@ -335,8 +328,8 @@ gulp.task "watch", -> gulp.watch(paths.images, ["copy-images"]) gulp.watch(paths.fonts, ["copy-fonts"]) -# Remove the tmp directory -del.sync(paths.tmp) +if isDeploy + del.sync(paths.tmp) gulp.task "deploy", [ "copy", diff --git a/package.json b/package.json index 8b00ec7e..cfdfbaa9 100644 --- a/package.json +++ b/package.json @@ -38,9 +38,6 @@ "gulp-jade": "^0.11.0", "gulp-jade-inheritance": "0.5.0", "gulp-minify-css": "^0.4.4", - "gulp-minify-html": "^0.1.8", - "gulp-newer": "^0.5.0", - "gulp-notify": "^2.2.0", "gulp-plumber": "^0.6.6", "gulp-rename": "^1.2.0", "gulp-ruby-sass": "^0.7.1", @@ -49,8 +46,6 @@ "gulp-styledocco": "0.0.1", "gulp-template": "^2.1.0", "gulp-uglify": "~1.1.0", - "gulp-util": "~3.0.3", - "gulp-watch": "^4.1.0", "gulp-wrap": "^0.10.1", "lazypipe": "^0.2.2", "readable-stream": "~1.0.33", From 34a37521cc780a255b6938f54621531aece22f3f Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Feb 2015 14:59:56 +0100 Subject: [PATCH 057/207] remove very-light-gray --- app/styles/layout/forms.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/layout/forms.scss b/app/styles/layout/forms.scss index 8099fd98..ad69d0f2 100644 --- a/app/styles/layout/forms.scss +++ b/app/styles/layout/forms.scss @@ -19,7 +19,7 @@ input[type="date"], input[type="password"], select, textarea { - background: $very-light-gray; + background: $whitish; border: 1px solid $gray-light; color: $grayer; margin: 0; From aece852b4129c2b67d5c628feec060379491d3e8 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Feb 2015 07:39:10 +0100 Subject: [PATCH 058/207] fix #2184 disable drag when the user click on the popover --- app/coffee/modules/backlog/sortable.coffee | 1 + 1 file changed, 1 insertion(+) diff --git a/app/coffee/modules/backlog/sortable.coffee b/app/coffee/modules/backlog/sortable.coffee index ac0cc1ac..96d74f0f 100644 --- a/app/coffee/modules/backlog/sortable.coffee +++ b/app/coffee/modules/backlog/sortable.coffee @@ -58,6 +58,7 @@ BacklogSortableDirective = ($repo, $rs, $rootscope, $tgConfirm) -> $el.sortable({ items: ".us-item-row", + cancel: ".popover" connectWith: ".sprint" containment: ".wrapper" dropOnEmpty: true From 4657e0674d02e42d2a7bc36826d5589aab5b3ed8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Feb 2015 07:47:57 +0100 Subject: [PATCH 059/207] Remove unmet dependencies from package.json --- package.json | 3 --- 1 file changed, 3 deletions(-) diff --git a/package.json b/package.json index cfdfbaa9..c5b6d869 100644 --- a/package.json +++ b/package.json @@ -25,7 +25,6 @@ "gulp-autoprefixer": "^2.1.0", "gulp-cached": "1.0.2", "gulp-changed": "^1.1.1", - "gulp-clean": "^0.3.1", "gulp-coffee": "^2.3.1", "gulp-coffeelint": "~0.4.0", "gulp-concat": "^2.4.3", @@ -34,7 +33,6 @@ "gulp-if": "^1.2.5", "gulp-imagemin": "^2.1.0", "gulp-insert": "^0.4.0", - "gulp-intermediate": "^3.0.1", "gulp-jade": "^0.11.0", "gulp-jade-inheritance": "0.5.0", "gulp-minify-css": "^0.4.4", @@ -43,7 +41,6 @@ "gulp-ruby-sass": "^0.7.1", "gulp-scss-lint": "0.1.6", "gulp-sourcemaps": "^1.3.0", - "gulp-styledocco": "0.0.1", "gulp-template": "^2.1.0", "gulp-uglify": "~1.1.0", "gulp-wrap": "^0.10.1", From 3612bc91eb5835c176def0436bcfe28f910891dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Feb 2015 08:41:41 +0100 Subject: [PATCH 060/207] Hide intro text of archived columns when vertical fold --- app/styles/modules/kanban/kanban-table.scss | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/styles/modules/kanban/kanban-table.scss b/app/styles/modules/kanban/kanban-table.scss index 8d5e75d9..f498637a 100644 --- a/app/styles/modules/kanban/kanban-table.scss +++ b/app/styles/modules/kanban/kanban-table.scss @@ -44,6 +44,9 @@ $column-margin: 0 10px 0 0; .kanban-task { display: none; } + .kanban-column-intro { + display: none; + } } } From 2fadda0caacbb362bc7d50c000bc3758939c2770 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Feb 2015 09:19:04 +0100 Subject: [PATCH 061/207] Standard padding space --- app/styles/layout/base.scss | 8 +++++--- app/styles/layout/issues.scss | 2 +- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/app/styles/layout/base.scss b/app/styles/layout/base.scss index 7976e40e..cae94352 100644 --- a/app/styles/layout/base.scss +++ b/app/styles/layout/base.scss @@ -93,7 +93,7 @@ body { flex: 0 0 auto; min-height: 100vh; min-width: 0; - padding: 2rem 1rem; + padding: 1rem; width: 320px; &.filters-bar { flex: 0 0 auto; @@ -110,6 +110,9 @@ body { } } } + .search-in { + margin-top: .5rem; + } } .menu-tertiary { @@ -127,8 +130,7 @@ body { .main { flex: 4; min-width: 600px; - padding: 2rem; - padding-bottom: 1rem; + padding: 1rem 2rem; } .icon { diff --git a/app/styles/layout/issues.scss b/app/styles/layout/issues.scss index d577a4a5..1c122c2f 100644 --- a/app/styles/layout/issues.scss +++ b/app/styles/layout/issues.scss @@ -5,6 +5,6 @@ } .filters-inner { opacity: 1; - padding: 2em 1em; + padding: 1rem; } } From 3967fc1bffd3726878a5de495110c1d8a5c615d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Feb 2015 10:06:47 +0100 Subject: [PATCH 062/207] Fix taiga secondary sidebar active state color --- app/styles/modules/admin/admin-submenu.scss | 1 + 1 file changed, 1 insertion(+) diff --git a/app/styles/modules/admin/admin-submenu.scss b/app/styles/modules/admin/admin-submenu.scss index 6865b220..5af5f8e5 100644 --- a/app/styles/modules/admin/admin-submenu.scss +++ b/app/styles/modules/admin/admin-submenu.scss @@ -20,6 +20,7 @@ &:hover { color: $blackish; .icon { + color: $blackish; opacity: 1; transition: opacity .3s linear; } From e25c52dfdd9cef99a0ffea7148acd5b7134e650e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Tue, 10 Feb 2015 12:46:03 +0100 Subject: [PATCH 063/207] Allowing auth plugins --- CHANGELOG.md | 1 + app/coffee/modules/auth.coffee | 4 +- app/coffee/modules/integrations/github.coffee | 111 ------------------ app/partials/includes/modules/login-form.jade | 2 +- app/styles/components/buttons.scss | 4 +- 5 files changed, 7 insertions(+), 115 deletions(-) delete mode 100644 app/coffee/modules/integrations/github.coffee diff --git a/CHANGELOG.md b/CHANGELOG.md index 8e30bff9..4a3c2ea6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ - ... ### Misc +- Plugin based authentication. - Added Taiga Style Guide in support Pages to enhance open source design. - Lots of small and not so small bugfixes. diff --git a/app/coffee/modules/auth.coffee b/app/coffee/modules/auth.coffee index 5e260cea..856488ef 100644 --- a/app/coffee/modules/auth.coffee +++ b/app/coffee/modules/auth.coffee @@ -197,7 +197,9 @@ LoginDirective = ($auth, $confirm, $location, $config, $routeParams, $navUrls, $ "password": $el.find("form.login-form input[name=password]").val() } - promise = $auth.login(data) + loginFormType = $config.get("loginFormType", "normal") + + promise = $auth.login(data, loginFormType) return promise.then(onSuccess, onError) $el.on "submit", "form", submit diff --git a/app/coffee/modules/integrations/github.coffee b/app/coffee/modules/integrations/github.coffee deleted file mode 100644 index fa61a86f..00000000 --- a/app/coffee/modules/integrations/github.coffee +++ /dev/null @@ -1,111 +0,0 @@ -### -# Copyright (C) 2014 Andrey Antukh -# Copyright (C) 2014 Jesús Espino Garcia -# Copyright (C) 2014 David Barragán Merino -# -# This program is free software: you can redistribute it and/or modify -# it under the terms of the GNU Affero General Public License as -# published by the Free Software Foundation, either version 3 of the -# License, or (at your option) any later version. -# -# This program is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -# GNU Affero General Public License for more details. -# -# You should have received a copy of the GNU Affero General Public License -# along with this program. If not, see . -# -# File: modules/integrations/github.coffee -### - -taiga = @.taiga - -module = angular.module("taigaIntegrations") - -AUTH_URL = "https://github.com/login/oauth/authorize" - - -############################################################################# -## User story team requirements button directive -############################################################################# - -GithubLoginButtonDirective = ($window, $params, $location, $config, $events, $confirm, $auth, $navUrls, $loader) -> - # Login or registar a user with his/her github account. - # - # Example: - # tg-github-login-button() - # - # Requirements: - # - ... - - template = """ - - - Login with Github - - """ #TODO: i18n - - link = ($scope, $el, $attrs) -> - clientId = $config.get("gitHubClientId", null) - return if not clientId - - renderGitHubButton = -> - $el.html(template) if clientId - - loginOnSuccess = (response) -> - if $params.next and $params.next != $navUrls.resolve("login") - nextUrl = $params.next - else - nextUrl = $navUrls.resolve("home") - - $events.setupConnection() - - $location.search("next", null) - $location.search("token", null) - $location.search("state", null) - $location.search("code", null) - $location.path(nextUrl) - - loginOnError = (response) -> - $location.search("state", null) - $location.search("code", null) - $loader.pageLoaded() - - if response.data.error_message - $confirm.notify("light-error", response.data.error_message ) - else - $confirm.notify("light-error", "Our Oompa Loompas have not been able to get you - credentials from GitHub.") #TODO: i18n - - loginWithGitHubAccount = -> - type = $params.state - code = $params.code - token = $params.token - - return if not (type == "github" and code) - $loader.start() - - data = {code: code, token: token} - $auth.login(data, type).then(loginOnSuccess, loginOnError) - - renderGitHubButton() - loginWithGitHubAccount() - - $el.on "click", ".button-github", (event) -> - redirectToUri = $location.absUrl() - url = "#{AUTH_URL}?client_id=#{clientId}&redirect_uri=#{redirectToUri}&state=github&scope=user:email" - $window.location.href = url - - $scope.$on "$destroy", -> - $el.off() - - return { - link: link - restrict: "EA" - template: "" - } - -module.directive("tgGithubLoginButton", ["$window", '$routeParams', "$tgLocation", "$tgConfig", "$tgEvents", - "$tgConfirm", "$tgAuth", "$tgNavUrls", "tgLoader", - GithubLoginButtonDirective]) diff --git a/app/partials/includes/modules/login-form.jade b/app/partials/includes/modules/login-form.jade index 67d510bf..3517cbde 100644 --- a/app/partials/includes/modules/login-form.jade +++ b/app/partials/includes/modules/login-form.jade @@ -12,6 +12,6 @@ div.login-form-container(tg-login) fieldset button.button-green.submit-button(type="submit", title="Sign in") Sign in - fieldset(tg-github-login-button) + fieldset(ng-repeat="plugin in contribPlugins|filter:{type: 'auth'}", ng-include="plugin.template") tg-public-register-message diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index e340990c..6a270a08 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -100,11 +100,11 @@ a.button-bulk { transition: background .3s linear; } } -.button-github { +.button-auth { @extend %button; background: $grayer; vertical-align: middle; - .icon { + .icon, img { @extend %large; color: $white; margin-right: .5rem; From b858adec9e44ff59382234d9fac116c7f2162092 Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Wed, 11 Feb 2015 21:07:38 +0100 Subject: [PATCH 064/207] Update nav user settings image on avatar change --- app/partials/project/project-menu.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/project/project-menu.jade b/app/partials/project/project-menu.jade index beb4a7f8..c913e249 100644 --- a/app/partials/project/project-menu.jade +++ b/app/partials/project/project-menu.jade @@ -60,4 +60,4 @@ div(class="menu-container") li a(href="" title="Logout" class="logout") Logout a(href="" title="User preferences" class="avatar" id="nav-user-settings") - img(src!="<%- user.photo %>" alt!="<%- user.full_name_display %>") + img(src!="{{ user.photo }}" alt!="{{ user.full_name_display }}") From 5246be9f695175940231a006e0d3d09b101ad8a9 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 12 Feb 2015 10:25:40 +0100 Subject: [PATCH 065/207] remove unnecessary lodash escaping --- app/partials/project/project-menu.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/project/project-menu.jade b/app/partials/project/project-menu.jade index c913e249..9b70ae09 100644 --- a/app/partials/project/project-menu.jade +++ b/app/partials/project/project-menu.jade @@ -60,4 +60,4 @@ div(class="menu-container") li a(href="" title="Logout" class="logout") Logout a(href="" title="User preferences" class="avatar" id="nav-user-settings") - img(src!="{{ user.photo }}" alt!="{{ user.full_name_display }}") + img(src="{{ user.photo }}" alt="{{ user.full_name_display }}") From 1313cbfdeb33da1e59fda91f65e1fc8467b2bcf9 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 12 Feb 2015 10:35:03 +0100 Subject: [PATCH 066/207] fix xss in the kanban with the fullname --- app/coffee/modules/kanban/main.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/kanban/main.coffee b/app/coffee/modules/kanban/main.coffee index 65eac846..f0575547 100644 --- a/app/coffee/modules/kanban/main.coffee +++ b/app/coffee/modules/kanban/main.coffee @@ -517,7 +517,7 @@ KanbanUserDirective = ($log) -> html = template(ctx) $el.html(html) username_label = $el.parent().find("a.task-assigned") - username_label.html(ctx.name) + username_label.text(ctx.name) username_label.on "click", (event) -> if $el.find("a").hasClass("noclick") return From 5466778017d3b8be657de2ae69bba021776f6795 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 10 Feb 2015 16:46:55 +0100 Subject: [PATCH 067/207] Desfault button refactor --- app/styles/components/buttons.scss | 96 ++++++++++++++++------------ app/styles/dependencies/helpers.scss | 29 ++------- 2 files changed, 58 insertions(+), 67 deletions(-) diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index 6a270a08..bb3a7050 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -1,80 +1,98 @@ -// Buttons components -.trans-button { - @extend %large; +.button, +%button { + @extend %medium; @extend %title; + background: transparent; + border: 0; + color: $white; + display: inline-block; + padding: .4rem 2.5rem; text-transform: uppercase; - &:hover, - &.active { - color: $green-taiga; - transition: color .3s linear; + transition: all .3s linear; + vertical-align: middle; + &:hover { + color: $white; + transition: all .3s linear; + } + &.loading { + span { + animation: loading .5s linear; + } + } + span { + color: $white; } .icon { + color: $white; margin-right: .3rem; } } -.button { +.trans-button { + @extend %large; + @extend %title; @extend %button; + span, + .icon { + color: $blackish; + transition: color .2s linear; + } + &:hover, + &.active { + span, + .icon { + color: $green-taiga; + } + } } -button { - @extend %button; -} .submit-button { width: 100%; } .button-green { + @extend %button; background: $green-taiga; - border: 0; - color: $white; - vertical-align: middle; &:hover, &.active { background: $fresh-taiga; } - span { - color: $white; - } } -.button-gray, -a.button-gray { +.button-gray { + @extend %button; background: $gray; - &:hover { + &:hover, + &.active { background: $fresh-taiga; color: $white; } - span { - color: $white; - } } -a.button-blackish { +.button-blackish { + @extend %button; background: $blackish; color: $whitish; &:hover { background: $blackish; color: $white; } - span { - color: $white; - } } -a.button-red { +.button-red { + @extend %button; background: $red-light; &:hover { background: $red; color: $white; } - span { + .icon { color: $white; } } -a.button-block { +.button-block { background: $white; color: $red; &:hover { @@ -83,35 +101,29 @@ a.button-block { } } -a.button-bulk { +.button-bulk { @extend %button; background: $green-taiga; - font-size: 22px; - margin-left: 2px; - padding: .3rem .5rem; - vertical-align: middle; + padding: .35rem .5rem; .icon { - @extend %medium; - color: $white; margin-right: 0; } &:hover { background: $fresh-taiga; - transition: background .3s linear; } } + + .button-auth { @extend %button; background: $grayer; - vertical-align: middle; - .icon, img { + .icon, + img { @extend %large; color: $white; margin-right: .5rem; - vertical-align: text-bottom; } &:hover { background: $black; - transition: background .3s linear; } } diff --git a/app/styles/dependencies/helpers.scss b/app/styles/dependencies/helpers.scss index b259563d..9440bf64 100644 --- a/app/styles/dependencies/helpers.scss +++ b/app/styles/dependencies/helpers.scss @@ -61,31 +61,6 @@ } } -.loading-spinner { - @extend %loading-spinner; -} - -%button { - @extend %medium; - @extend %title; - display: inline-block; - padding: 7px 40px 6px; - transition: background .3s linear; - text-transform: uppercase; - &:hover { - transition: background .3s linear; - } - &.loading { - span { - animation: loading .5s linear; - animation: spin 1s linear infinite; - } - } - .icon { - margin-right: .3rem; - } -} - // Background %triangled-bg { background: url('/images/bg.png') no-repeat center center; @@ -105,3 +80,7 @@ max-width: 1rem; transform-origin: 32 32; } + +.loading-spinner { + @extend %loading-spinner; +} From 61ce5e21db7867012e91dc00a4239e0a472f02ca Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 10 Feb 2015 16:49:23 +0100 Subject: [PATCH 068/207] A lot of stuff. Sorry. --- app/partials/admin/admin-memberships.jade | 2 +- app/partials/admin/admin-project-export.jade | 3 +- ...admin-project-values-issue-priorities.jade | 2 +- ...admin-project-values-issue-severities.jade | 2 +- .../admin-project-values-issue-status.jade | 2 +- .../admin-project-values-issue-types.jade | 2 +- .../admin-project-values-task-status.jade | 2 +- .../admin/admin-project-values-us-points.jade | 2 +- .../admin/admin-project-values-us-status.jade | 2 +- app/partials/admin/admin-roles.jade | 2 +- .../admin/admin-third-parties-webhooks.jade | 2 +- app/partials/backlog/backlog.jade | 21 ++++---- .../common/components/block-button.jade | 6 ++- .../common/components/delete-button.jade | 3 +- .../common/lightbox/lightbox-block.jade | 2 +- .../includes/components/addnewus.jade | 4 +- .../includes/components/large-summary.jade | 32 ++++++------- .../includes/components/sprint-summary.jade | 22 ++++----- app/partials/includes/components/summary.jade | 26 +++++----- .../includes/modules/admin-submenu-roles.jade | 2 +- .../includes/modules/admin-submenu.jade | 2 +- .../includes/modules/cancel-account-form.jade | 2 +- .../includes/modules/change-email-form.jade | 2 +- .../help-notions/lightbox-generic-notion.jade | 2 +- .../includes/modules/lightbox-ask-choice.jade | 4 +- .../modules/lightbox-attachments.jade | 4 +- .../modules/lightbox-delete-project.jade | 4 +- .../modules/lightbox-generic-ask.jade | 4 +- .../modules/lightbox-generic-error.jade | 2 +- .../modules/lightbox-generic-success.jade | 2 +- .../includes/modules/list-filters-kanban.jade | 5 +- .../includes/modules/list-filters.jade | 13 +---- app/partials/includes/modules/sprint.jade | 2 +- app/partials/includes/modules/sprints.jade | 14 ++---- .../issue/promote-issue-to-us-button.jade | 2 +- app/partials/kanban/kanban.jade | 9 ---- app/partials/project/project-colors.jade | 2 +- app/partials/project/projects.jade | 4 +- app/partials/task/task-detail.jade | 2 +- app/partials/us/us-detail.jade | 2 +- .../lightbox/lightbox-delete-account.jade | 4 +- app/partials/user/user-profile.jade | 2 +- app/styles/components/summary.scss | 48 +++++++++++-------- app/styles/layout/backlog.scss | 12 ++--- app/styles/modules/backlog/sprints.scss | 24 +++++----- app/styles/modules/filters/list-filters.scss | 28 ++--------- 46 files changed, 149 insertions(+), 193 deletions(-) diff --git a/app/partials/admin/admin-memberships.jade b/app/partials/admin/admin-memberships.jade index cf996944..880ccb68 100644 --- a/app/partials/admin/admin-memberships.jade +++ b/app/partials/admin/admin-memberships.jade @@ -9,7 +9,7 @@ div.wrapper.memberships(ng-controller="MembershipsController as ctrl", include ../includes/components/mainTitle .action-buttons - a.button.button-green(title="Add new member" href="" ng-click="ctrl.addNewMembers()") + a.button-green(title="Add new member" href="" ng-click="ctrl.addNewMembers()") span.text + New member include ../includes/modules/admin/admin-membership-table diff --git a/app/partials/admin/admin-project-export.jade b/app/partials/admin/admin-project-export.jade index ccac3ecb..807897e8 100644 --- a/app/partials/admin/admin-project-export.jade +++ b/app/partials/admin/admin-project-export.jade @@ -12,7 +12,8 @@ div.wrapper(ng-controller="ProjectProfileController as ctrl", p.admin-subtitle Export your project to save a backup or to create a new one based on this. div.admin-project-export-buttons - a.button.button-green.button-export(href="", title="Export your project") Export + a.button-green.button-export(href="", title="Export your project") + span Export div.admin-project-export-result.hidden div.spin.hidden diff --git a/app/partials/admin/admin-project-values-issue-priorities.jade b/app/partials/admin/admin-project-values-issue-priorities.jade index cb2a2116..be45b28d 100644 --- a/app/partials/admin/admin-project-values-issue-priorities.jade +++ b/app/partials/admin/admin-project-values-issue-priorities.jade @@ -12,7 +12,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify the priority levels users can assign to issues div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new priority include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-issue-severities.jade b/app/partials/admin/admin-project-values-issue-severities.jade index 57fea5a7..25d17ced 100644 --- a/app/partials/admin/admin-project-values-issue-severities.jade +++ b/app/partials/admin/admin-project-values-issue-severities.jade @@ -12,7 +12,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify the severity level users can select to classify issues div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new severity include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-issue-status.jade b/app/partials/admin/admin-project-values-issue-status.jade index b02c72e6..629b7fdd 100644 --- a/app/partials/admin/admin-project-values-issue-status.jade +++ b/app/partials/admin/admin-project-values-issue-status.jade @@ -12,7 +12,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify the column headers that you will use to classify Issues div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new status include ../includes/modules/admin/project-status diff --git a/app/partials/admin/admin-project-values-issue-types.jade b/app/partials/admin/admin-project-values-issue-types.jade index 20072b9e..4d702362 100644 --- a/app/partials/admin/admin-project-values-issue-types.jade +++ b/app/partials/admin/admin-project-values-issue-types.jade @@ -12,7 +12,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify the categories users can select to classify issues div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new type include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-task-status.jade b/app/partials/admin/admin-project-values-task-status.jade index be883b1f..5d6fa0ba 100644 --- a/app/partials/admin/admin-project-values-task-status.jade +++ b/app/partials/admin/admin-project-values-task-status.jade @@ -12,7 +12,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify the column headers that you will use to classify Tasks related to each User Stories div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new status include ../includes/modules/admin/project-status diff --git a/app/partials/admin/admin-project-values-us-points.jade b/app/partials/admin/admin-project-values-us-points.jade index 4483a03f..41b434ae 100644 --- a/app/partials/admin/admin-project-values-us-points.jade +++ b/app/partials/admin/admin-project-values-us-points.jade @@ -15,7 +15,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", include ../includes/components/help-notion-button div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new point include ../includes/modules/admin/project-points diff --git a/app/partials/admin/admin-project-values-us-status.jade b/app/partials/admin/admin-project-values-us-status.jade index eb6980cc..c87811ce 100644 --- a/app/partials/admin/admin-project-values-us-status.jade +++ b/app/partials/admin/admin-project-values-us-status.jade @@ -12,7 +12,7 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify the column headers that you will use to classify User Stories div.project-values-options - a.button.button-green.show-add-new(href="", title="Add New") + a.button-green.show-add-new(href="", title="Add New") span Add new status include ../includes/modules/admin/project-us-status diff --git a/app/partials/admin/admin-roles.jade b/app/partials/admin/admin-roles.jade index 335cef2d..0d42b660 100644 --- a/app/partials/admin/admin-roles.jade +++ b/app/partials/admin/admin-roles.jade @@ -9,7 +9,7 @@ div.wrapper.roles(ng-controller="RolesController as ctrl", .header-with-actions include ../includes/components/mainTitle .action-buttons - a.button.button-red.delete-role(href="", title="Delete", ng-click="ctrl.delete()") Delete + a.button-red.delete-role(href="", title="Delete", ng-click="ctrl.delete()") Delete div(tg-edit-role) diff --git a/app/partials/admin/admin-third-parties-webhooks.jade b/app/partials/admin/admin-third-parties-webhooks.jade index e56468a5..4262608c 100644 --- a/app/partials/admin/admin-third-parties-webhooks.jade +++ b/app/partials/admin/admin-third-parties-webhooks.jade @@ -14,7 +14,7 @@ block content p.admin-subtitle Webhooks notify external services about events in Taiga, like comments, user stories.... div.webhooks-options - a.button.button-green.hidden.add-webhook(href="",title="Add a New Webhook") Add Webhook + a.utton-green.hidden.add-webhook(href="",title="Add a New Webhook") Add Webhook section.webhooks-table.basic-table div.table-header diff --git a/app/partials/backlog/backlog.jade b/app/partials/backlog/backlog.jade index e8b4dd55..1b96fa32 100644 --- a/app/partials/backlog/backlog.jade +++ b/app/partials/backlog/backlog.jade @@ -9,16 +9,17 @@ div.wrapper(tg-backlog, ng-controller="BacklogController as ctrl", div.burndown(tg-gm-backlog-graph) include ../includes/modules/burndown div.backlog-menu - a.trans-button.move-to-current-sprint(href="", title="Move to Current Sprint", - id="move-to-current-sprint") - span.icon.icon-move - span.text Move to current Sprint - a.trans-button(href="", title="Show Filters", id="show-filters-button") - span.icon.icon-filter - span.text Show Filters - a.trans-button(href="", title="Show Tags", id="show-tags") - span.icon.icon-tag - span.text Show Tags + div.backlog-table-options + a.trans-button.move-to-current-sprint(href="", title="Move to Current Sprint", + id="move-to-current-sprint") + span.icon.icon-move + span.text Move to current Sprint + a.trans-button(href="", title="Show Filters", id="show-filters-button") + span.icon.icon-filter + span.text Show Filters + a.trans-button(href="", title="Show Tags", id="show-tags") + span.icon.icon-tag + span.text Show Tags include ../includes/components/addnewus section.backlog-table(ng-class="{'hidden': !visibleUserstories.length}") include ../includes/modules/backlog-table diff --git a/app/partials/common/components/block-button.jade b/app/partials/common/components/block-button.jade index 354ec00d..7e187687 100644 --- a/app/partials/common/components/block-button.jade +++ b/app/partials/common/components/block-button.jade @@ -1,2 +1,4 @@ -a(href="#", class="button button-gray item-block") Block -a(href="#", class="button button-red item-unblock") Unblock \ No newline at end of file +a(href="#", class="button button-gray item-block") + span Block +a(href="#", class="button button-red item-unblock") + span Unblock diff --git a/app/partials/common/components/delete-button.jade b/app/partials/common/components/delete-button.jade index c33733cf..dc2f2065 100644 --- a/app/partials/common/components/delete-button.jade +++ b/app/partials/common/components/delete-button.jade @@ -1 +1,2 @@ -a(href="", class="button button-red") Delete \ No newline at end of file +a(href="", class="button button-red") + span Delete diff --git a/app/partials/common/lightbox/lightbox-block.jade b/app/partials/common/lightbox/lightbox-block.jade index b80a0177..a6290d16 100644 --- a/app/partials/common/lightbox/lightbox-block.jade +++ b/app/partials/common/lightbox/lightbox-block.jade @@ -5,5 +5,5 @@ div.form fieldset textarea.reason(placeholder="Please explain the reason") - a.button.button-green(href="") + a.button-green(href="") span Save diff --git a/app/partials/includes/components/addnewus.jade b/app/partials/includes/components/addnewus.jade index 815ca0b1..403c271c 100644 --- a/app/partials/includes/components/addnewus.jade +++ b/app/partials/includes/components/addnewus.jade @@ -1,9 +1,9 @@ div.new-us - a.button.button-green(href="", title="Add a new User Story", + a.button-green(href="", title="Add a new User Story", ng-click="ctrl.addNewUs('standard')", tg-check-permission="add_us") span.text + Add a new User Story - a.button.button-bulk(href="", title="Add some new User Stories in bulk", + a.button-bulk(href="", title="Add some new User Stories in bulk", ng-click="ctrl.addNewUs('bulk')", tg-check-permission="add_us") span.icon.icon-bulk diff --git a/app/partials/includes/components/large-summary.jade b/app/partials/includes/components/large-summary.jade index a20b326d..ed410e63 100644 --- a/app/partials/includes/components/large-summary.jade +++ b/app/partials/includes/components/large-summary.jade @@ -1,37 +1,35 @@ div.summary.large-summary - div - div.summary-progress-bar - div.current-progress - div.data - span.number 30% - span.description completed - ul - li + div.large-summary-wrapper + div + div.summary-progress-bar + div.current-progress + div.data + span.number 30% + span.description completed + div.summary-stats span.number 12 span.description project
points - li + div.summary-stats span.number 23 span.description defined
points - li + div.summary-stats span.number 12 span.description assigned
points - li + div.summary-stats.summary-stats-divider span.number 23 span.description closed
points - ul - li + div.summary-stats span.icon.icon-bulk span.number 73 span.description created
tasks - li + div.summary-stats span.number 72 span.description closed
tasks - li + div.summary-stats span.number 18 span.description remaining
tasks - ul - li + div.summary-stats span.icon.icon-iocaine span.number 10 span.description iocanie
doses diff --git a/app/partials/includes/components/sprint-summary.jade b/app/partials/includes/components/sprint-summary.jade index 585f7b25..64d6bdbb 100644 --- a/app/partials/includes/components/sprint-summary.jade +++ b/app/partials/includes/components/sprint-summary.jade @@ -1,28 +1,26 @@ div.summary.large-summary - div - div.summary-progress-bar(tg-progress-bar="stats.completedPercentage") - div.data - span.number(ng-bind="stats.completedPercentage + '%'") + div.large-summary-wrapper + div.summary-progress-wrapper + div.summary-progress-bar(tg-progress-bar="stats.completedPercentage") + div.data + span.number(ng-bind="stats.completedPercentage + '%'") - ul - li + div.summary-stats span.number(ng-bind="stats.totalPointsSum|default:'--'") span.description total
points - li + div.summary-stats span.number(ng-bind="stats.completedPointsSum|default:'--'") span.description completed
points - ul - li + div.summary-stats span.icon.icon-bulk span.number(ng-bind="stats.openTasks|default:'--'") span.description open
tasks - li + div.summary-stats span.number(ng-bind="stats.completed_tasks|default:'--'") span.description closed
tasks - ul - li(title="Feeling a bit overwhelmed by a task? Make sure others know about it by clicking on Iocaine when editing a task. It's possible to become immune to this (fictional) deadly poison by consuming small amounts over time just as it's possible to get better at what you do by occasionally taking on extra challenges!") + div.summary-stats(title="Feeling a bit overwhelmed by a task? Make sure others know about it by clicking on Iocaine when editing a task. It's possible to become immune to this (fictional) deadly poison by consuming small amounts over time just as it's possible to get better at what you do by occasionally taking on extra challenges!") span.icon.icon-iocaine span.number(ng-bind="stats.iocaine_doses|default:'--'") span.description iocaine
doses diff --git a/app/partials/includes/components/summary.jade b/app/partials/includes/components/summary.jade index 9af07112..11624d8d 100644 --- a/app/partials/includes/components/summary.jade +++ b/app/partials/includes/components/summary.jade @@ -3,16 +3,16 @@ div.summary div.data span.number(ng-bind="stats.completedPercentage + '%'") - ul - li - span.number(ng-bind="stats.total_points") -- - span.description project
points - li - span.number(ng-bind="stats.defined_points") -- - span.description defined
points - li - span.number(ng-bind="stats.closed_points") -- - span.description closed
points - li - span.number(ng-bind="stats.speed | number:0") -- - span.description points /
sprint + + div.summary-stats + span.number(ng-bind="stats.total_points") -- + span.description project
points + div.summary-stats + span.number(ng-bind="stats.defined_points") -- + span.description defined
points + div.summary-stats + span.number(ng-bind="stats.closed_points") -- + span.description closed
points + div.summary-stats + span.number(ng-bind="stats.speed | number:0") -- + span.description points /
sprint diff --git a/app/partials/includes/modules/admin-submenu-roles.jade b/app/partials/includes/modules/admin-submenu-roles.jade index b4ee5663..3b5b12e0 100644 --- a/app/partials/includes/modules/admin-submenu-roles.jade +++ b/app/partials/includes/modules/admin-submenu-roles.jade @@ -10,6 +10,6 @@ section.admin-submenu-roles span.icon.icon-arrow-right div(tg-new-role) - a.button.button-gray.add-button(href="", title="Add New Role") + a.button-gray.add-button(href="", title="Add New Role") span.text + New role input(type="text", class="hidden new") diff --git a/app/partials/includes/modules/admin-submenu.jade b/app/partials/includes/modules/admin-submenu.jade index f6b296ca..ecd19c37 100644 --- a/app/partials/includes/modules/admin-submenu.jade +++ b/app/partials/includes/modules/admin-submenu.jade @@ -20,5 +20,5 @@ section.admin-submenu a(href="") Front span.icon.icon-arrow-right - a.button.button-gray(href="", title="Add New role") + a.button-gray(href="", title="Add New role") span.text + New role diff --git a/app/partials/includes/modules/cancel-account-form.jade b/app/partials/includes/modules/cancel-account-form.jade index 5e99a94b..28f34d34 100644 --- a/app/partials/includes/modules/cancel-account-form.jade +++ b/app/partials/includes/modules/cancel-account-form.jade @@ -8,5 +8,5 @@ div.change-email-form-container(tg-cancel-account) input(type="hidden", name="cancel_token", ng-model="data.cancel_token", data-required="true", placeholder="cancel account token") - a.button.button-cancel-account.button-gray(href="", title="Yes, I'm leaving") Yes, I'm leaving! + a.button-cancel-account.button-gray(href="", title="Yes, I'm leaving") Yes, I'm leaving! button(type="submit", class="hidden") diff --git a/app/partials/includes/modules/change-email-form.jade b/app/partials/includes/modules/change-email-form.jade index 4acd78fb..bd980f8b 100644 --- a/app/partials/includes/modules/change-email-form.jade +++ b/app/partials/includes/modules/change-email-form.jade @@ -8,5 +8,5 @@ div.change-email-form-container(tg-change-email) input(type="hidden", name="email_token", ng-model="data.email_token", data-required="true", placeholder="change email token") - a.button.button-change-email.button-gray(href="", title="Change email") Change email + a.button-change-email.button-gray(href="", title="Change email") Change email button(type="submit", class="hidden") diff --git a/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade b/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade index 00ce3a93..1c312656 100644 --- a/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade +++ b/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade @@ -8,5 +8,5 @@ section block content div.options - a.button.button-green(href="", title="Accept") + a.button-green(href="", title="Accept") span Accept diff --git a/app/partials/includes/modules/lightbox-ask-choice.jade b/app/partials/includes/modules/lightbox-ask-choice.jade index 4e69be3b..815c1076 100644 --- a/app/partials/includes/modules/lightbox-ask-choice.jade +++ b/app/partials/includes/modules/lightbox-ask-choice.jade @@ -9,7 +9,7 @@ form p.warning div.options - a.button.button-green(href="", title="Accept") + a.button-green(href="", title="Accept") span Accept - a.button.button-red(href="", title="Delete") + a.button-red(href="", title="Delete") span Cancel diff --git a/app/partials/includes/modules/lightbox-attachments.jade b/app/partials/includes/modules/lightbox-attachments.jade index b8d4cd19..8e86d3d5 100644 --- a/app/partials/includes/modules/lightbox-attachments.jade +++ b/app/partials/includes/modules/lightbox-attachments.jade @@ -4,7 +4,7 @@ fieldset.attachments span.icon.icon-attachment span.attachments-num 1 span.attachments-text attachment - a.button.button-gray(href="", title="Add new attachment") + a.button-gray(href="", title="Add new attachment") span + add attachment div.attachment-body - for(var x = 0; x < 1; x++) @@ -14,4 +14,4 @@ fieldset.attachments a(href="", title="Attachment pefildeusuario.png") pefildeusuariopefildeusuariopefildeusuario.png div.attachment-comment span Comentario sobre el contenido - span.attachment-size (125kb.) \ No newline at end of file + span.attachment-size (125kb.) diff --git a/app/partials/includes/modules/lightbox-delete-project.jade b/app/partials/includes/modules/lightbox-delete-project.jade index b05fb346..843f80f7 100644 --- a/app/partials/includes/modules/lightbox-delete-project.jade +++ b/app/partials/includes/modules/lightbox-delete-project.jade @@ -6,7 +6,7 @@ form span.question Are you sure you want to delete this project? span.subtitle All project data US/Tasks/Issues/Sprints/WikiPages will be lost! :-( div.options - a.button.button-green(href="", title="Yes, I'm really sure") + a.button-green(href="", title="Yes, I'm really sure") span Yes, I'm really sure - a.button.button-red(href="", title="Cancel") + a.button-red(href="", title="Cancel") span Cancel diff --git a/app/partials/includes/modules/lightbox-generic-ask.jade b/app/partials/includes/modules/lightbox-generic-ask.jade index af346d15..e09ef2ae 100644 --- a/app/partials/includes/modules/lightbox-generic-ask.jade +++ b/app/partials/includes/modules/lightbox-generic-ask.jade @@ -6,7 +6,7 @@ form span.subtitle span.message div.options - a.button.button-green(href="", title="Accept") + a.button-green(href="", title="Accept") span Accept - a.button.button-red(href="", title="Delete") + a.button-red(href="", title="Delete") span Cancel diff --git a/app/partials/includes/modules/lightbox-generic-error.jade b/app/partials/includes/modules/lightbox-generic-error.jade index e8277d96..75fc6022 100644 --- a/app/partials/includes/modules/lightbox-generic-error.jade +++ b/app/partials/includes/modules/lightbox-generic-error.jade @@ -3,5 +3,5 @@ a.close(href="", title="close") section h2.title div.options - a.button.button-green(href="", title="Accept") + a.button-green(href="", title="Accept") span Accept diff --git a/app/partials/includes/modules/lightbox-generic-success.jade b/app/partials/includes/modules/lightbox-generic-success.jade index 02230f5d..1fd9208b 100644 --- a/app/partials/includes/modules/lightbox-generic-success.jade +++ b/app/partials/includes/modules/lightbox-generic-success.jade @@ -4,5 +4,5 @@ section h2.title p.message div.options - a.button.button-green(href="", title="Accept") + a.button-green(href="", title="Accept") span Accept diff --git a/app/partials/includes/modules/list-filters-kanban.jade b/app/partials/includes/modules/list-filters-kanban.jade index f97b82e7..75151fb0 100644 --- a/app/partials/includes/modules/list-filters-kanban.jade +++ b/app/partials/includes/modules/list-filters-kanban.jade @@ -6,8 +6,7 @@ section.list-filters | SHOW FILTERS div.new-issue - a.button.button-green(href="") - span.text - | + NEW TASK + a.button-green(href="") + span.text + NEW TASK a.button-bulk(href="") span.icon.icon-bulk diff --git a/app/partials/includes/modules/list-filters.jade b/app/partials/includes/modules/list-filters.jade index f4b4d71e..459540c9 100644 --- a/app/partials/includes/modules/list-filters.jade +++ b/app/partials/includes/modules/list-filters.jade @@ -1,17 +1,6 @@ section.list-filters(tg-check-permission="add_issue") - ul - // li - // a(href="#").active - // span.icon.icon-issues - // | SHOW LIST - - // li - // a(href="#") - // span.icon.icon-graph - // | SHOW GRAPH - div.new-issue - a.button.button-green(href="", ng-click="ctrl.addNewIssue()") + a.button-green(href="", ng-click="ctrl.addNewIssue()") span.text | + NEW ISSUE a.button-bulk(href="", ng-click="ctrl.addIssuesInBulk()") diff --git a/app/partials/includes/modules/sprint.jade b/app/partials/includes/modules/sprint.jade index ab3f19f6..6ceb219f 100644 --- a/app/partials/includes/modules/sprint.jade +++ b/app/partials/includes/modules/sprint.jade @@ -12,7 +12,7 @@ div.sprint-table span(tg-bo-bind="us.subject") div.column-points.width-1(tg-bo-bind="us.total_points", ng-class="{closed: us.is_closed, blocked: us.is_blocked}") -a.button.button-gray(tg-bo-title="'Go to Taskboard of ' + sprint.name", +a.button-gray(tg-bo-title="'Go to Taskboard of ' + sprint.name", tg-nav="project-taskboard:project=project.slug,sprint=sprint.slug", tg-check-permission="view_milestones") diff --git a/app/partials/includes/modules/sprints.jade b/app/partials/includes/modules/sprints.jade index f5b147bc..2974915a 100644 --- a/app/partials/includes/modules/sprints.jade +++ b/app/partials/includes/modules/sprints.jade @@ -2,15 +2,11 @@ section.sprints header h1 SPRINTS div.summary - ul - li - span.number(ng-bind="project.total_milestones") -- - span.description
sprints - div.new-sprint - a.button.button-green(href="", title="Add New sprint", - ng-click="ctrl.addNewSprint()", - tg-check-permission="add_milestone") - span.text + New sprint + div.total-sprints + span.number(ng-bind="project.total_milestones") -- + span.description
sprints + a.button-green.add-sprint(href="", title="Add New sprint", ng-click="ctrl.addNewSprint()", tg-check-permission="add_milestone") + span.text + New sprint div.sprint.sprint-open(ng-repeat="sprint in openSprints track by sprint.id", tg-backlog-sprint="sprint", tg-sprint-sortable) include sprint diff --git a/app/partials/issue/promote-issue-to-us-button.jade b/app/partials/issue/promote-issue-to-us-button.jade index baf86991..6bbd17c5 100644 --- a/app/partials/issue/promote-issue-to-us-button.jade +++ b/app/partials/issue/promote-issue-to-us-button.jade @@ -1,2 +1,2 @@ a(class="button button-gray editable", tg-check-permission="add_us") - | Promote to User Story + span Promote to User Story diff --git a/app/partials/kanban/kanban.jade b/app/partials/kanban/kanban.jade index b8354946..606098d0 100644 --- a/app/partials/kanban/kanban.jade +++ b/app/partials/kanban/kanban.jade @@ -2,15 +2,6 @@ div.wrapper(tg-kanban, ng-controller="KanbanController as ctrl" ng-init="section='kanban'") section.main.kanban include ../includes/components/mainTitle - //- div.kanban-settings - //- // a.button.button-trans(href="", title="Filter") - //- // span.icon.icon-filter - //- // span Filters - //- //a.button.button-gray(href="", title="Filter") - //- // span Show Statistics - //-include ../includes/components/large-summary - //-include ../includes/modules/burndown - //-include ../includes/modules/list-filters-kanban include ../includes/modules/kanban-table div.lightbox.lightbox-generic-form.lb-create-edit-userstory(tg-lb-create-edit-userstory) diff --git a/app/partials/project/project-colors.jade b/app/partials/project/project-colors.jade index 9867471b..bab64a73 100644 --- a/app/partials/project/project-colors.jade +++ b/app/partials/project/project-colors.jade @@ -10,7 +10,7 @@ div.wrapper include ../includes/components/mainTitle div.project-colors-options - a.button.button-green.new-color(href="") + a.button-green.new-color(href="") span.text | + Add new status diff --git a/app/partials/project/projects.jade b/app/partials/project/projects.jade index ed120fba..f51708fa 100644 --- a/app/partials/project/projects.jade +++ b/app/partials/project/projects.jade @@ -25,10 +25,10 @@ div.home-projects-list(ng-controller="ProjectsController as ctrl") div(tg-projects-list) .create-project-button-wrapper - a.button.button-green.create-project-button(href="", ng-click="ctrl.newProject()", + a.button-green.create-project-button(href="", ng-click="ctrl.newProject()", title="Create new project") Create project div(tg-import-project-button) - a.button.button-blackish.import-project-button(href="", title="Import project") + a.button-blackish.import-project-button(href="", title="Import project") span.icon.icon-upload input.import-file.hidden(type="file") diff --git a/app/partials/task/task-detail.jade b/app/partials/task/task-detail.jade index d8ef1366..dd0075a0 100644 --- a/app/partials/task/task-detail.jade +++ b/app/partials/task/task-detail.jade @@ -4,7 +4,7 @@ div.wrapper(ng-controller="TaskDetailController as ctrl", div.us-detail-header.header-with-actions include ../includes/components/mainTitle .action-buttons - a.button.button-gray( + a.button-gray( tg-check-permission="view_milestones", href="", title="Go to taskboard", tg-nav="project-taskboard:project=project.slug,sprint=sprint.slug", diff --git a/app/partials/us/us-detail.jade b/app/partials/us/us-detail.jade index 6b706ed6..5a78e15c 100644 --- a/app/partials/us/us-detail.jade +++ b/app/partials/us/us-detail.jade @@ -4,7 +4,7 @@ div.wrapper(ng-controller="UserStoryDetailController as ctrl", div.us-detail-header.header-with-actions include ../includes/components/mainTitle .action-buttons - a.button.button-gray( + a.button-gray( tg-check-permission="view_milestones", href="", title="Go to taskboard", tg-nav="project-taskboard:project=project.slug,sprint=sprint.slug", diff --git a/app/partials/user/lightbox/lightbox-delete-account.jade b/app/partials/user/lightbox/lightbox-delete-account.jade index bd7c15af..03b3b528 100644 --- a/app/partials/user/lightbox/lightbox-delete-account.jade +++ b/app/partials/user/lightbox/lightbox-delete-account.jade @@ -6,7 +6,7 @@ form span.question Are you sure you want to delete your Taiga account? span.subtitle We're going to miss you! :-( div.options - a.button.button-green(href="", title="Accept") + a.button-green(href="", title="Accept") span Accept - a.button.button-red(href="", title="Cancel") + a.button-red(href="", title="Cancel") span Cancel diff --git a/app/partials/user/user-profile.jade b/app/partials/user/user-profile.jade index 2d6989e6..9f3dd154 100644 --- a/app/partials/user/user-profile.jade +++ b/app/partials/user/user-profile.jade @@ -20,7 +20,7 @@ div.wrapper(tg-user-profile, ng-controller="UserSettingsController as ctrl", tg-avatar-model="avatarAttachment") p The image will be cropped to 80x80px.
span.size-info.hidden(tg-bo-html="maxFileSizeMsg") - a.button.button-green.change(tg-bo-title="'Change photo. ' + maxFileSizeMsg") Change + a.button-green.change(tg-bo-title="'Change photo. ' + maxFileSizeMsg") Change a.use-gravatar Use gravatar image div.data diff --git a/app/styles/components/summary.scss b/app/styles/components/summary.scss index 7eb54e96..0c50809c 100644 --- a/app/styles/components/summary.scss +++ b/app/styles/components/summary.scss @@ -1,21 +1,17 @@ .summary { - @include clearfix; + align-content: center; background: $grayer; color: $white; + display: flex; + flex-wrap: wrap; + justify-content: flex-start; margin-bottom: 2rem; padding: 1em; - ul { - display: inline-block; - margin: 0; - padding: 0; - } - li { - display: inline-block; - margin-right: 1rem; + .summary-stats { + display: flex; + margin: 0 .5rem; } .data { - float: left; - margin-right: 1em; margin-top: 4px; .number { color: $fresh-taiga; @@ -25,29 +21,24 @@ } .icon { @extend %large; - float: left; } .number { @extend %xlarge; @extend %bold; - float: left; margin-right: .3rem; position: relative; top: 5px; } .description { - // line-height: 0; @extend %small; @extend %text; - float: left; line-height: .9rem; } } .summary-progress-bar { - background: $whitish; - float: left; + background: $white; height: 30px; margin-bottom: 0; margin-right: 10px; @@ -78,15 +69,30 @@ .large-summary { - ul { - border-right: 1px solid $whitish; + justify-content: space-between; + .large-summary-wrapper { + align-content: center; + display: flex; + flex-wrap: wrap; + justify-content: flex-start; + } + .summary-progress-wrapper { + display: flex; + } + .summary-progress-bar { + flex-basis: 200px; + min-width: 200px; + } + .summary-stats { margin-right: 1rem; - vertical-align: top; - &:last-of-type { + &:last-child { border: 0; margin: 0; } } + .summary-stats-divider { + margin-right: 2rem; + } .icon { @extend %xlarge; margin-right: .4rem; diff --git a/app/styles/layout/backlog.scss b/app/styles/layout/backlog.scss index 324d0eb5..65941a74 100644 --- a/app/styles/layout/backlog.scss +++ b/app/styles/layout/backlog.scss @@ -1,13 +1,8 @@ -.backlog { - .new-us { - float: right; - } -} - .backlog-menu { - @include clearfix; background: $whitish; color: $blackish; + display: flex; + justify-content: space-between; margin-bottom: 1rem; padding: .5rem; .trans-button { @@ -21,4 +16,7 @@ vertical-align: middle; } } + .button-bulk { + margin-left: .2rem; + } } diff --git a/app/styles/modules/backlog/sprints.scss b/app/styles/modules/backlog/sprints.scss index cecbd7f0..c6731682 100644 --- a/app/styles/modules/backlog/sprints.scss +++ b/app/styles/modules/backlog/sprints.scss @@ -1,19 +1,17 @@ .sprints { .summary { - @include clearfix; - background: $gray-light; - ul { - width: 40%; - } - li { - color: $grayer; - } + background: darken($whitish, 10%); + display: flex; + justify-content: space-between; } - .new-sprint { - float: right; - .button { - padding: .5rem 1.5rem; - } + .total-sprints { + align-items: flex-start; + color: $grayer; + display: flex; + } + .add-sprint { + margin: 0; + padding: .3rem 1.5rem; } .filter-closed-sprints { @extend %small; diff --git a/app/styles/modules/filters/list-filters.scss b/app/styles/modules/filters/list-filters.scss index 609cb8bd..56e0a7e9 100644 --- a/app/styles/modules/filters/list-filters.scss +++ b/app/styles/modules/filters/list-filters.scss @@ -2,32 +2,10 @@ align-items: center; background-color: $whitish; display: flex; - justify-content: space-between; + justify-content: flex-end; margin-bottom: 2rem; padding: .5rem 1rem; - ul { - display: flex; - margin-bottom: 0; - } - li { - margin-right: 2rem; - a { - @extend %large; - @extend %title; - opacity: .4; - &:hover { - color: $blackish; - opacity: 1; - transition: opacity .3s linear; - } - } - .active { - color: $blackish; - opacity: 1; - transition: opacity .3s linear; - } - .icon { - padding-right: .5rem; - } + .button-bulk { + margin-left: .2rem; } } From a8aae53c00d4faacdad147dae7769fdf49c24b74 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 10 Feb 2015 16:46:55 +0100 Subject: [PATCH 069/207] Desfault button refactor --- app/styles/components/buttons.scss | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index bb3a7050..baf0ea05 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -87,6 +87,7 @@ background: $red; color: $white; } +<<<<<<< HEAD .icon { color: $white; } @@ -99,6 +100,8 @@ background: $red-light; color: $white; } +======= +>>>>>>> Desfault button refactor } .button-bulk { @@ -113,6 +116,7 @@ } } +<<<<<<< HEAD .button-auth { @extend %button; @@ -121,6 +125,12 @@ img { @extend %large; color: $white; +======= +.button-auth { + @extend %button; + background: $grayer; + .icon { +>>>>>>> Desfault button refactor margin-right: .5rem; } &:hover { From 0187462216c9892cee800a2c52f44fc5f5015336 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Feb 2015 08:10:26 +0100 Subject: [PATCH 070/207] Fix wrong button extend in lightbox --- .../modules/lightbox-task-create-edit.jade | 4 ++-- .../modules/lightbox-us-create-edit.jade | 6 ++--- app/styles/components/buttons.scss | 2 +- app/styles/modules/common/lightbox.scss | 22 ------------------- 4 files changed, 6 insertions(+), 28 deletions(-) diff --git a/app/partials/includes/modules/lightbox-task-create-edit.jade b/app/partials/includes/modules/lightbox-task-create-edit.jade index c07b101a..4541d3a4 100644 --- a/app/partials/includes/modules/lightbox-task-create-edit.jade +++ b/app/partials/includes/modules/lightbox-task-create-edit.jade @@ -24,13 +24,13 @@ form div.settings fieldset.iocaine-flag(title="Feeling a bit overwhelmed by a task? Make sure others know about it by clicking on Iocaine when editing a task. It's possible to become immune to this (fictional) deadly poison by consuming small amounts over time just as it's possible to get better at what you do by occasionally taking on extra challenges!") input(type="checkbox", ng-model="task.is_iocaine", name="iocaine-task", id="iocaine-task", ng-value="true") - label.iocaine(for="iocaine-task") + label.iocaine.trans-button(for="iocaine-task") span.icon.icon-iocaine(for="iocaine-task icon-iocaine") span Iocaine fieldset.blocking-flag input(type="checkbox", ng-model="task.is_blocked", name="blocked-task", id="blocked-task", ng-value="true") - label.blocked(for="blocked-task", tr="common.blocked") + label.blocked.trans-button(for="blocked-task", tr="common.blocked") tg-blocking-message-input(watch="task.is_blocked", ng-model="task.blocked_note") diff --git a/app/partials/includes/modules/lightbox-us-create-edit.jade b/app/partials/includes/modules/lightbox-us-create-edit.jade index 0a6d73e7..9fcbd723 100644 --- a/app/partials/includes/modules/lightbox-us-create-edit.jade +++ b/app/partials/includes/modules/lightbox-us-create-edit.jade @@ -23,16 +23,16 @@ form fieldset.team-requirement input(type="checkbox", name="team_requirement", ng-model="us.team_requirement", id="team-requirement", ng-value="true") - label.requirement(for="team-requirement", tr="us.team-requirement") + label.requirement.trans-button(for="team-requirement", tr="us.team-requirement") fieldset.client-requirement input(type="checkbox", name="client_requirement", ng-model="us.client_requirement", id="client-requirement", ng-value="true") - label.requirement(for="client-requirement", tr="us.client-requirement") + label.requirement.trans-button(for="client-requirement", tr="us.client-requirement") fieldset.blocking-flag input(type="checkbox", name="is_blocked", ng-model="us.is_blocked", id="blocked-us" ng-value="true") - label.blocked(for="blocked-us", tr="common.blocked") + label.blocked.trans-button(for="blocked-us", tr="common.blocked") tg-blocking-message-input(watch="us.is_blocked", ng-model="us.blocked_note") diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index baf0ea05..b8755325 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -29,7 +29,7 @@ } .trans-button { - @extend %large; + @extend %medium; @extend %title; @extend %button; span, diff --git a/app/styles/modules/common/lightbox.scss b/app/styles/modules/common/lightbox.scss index e2fa350f..9824ce43 100644 --- a/app/styles/modules/common/lightbox.scss +++ b/app/styles/modules/common/lightbox.scss @@ -2,27 +2,6 @@ @extend %lightbox; } -.markdown-preview { - display: inline-block; - margin-bottom: .5rem; - a { - @extend %button; - @extend %small; - color: $gray-light; - padding: 3px 20px; - &:first-child { - border-right: 1px solid $gray-light; - } - &:hover { - color: $grayer; - transition: color .2s linear; - } - } - .active { - color: $grayer; - } -} - .lightbox-generic-form { form { flex-basis: 600px; @@ -41,7 +20,6 @@ } label { - @extend %button; border: 1px solid $gray-light; color: $grayer; cursor: pointer; From 8bb75f306847e2a58ee98ef23e4b87681c74d887 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Feb 2015 08:17:42 +0100 Subject: [PATCH 071/207] Fix wrong button merge --- app/styles/components/buttons.scss | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index b8755325..a7e371e5 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -87,7 +87,6 @@ background: $red; color: $white; } -<<<<<<< HEAD .icon { color: $white; } @@ -100,8 +99,6 @@ background: $red-light; color: $white; } -======= ->>>>>>> Desfault button refactor } .button-bulk { @@ -116,8 +113,6 @@ } } -<<<<<<< HEAD - .button-auth { @extend %button; background: $grayer; @@ -125,12 +120,6 @@ img { @extend %large; color: $white; -======= -.button-auth { - @extend %button; - background: $grayer; - .icon { ->>>>>>> Desfault button refactor margin-right: .5rem; } &:hover { From 51019c458bb2050c1b1c6f70ac2cc5de59d7ca40 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Feb 2015 08:28:09 +0100 Subject: [PATCH 072/207] Fix public/private project styles --- app/partials/admin/admin-project-profile.jade | 6 ++++-- .../modules/admin/admin-project-profile.scss | 21 +++++++++++++------ 2 files changed, 19 insertions(+), 8 deletions(-) diff --git a/app/partials/admin/admin-project-profile.jade b/app/partials/admin/admin-project-profile.jade index 4b8010c7..6ee7c272 100644 --- a/app/partials/admin/admin-project-profile.jade +++ b/app/partials/admin/admin-project-profile.jade @@ -41,10 +41,12 @@ div.wrapper(tg-project-profile, ng-controller="ProjectProfileController as ctrl" div.privacy-settings div input.hidden(type="radio", disabled="disabled") - label.button(for="public-project") Public Project + label.trans-button(for="public-project") + span Public Project div input.hidden(type="radio", checked="checked", disabled="disabled") - label.button(for="private-project") Private Project + label.trans-button(for="private-project") + span Private Project p All projects are private during Taiga's beta period. diff --git a/app/styles/modules/admin/admin-project-profile.scss b/app/styles/modules/admin/admin-project-profile.scss index 01049811..0339fc66 100644 --- a/app/styles/modules/admin/admin-project-profile.scss +++ b/app/styles/modules/admin/admin-project-profile.scss @@ -28,17 +28,26 @@ margin-right: .5rem; } } + // TODO: This should change when public projects available label { @extend %title; - background: $white; - border: 1px solid $whitish; - cursor: pointer; + border: 1px solid $gray-light; + cursor: not-allowed; display: block; text-align: center; + transition: all .2s linear; + span { + color: $gray-light; + } + // &:hover { + // border: 1px solid $fresh-taiga; + // } } - input { - &:checked+label { - background: $fresh-taiga; + input:checked+label { + background: $fresh-taiga; + border: 1px solid $fresh-taiga; + cursor: default; + span { color: $white; } } From 076cea03e53ddf515680d498ea0e72d5aac1d94d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Feb 2015 08:30:37 +0100 Subject: [PATCH 073/207] Fix broken button style on admin roles --- app/partials/admin/admin-roles.jade | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/partials/admin/admin-roles.jade b/app/partials/admin/admin-roles.jade index 0d42b660..52dc954f 100644 --- a/app/partials/admin/admin-roles.jade +++ b/app/partials/admin/admin-roles.jade @@ -9,7 +9,8 @@ div.wrapper.roles(ng-controller="RolesController as ctrl", .header-with-actions include ../includes/components/mainTitle .action-buttons - a.button-red.delete-role(href="", title="Delete", ng-click="ctrl.delete()") Delete + a.button-red.delete-role(href="", title="Delete", ng-click="ctrl.delete()") + span Delete div(tg-edit-role) From 5803926cc049614c781dea165d41abb1efbd1aef Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Fri, 13 Feb 2015 09:59:53 +0100 Subject: [PATCH 074/207] Update README.md --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index de60d8f1..c03c93a2 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,7 @@ # Taiga Front # ![Kaleidos Project](http://kaleidos.net/static/img/badge.png "Kaleidos Project") +[![Managed with Taiga](https://taiga.io/media/support/attachments/article-22/banner-gh.png)](https://taiga.io "Managed with Taiga") ## Get the compiled version ## From 575370fd9b45c431ee5e7b4f18368f967b2f6eae Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Feb 2015 15:43:41 +0100 Subject: [PATCH 075/207] speed up gulfile - add gulp-cache - replace gulp-ruby-sass by gulp-sass - convert gulpfile to js --- ...lite.github.scss => codehilite.github.css} | 0 gulpfile.coffee | 351 --------------- gulpfile.js | 409 ++++++++++++++++++ package.json | 11 +- scsslint.yml | 6 - 5 files changed, 414 insertions(+), 363 deletions(-) rename app/styles/vendor/{codehilite.github.scss => codehilite.github.css} (100%) delete mode 100644 gulpfile.coffee create mode 100644 gulpfile.js diff --git a/app/styles/vendor/codehilite.github.scss b/app/styles/vendor/codehilite.github.css similarity index 100% rename from app/styles/vendor/codehilite.github.scss rename to app/styles/vendor/codehilite.github.css diff --git a/gulpfile.coffee b/gulpfile.coffee deleted file mode 100644 index c4ae3ea8..00000000 --- a/gulpfile.coffee +++ /dev/null @@ -1,351 +0,0 @@ -gulp = require("gulp") -jade = require("gulp-jade") -coffee = require("gulp-coffee") -concat = require("gulp-concat") -uglify = require("gulp-uglify") -plumber = require("gulp-plumber") -wrap = require("gulp-wrap") -rename = require("gulp-rename") -flatten = require("gulp-flatten") -gulpif = require("gulp-if") -replace = require("gulp-replace") -sass = require("gulp-ruby-sass") -csslint = require("gulp-csslint") -minifyCSS = require("gulp-minify-css") -scsslint = require("gulp-scss-lint") -cache = require("gulp-cached") -jadeInheritance = require("gulp-jade-inheritance") -sourcemaps = require("gulp-sourcemaps") -insert = require("gulp-insert") -imagemin = require("gulp-imagemin") -autoprefixer = require("gulp-autoprefixer") -templateCache = require("gulp-angular-templatecache") -changed = require("gulp-changed") - -runSequence = require("run-sequence") -lazypipe = require("lazypipe") -del = require("del") - -mainSass = require("./main-sass").files - -paths = {} -paths.app = "app/" -paths.dist = "dist/" -paths.tmp = "tmp/" -paths.extras = "extras/" - -paths.jade = [ - "#{paths.app}**/*.jade", - "!#{paths.app}partial/includes/**", -] - -paths.htmlPartials = [ - "#{paths.tmp}partials/**/*.html", - "#{paths.tmp}plugins/**/*.html" -] - -paths.images = "#{paths.app}images/**/*" -paths.svg = "#{paths.app}svg/**/*" -paths.css = "#{paths.app}styles/vendor/*.css" -paths.locales = "#{paths.app}locales/**/*.json" - -paths.sass = [ - "#{paths.app}**/*.scss" - "!#{paths.app}/styles/bourbon/**/*.scss" - "!#{paths.app}/styles/dependencies/**/*.scss" - "!#{paths.app}/styles/extras/**/*.scss" -] - -paths.coffee = "#{paths.app}**/*.coffee" - -paths.js = [ - "#{paths.tmp}coffee/app.js", - "#{paths.tmp}coffee/*.js", - "#{paths.tmp}coffee/modules/controllerMixins.js", - "#{paths.tmp}coffee/modules/*.js", - "#{paths.tmp}coffee/modules/common/*.js", - "#{paths.tmp}coffee/modules/backlog/*.js", - "#{paths.tmp}coffee/modules/taskboard/*.js", - "#{paths.tmp}coffee/modules/kanban/*.js", - "#{paths.tmp}coffee/modules/issues/*.js", - "#{paths.tmp}coffee/modules/userstories/*.js", - "#{paths.tmp}coffee/modules/tasks/*.js", - "#{paths.tmp}coffee/modules/team/*.js", - "#{paths.tmp}coffee/modules/wiki/*.js", - "#{paths.tmp}coffee/modules/admin/*.js", - "#{paths.tmp}coffee/modules/projects/*.js", - "#{paths.tmp}coffee/modules/locales/*.js", - "#{paths.tmp}coffee/modules/base/*.js", - "#{paths.tmp}coffee/modules/resources/*.js", - "#{paths.tmp}coffee/modules/user-settings/*.js", - "#{paths.tmp}coffee/modules/integrations/*.js", - "#{paths.tmp}plugins/**/*.js" -] - -paths.libs = [ - "#{paths.app}vendor/jquery/dist/jquery.js", - "#{paths.app}vendor/lodash/dist/lodash.js", - "#{paths.app}vendor/emoticons/lib/emoticons.js", - "#{paths.app}vendor/underscore.string/lib/underscore.string.js", - "#{paths.app}vendor/angular/angular.js", - "#{paths.app}vendor/angular-route/angular-route.js", - "#{paths.app}vendor/angular-sanitize/angular-sanitize.js", - "#{paths.app}vendor/angular-animate/angular-animate.js", - "#{paths.app}vendor/i18next/i18next.js", - "#{paths.app}vendor/moment/min/moment-with-langs.js", - "#{paths.app}vendor/checksley/checksley.js", - "#{paths.app}vendor/pikaday/pikaday.js", - "#{paths.app}vendor/jquery-flot/jquery.flot.js", - "#{paths.app}vendor/jquery-flot/jquery.flot.pie.js", - "#{paths.app}vendor/jquery-flot/jquery.flot.time.js", - "#{paths.app}vendor/flot-axislabels/jquery.flot.axislabels.js", - "#{paths.app}vendor/flot.tooltip/js/jquery.flot.tooltip.js", - "#{paths.app}vendor/jquery-textcomplete/jquery.textcomplete.js", - "#{paths.app}vendor/markitup-1x/markitup/jquery.markitup.js", - "#{paths.app}vendor/malihu-custom-scrollbar-plugin/jquery.mCustomScrollbar.concat.min.js", - "#{paths.app}vendor/raven-js/dist/raven.js", - "#{paths.app}vendor/l.js/l.js", - "#{paths.app}js/jquery.ui.git-custom.js", - "#{paths.app}js/jquery-ui.drag-multiple-custom.js", - "#{paths.app}js/sha1-custom.js", -] - -isDeploy = process.argv[process.argv.length - 1] == "deploy" - -############################################################################ -# Layout/CSS Related tasks -############################################################################## - -gulp.task "jade", -> - gulp.src(paths.jade) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".html"})) - .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "jade-inheritance", -> - gulp.src(paths.jade) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".html"})) - .pipe(jadeInheritance({basedir: "./app/"})) - .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "copy-index", -> - gulp.src(paths.tmp + "index.html") - .pipe(gulp.dest(paths.dist)) - -gulp.task "template-cache", -> - gulp.src(paths.htmlPartials) - .pipe(templateCache({standalone: true})) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "jade-deploy", (cb) -> - runSequence("jade", "copy-index", "template-cache", cb) - -gulp.task "jade-watch", (cb) -> - runSequence("jade-inheritance", "copy-index", "template-cache", cb) - -############################################################################## -# CSS Related tasks -############################################################################## - -gulp.task "scss-lint", -> - gulp.src(paths.sass.concat("!#{paths.app}/styles/shame/**/*.scss")) - .pipe(cache("scsslint")) - .pipe(gulpif(!isDeploy, scsslint({config: "scsslint.yml"}))) - -gulp.task "sass-compile", ["scss-lint"], -> - gulp.src(paths.sass) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".css"})) - .pipe(insert.prepend('@import "dependencies";')) - .pipe(sass({ - "sourcemap=none": true, - loadPath: [ - "#{paths.app}styles/extras/" - ] - })) - .pipe(gulp.dest(paths.tmp)) - -csslintChannel = lazypipe() - .pipe(csslint, "csslintrc.json") - .pipe(csslint.reporter) - -gulp.task "css-lint-app", -> - gulp.src(mainSass.concat(["#{paths.tmp}plugins/**/*.css"])) - .pipe(cache("csslint")) - .pipe(gulpif(!isDeploy, csslintChannel())) - -gulp.task "css-join", ["css-lint-app"], -> - gulp.src(mainSass.concat(["#{paths.tmp}plugins/**/*.css"])) - .pipe(concat("app.css")) - .pipe(autoprefixer({ - cascade: false - })) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "css-app", (cb) -> - runSequence("sass-compile", "css-join", cb) - -gulp.task "css-vendor", -> - gulp.src(paths.css) - .pipe(concat("vendor.css")) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "styles", ["css-app", "css-vendor"], -> - _paths = [ - paths.tmp + "vendor.css", - paths.tmp + "app.css" - ] - - gulp.src(_paths) - .pipe(concat("main.css")) - .pipe(gulpif(isDeploy, minifyCSS({noAdvanced: true}))) - .pipe(gulp.dest(paths.dist + "styles/")) - -############################################################################## -# JS Related tasks -############################################################################## - -gulp.task "conf", -> - gulp.src(["conf/conf.example.json"]) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "app-loader", -> - gulp.src("app-loader/app-loader.coffee") - .pipe(replace("___VERSION___", (new Date()).getTime())) - .pipe(coffee()) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "locales", -> - gulp.src("app/locales/en/app.json") - .pipe(wrap("angular.module('taigaBase').value('localesEn', <%= contents %>);", {}, {parse: false})) - .pipe(rename("locales.en.js")) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "coffee", -> - gulp.src(paths.coffee) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".js"})) - .pipe(coffee()) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "plugins-js", -> - gulp.src("#{paths.app}plugins/**/*.js") - .pipe(gulp.dest(paths.tmp)) - -gulp.task "jslibs-watch", -> - gulp.src(paths.libs) - .pipe(plumber()) - .pipe(concat("libs.js")) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "jslibs-deploy", -> - gulp.src(paths.libs) - .pipe(plumber()) - .pipe(sourcemaps.init()) - .pipe(concat("libs.js")) - .pipe(uglify({mangle:false, preserveComments: false})) - .pipe(sourcemaps.write("./")) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "app-watch", ["coffee", "plugins-js", "conf", "locales", "app-loader"], -> - _paths = paths.js.concat("#{paths.tmp}locales.en.js") - - gulp.src(_paths) - .pipe(concat("app.js")) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "app-deploy", ["coffee", "plugins-js", "conf", "locales", "app-loader"], -> - _paths = paths.js.concat("#{paths.tmp}locales.en.js") - - gulp.src(_paths) - .pipe(sourcemaps.init()) - .pipe(concat("app.js")) - .pipe(uglify({mangle:false, preserveComments: false})) - .pipe(sourcemaps.write("./")) - .pipe(gulp.dest(paths.dist + "js/")) - -############################################################################## -# Common tasks -############################################################################## - -# SVG -gulp.task "copy-svg", -> - gulp.src("#{paths.app}/svg/**/*") - .pipe(gulp.dest("#{paths.dist}/svg/")) - -gulp.task "copy-fonts", -> - gulp.src("#{paths.app}/fonts/*") - .pipe(gulp.dest("#{paths.dist}/fonts/")) - -gulp.task "copy-images", -> - gulp.src("#{paths.app}/images/**/*") - .pipe(gulpif(isDeploy, imagemin({progressive: true}))) - .pipe(gulp.dest("#{paths.dist}/images/")) - - gulp.src("#{paths.app}/plugins/**/images/*") - .pipe(flatten()) - .pipe(gulp.dest("#{paths.dist}/images/")) - -gulp.task "copy-plugin-templates", -> - gulp.src("#{paths.app}/plugins/**/templates/**/*.html") - .pipe(gulp.dest("#{paths.dist}/plugins/")) - -gulp.task "copy-extras", -> - gulp.src("#{paths.extras}/*") - .pipe(gulp.dest("#{paths.dist}/")) - -gulp.task "copy", ["copy-fonts", "copy-images", "copy-plugin-templates", "copy-svg", "copy-extras"] - -gulp.task "express", -> - express = require("express") - app = express() - - app.use("/js", express.static("#{__dirname}/dist/js")) - app.use("/styles", express.static("#{__dirname}/dist/styles")) - app.use("/images", express.static("#{__dirname}/dist/images")) - app.use("/svg", express.static("#{__dirname}/dist/svg")) - app.use("/partials", express.static("#{__dirname}/dist/partials")) - app.use("/fonts", express.static("#{__dirname}/dist/fonts")) - app.use("/plugins", express.static("#{__dirname}/dist/plugins")) - - app.all "/*", (req, res, next) -> - # Just send the index.html for other files to support HTML5Mode - res.sendFile("index.html", {root: "#{__dirname}/dist/"}) - - app.listen(9001) - -# Rerun the task when a file changes -gulp.task "watch", -> - gulp.watch(paths.jade, ["jade-watch"]) - gulp.watch(paths.sass, ["styles"]) - gulp.watch(paths.svg, ["copy-svg"]) - gulp.watch(paths.coffee, ["app-watch"]) - gulp.watch(paths.js, ["jslibs-watch"]) - gulp.watch(paths.locales, ["app-watch"]) - gulp.watch(paths.images, ["copy-images"]) - gulp.watch(paths.fonts, ["copy-fonts"]) - -if isDeploy - del.sync(paths.tmp) - -gulp.task "deploy", [ - "copy", - "jade-deploy", - "app-deploy", - "jslibs-deploy", - "styles" -] - -# The default task (called when you run gulp from cli) -gulp.task "default", [ - "copy", - "styles", - "app-watch", - "jslibs-watch", - "jade-deploy", - "express", - "watch" -] diff --git a/gulpfile.js b/gulpfile.js new file mode 100644 index 00000000..252cb353 --- /dev/null +++ b/gulpfile.js @@ -0,0 +1,409 @@ +var gulp = require("gulp"), + jade = require("gulp-jade"), + coffee = require("gulp-coffee"), + concat = require("gulp-concat"), + uglify = require("gulp-uglify"), + plumber = require("gulp-plumber"), + wrap = require("gulp-wrap"), + rename = require("gulp-rename"), + flatten = require("gulp-flatten"), + gulpif = require("gulp-if"), + replace = require("gulp-replace"), + sass = require("gulp-sass"), + csslint = require("gulp-csslint"), + minifyCSS = require("gulp-minify-css"), + scsslint = require("gulp-scss-lint"), + cache = require("gulp-cache"), + cached = require("gulp-cached"), + jadeInheritance = require("gulp-jade-inheritance"), + sourcemaps = require("gulp-sourcemaps"), + insert = require("gulp-insert"), + autoprefixer = require("gulp-autoprefixer"), + templateCache = require("gulp-angular-templatecache"), + runSequence = require("run-sequence"), + del = require("del"); + +var mainSass = require("./main-sass").files; + +var paths = {}; +paths.app = "app/"; +paths.dist = "dist/"; +paths.tmp = "tmp/"; +paths.extras = "extras/"; + +paths.jade = [ + paths.app + "**/*.jade", + "!" + paths.app + "partial/includes/**", +]; + +paths.htmlPartials = [ + paths.tmp + "partials/**/*.html", + paths.tmp + "plugins/**/*.html" +]; + +paths.images = paths.app + "images/**/*"; +paths.svg = paths.app + "svg/**/*"; +paths.css = paths.app + "styles/vendor/*.css"; +paths.locales = paths.app + "locales/**/*.json"; + +paths.sass = [ + paths.app + "**/*.scss", + "!" + paths.app + "/styles/bourbon/**/*.scss", + "!" + paths.app + "/styles/dependencies/**/*.scss", + "!" + paths.app + "/styles/extras/**/*.scss" +]; + +paths.coffee = paths.app + "**/*.coffee"; + +paths.js = [ + paths.tmp + "coffee/app.js", + paths.tmp + "coffee/*.js", + paths.tmp + "coffee/modules/controllerMixins.js", + paths.tmp + "coffee/modules/*.js", + paths.tmp + "coffee/modules/common/*.js", + paths.tmp + "coffee/modules/backlog/*.js", + paths.tmp + "coffee/modules/taskboard/*.js", + paths.tmp + "coffee/modules/kanban/*.js", + paths.tmp + "coffee/modules/issues/*.js", + paths.tmp + "coffee/modules/userstories/*.js", + paths.tmp + "coffee/modules/tasks/*.js", + paths.tmp + "coffee/modules/team/*.js", + paths.tmp + "coffee/modules/wiki/*.js", + paths.tmp + "coffee/modules/admin/*.js", + paths.tmp + "coffee/modules/projects/*.js", + paths.tmp + "coffee/modules/locales/*.js", + paths.tmp + "coffee/modules/base/*.js", + paths.tmp + "coffee/modules/resources/*.js", + paths.tmp + "coffee/modules/user-settings/*.js", + paths.tmp + "coffee/modules/integrations/*.js", + paths.tmp + "plugins/**/*.js" +]; + +paths.libs = [ + paths.app + "vendor/jquery/dist/jquery.js", + paths.app + "vendor/lodash/dist/lodash.js", + paths.app + "vendor/emoticons/lib/emoticons.js", + paths.app + "vendor/underscore.string/lib/underscore.string.js", + paths.app + "vendor/angular/angular.js", + paths.app + "vendor/angular-route/angular-route.js", + paths.app + "vendor/angular-sanitize/angular-sanitize.js", + paths.app + "vendor/angular-animate/angular-animate.js", + paths.app + "vendor/i18next/i18next.js", + paths.app + "vendor/moment/min/moment-with-langs.js", + paths.app + "vendor/checksley/checksley.js", + paths.app + "vendor/pikaday/pikaday.js", + paths.app + "vendor/jquery-flot/jquery.flot.js", + paths.app + "vendor/jquery-flot/jquery.flot.pie.js", + paths.app + "vendor/jquery-flot/jquery.flot.time.js", + paths.app + "vendor/flot-axislabels/jquery.flot.axislabels.js", + paths.app + "vendor/flot.tooltip/js/jquery.flot.tooltip.js", + paths.app + "vendor/jquery-textcomplete/jquery.textcomplete.js", + paths.app + "vendor/markitup-1x/markitup/jquery.markitup.js", + paths.app + "vendor/malihu-custom-scrollbar-plugin/jquery.mCustomScrollbar.concat.min.js", + paths.app + "vendor/raven-js/dist/raven.js", + paths.app + "vendor/l.js/l.js", + paths.app + "js/jquery.ui.git-custom.js", + paths.app + "js/jquery-ui.drag-multiple-custom.js", + paths.app + "js/sha1-custom.js" +]; + +var isDeploy = process.argv[process.argv.length - 1] == "deploy"; + +/* +############################################################################ +# Layout/CSS Related tasks +############################################################################## +*/ + +gulp.task("jade", function() { + return gulp.src(paths.jade) + .pipe(plumber()) + .pipe(cached("jade")) + .pipe(cache(jade({pretty: true, locals:{v:(new Date()).getTime()}}))) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("jade-inheritance", function() { + return gulp.src(paths.jade) + .pipe(plumber()) + .pipe(cached('jade')) + .pipe(jadeInheritance({basedir: "./app/"})) + .pipe(cache(jade({pretty: true, locals:{v:(new Date()).getTime()}}))) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("copy-index", function() { + return gulp.src(paths.tmp + "index.html") + .pipe(gulp.dest(paths.dist)); +}); + +gulp.task("template-cache", function() { + return gulp.src(paths.htmlPartials) + .pipe(templateCache({standalone: true})) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("jade-deploy", function(cb) { + return runSequence("jade", "copy-index", "template-cache", cb); +}); + +gulp.task("jade-watch", function(cb) { + return runSequence("jade-inheritance", "copy-index", "template-cache", cb); +}); + +/* +############################################################################## +# CSS Related tasks +############################################################################## +*/ + +gulp.task("scss-lint", [], function() { + var ignore = [ + "!" + paths.app + "/styles/shame/**/*.scss", + "!" + paths.app + "/styles/components/markitup.scss" + ]; + + return gulp.src(paths.sass.concat(ignore)) + .pipe(gulpif(!isDeploy, cache(scsslint({endless: true, sync: true, config: "scsslint.yml"}), { + success: function(scsslintFile) { + return scsslintFile.scsslint.success; + }, + value: function(scsslintFile) { + return { + scsslint: scsslintFile.scsslint + }; + } + }))) +}); + +gulp.task("sass-compile", ["scss-lint"], function() { + return gulp.src(paths.sass) + .pipe(plumber()) + .pipe(insert.prepend('@import "dependencies";')) + .pipe(cache(sass({ + includePaths: [ + paths.app + "styles/extras/" + ] + }))) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("css-lint-app", function() { + return gulp.src(mainSass.concat([paths.tmp + "plugins/**/*.css"])) + .pipe(gulpif(!isDeploy, cache(csslint("csslintrc.json"), { + success: function(csslintFile) { + return csslintFile.csslint.success; + }, + value: function(csslintFile) { + return { + csslint: csslintFile.csslint + }; + } + }))) + .pipe(csslint.reporter()); +}); + +gulp.task("css-join", ["css-lint-app"], function() { + return gulp.src(mainSass.concat([paths.tmp + "plugins/**/*.css"])) + .pipe(concat("app.css")) + .pipe(autoprefixer({ + cascade: false + })) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("css-app", function(cb) { + return runSequence("sass-compile", "css-join", cb); +}); + +gulp.task("css-vendor", function() { + return gulp.src(paths.css) + .pipe(concat("vendor.css")) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("styles", ["css-app", "css-vendor"], function() { + var _paths = [ + paths.tmp + "vendor.css", + paths.tmp + "app.css" + ]; + + return gulp.src(_paths) + .pipe(concat("main.css")) + .pipe(gulpif(isDeploy, minifyCSS({noAdvanced: true}))) + .pipe(gulp.dest(paths.dist + "styles/")) +}); + +/* +############################################################################## +# JS Related tasks +############################################################################## +*/ +gulp.task("conf", function() { + return gulp.src(["conf/conf.example.json"]) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("app-loader", function() { + return gulp.src("app-loader/app-loader.coffee") + .pipe(replace("___VERSION___", (new Date()).getTime())) + .pipe(coffee()) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("locales", function() { + return gulp.src("app/locales/en/app.json") + .pipe(wrap("angular.module('taigaBase').value('localesEn', <%= contents %>);", {}, {parse: false})) + .pipe(rename("locales.en.js")) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("coffee", function() { + return gulp.src(paths.coffee) + .pipe(plumber()) + .pipe(cache(coffee())) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("plugins-js", function() { + return gulp.src(paths.app + "plugins/**/*.js") + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("jslibs-watch", function() { + return gulp.src(paths.libs) + .pipe(plumber()) + .pipe(concat("libs.js")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("jslibs-deploy", function() { + return gulp.src(paths.libs) + .pipe(plumber()) + .pipe(sourcemaps.init()) + .pipe(concat("libs.js")) + .pipe(uglify({mangle:false, preserveComments: false})) + .pipe(sourcemaps.write("./")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("app-watch", ["coffee", "plugins-js", "conf", "locales", "app-loader"], function() { + var _paths = paths.js.concat(paths.tmp + "locales.en.js") + + return gulp.src(_paths) + .pipe(concat("app.js")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("app-deploy", ["coffee", "plugins-js", "conf", "locales", "app-loader"], function() { + var _paths = paths.js.concat(paths.tmp + "locales.en.js") + + return gulp.src(_paths) + .pipe(sourcemaps.init()) + .pipe(concat("app.js")) + .pipe(uglify({mangle:false, preserveComments: false})) + .pipe(sourcemaps.write("./")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +/* +############################################################################## +# Common tasks +############################################################################## +*/ +gulp.task("clear", function(done) { + del.sync(paths.tmp); + + return cache.clearAll(done); +}); + +//SVG +gulp.task("copy-svg", function() { + return gulp.src(paths.app + "/svg/**/*") + .pipe(gulp.dest(paths.dist + "/svg/")); +}); + +gulp.task("copy-fonts", function() { + return gulp.src(paths.app + "/fonts/*") + .pipe(gulp.dest(paths.dist + "/fonts/")); +}); + +gulp.task("copy-images", function() { + var imageMin = gulp.src(paths.app + "/images/**/*"); + + if (isDeploy) { + //require imagemin is very slow + var imagemin = require("gulp-imagemin"); + imageMin.pipe(imagemin({progressive: true})) + } + + imageMin.pipe(gulp.dest(paths.dist + "/images/")) + + return gulp.src(paths.app + "/plugins/**/images/*") + .pipe(flatten()) + .pipe(gulp.dest(paths.dist + "/images/")); +}); + +gulp.task("copy-plugin-templates", function() { + return gulp.src(paths.app + "/plugins/**/templates/**/*.html") + .pipe(gulp.dest(paths.dist + "/plugins/")); +}); + +gulp.task("copy-extras", function() { + return gulp.src(paths.extras + "/*") + .pipe(gulp.dest(paths.dist + "/")); +}); + +gulp.task("copy", ["copy-fonts", "copy-images", "copy-plugin-templates", "copy-svg", "copy-extras"]); + +gulp.task("express", function() { + var express = require("express"); + var app = express(); + + app.use("/js", express.static(__dirname + "/dist/js")); + app.use("/styles", express.static(__dirname + "/dist/styles")); + app.use("/images", express.static(__dirname + "/dist/images")); + app.use("/svg", express.static(__dirname + "/dist/svg")); + app.use("/partials", express.static(__dirname + "/dist/partials")); + app.use("/fonts", express.static(__dirname + "/dist/fonts")); + app.use("/plugins", express.static(__dirname + "/dist/plugins")); + + app.all("/*", function(req, res, next) { + //Just send the index.html for other files to support HTML5Mode + res.sendFile("index.html", {root: __dirname + "/dist/"}); + }); + + app.listen(9001); +}); + +//Rerun the task when a file changes +gulp.task("watch", function() { + gulp.watch(paths.jade, ["jade-watch"]); + gulp.watch(paths.sass, ["styles"]); + gulp.watch(paths.svg, ["copy-svg"]); + gulp.watch(paths.coffee, ["app-watch"]); + gulp.watch(paths.libs, ["jslibs-watch"]); + gulp.watch(paths.locales, ["app-watch"]); + gulp.watch(paths.images, ["copy-images"]); + gulp.watch(paths.fonts, ["copy-fonts"]); +}); + +gulp.task("deploy", function(cb) { + runSequence("clear", [ + "copy", + "jade-deploy", + "app-deploy", + "jslibs-deploy", + "styles" + ], cb); +}); +//The default task (called when you run gulp from cli) +gulp.task("default", [ + "copy", + "styles", + "app-watch", + "jslibs-watch", + "jade-deploy", + "express", + "watch" +]); diff --git a/package.json b/package.json index c5b6d869..a1f81bd5 100644 --- a/package.json +++ b/package.json @@ -23,8 +23,8 @@ "gulp": "^3.8.10", "gulp-angular-templatecache": "^1.5.0", "gulp-autoprefixer": "^2.1.0", + "gulp-cache": "^0.2.4", "gulp-cached": "1.0.2", - "gulp-changed": "^1.1.1", "gulp-coffee": "^2.3.1", "gulp-coffeelint": "~0.4.0", "gulp-concat": "^2.4.3", @@ -38,16 +38,15 @@ "gulp-minify-css": "^0.4.4", "gulp-plumber": "^0.6.6", "gulp-rename": "^1.2.0", - "gulp-ruby-sass": "^0.7.1", - "gulp-scss-lint": "0.1.6", + "gulp-replace": "^0.5.2", + "gulp-sass": "^1.3.2", + "gulp-scss-lint": "0.1.7", "gulp-sourcemaps": "^1.3.0", "gulp-template": "^2.1.0", "gulp-uglify": "~1.1.0", "gulp-wrap": "^0.10.1", - "lazypipe": "^0.2.2", "readable-stream": "~1.0.33", "run-sequence": "^1.0.2", - "through2": "~0.6.3", - "gulp-replace": "^0.5.2" + "through2": "~0.6.3" } } diff --git a/scsslint.yml b/scsslint.yml index e8543b80..42a06f1c 100644 --- a/scsslint.yml +++ b/scsslint.yml @@ -1,8 +1,3 @@ -exclude: - - 'app/styles/components/markitup.scss' - - 'app/styles/bourbon/**' - - 'app/styles/vendor/**' - linters: BorderZero: enabled: true @@ -144,4 +139,3 @@ linters: Compass::*: enabled: false - From fcfb4bf7e004f5c5224b5bbfbf04c25fcd44dcab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 16 Feb 2015 11:18:04 +0100 Subject: [PATCH 076/207] Fixed watchers size --- app/partials/common/components/watchers.jade | 5 ++--- app/styles/components/watchers.scss | 13 +++++++++---- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/app/partials/common/components/watchers.jade b/app/partials/common/components/watchers.jade index 1361d34c..8d5dac17 100644 --- a/app/partials/common/components/watchers.jade +++ b/app/partials/common/components/watchers.jade @@ -11,8 +11,7 @@ <% if(watcher) { %> .watcher-single .watcher-avatar - span.avatar(title!="<%- watcher.full_name_display %>") - img(src!="<%- watcher.photo %>" alt!="<%- watcher.full_name_display %>") + img(src!="<%- watcher.photo %>" alt!="<%- watcher.full_name_display %>") .watcher-name span <%- watcher.full_name_display %> @@ -20,4 +19,4 @@ a.icon.icon-delete(data-watcher-id!="<%- watcher.id %>" href="" title="delete-watcher") <% }; %> <% } %> -<% }); %> \ No newline at end of file +<% }); %> diff --git a/app/styles/components/watchers.scss b/app/styles/components/watchers.scss index 0d0f0223..1c0a5770 100644 --- a/app/styles/components/watchers.scss +++ b/app/styles/components/watchers.scss @@ -25,7 +25,7 @@ border-bottom: 1px solid $gray-light; display: flex; justify-content: center; - padding: .5rem; + padding: .5rem 0 .3rem; vertical-align: middle; &:last-child { border: 0; @@ -37,6 +37,14 @@ } } } + .watcher-avatar { + align-items: center; + flex-basis: 3rem; + max-width: 3rem; + img { + width: 100%; + } + } .watcher-name { @extend %small; color: $grayer; @@ -44,9 +52,6 @@ margin-left: 1rem; position: relative; } - .watcher-avatar { - flex: 1 0 0; - } .icon-delete { opacity: 0; position: absolute; From 9076d3d39c77123e6251208e8f7774c7875539fd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 16 Feb 2015 11:20:06 +0100 Subject: [PATCH 077/207] Remove unused flexbox rule --- app/styles/components/watchers.scss | 1 - 1 file changed, 1 deletion(-) diff --git a/app/styles/components/watchers.scss b/app/styles/components/watchers.scss index 1c0a5770..bb37f04b 100644 --- a/app/styles/components/watchers.scss +++ b/app/styles/components/watchers.scss @@ -38,7 +38,6 @@ } } .watcher-avatar { - align-items: center; flex-basis: 3rem; max-width: 3rem; img { From 43c5075c0a55848cbe845e0a0ad56ed312774633 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 16 Feb 2015 11:31:37 +0100 Subject: [PATCH 078/207] Fixed related tasks layout on small resolution --- app/styles/modules/common/related-tasks.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/styles/modules/common/related-tasks.scss b/app/styles/modules/common/related-tasks.scss index d6617bac..13286580 100644 --- a/app/styles/modules/common/related-tasks.scss +++ b/app/styles/modules/common/related-tasks.scss @@ -53,11 +53,11 @@ flex-grow: 10; } .status { - flex-basis: 10%; + flex-basis: 100px; } .assigned-to { cursor: pointer; - flex-basis: 10%; + flex-basis: 150px; } } .related-task-create-form { From 818ed946f3e3b1cf3f0d3309ca4f03c7d396444c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 16 Feb 2015 12:01:39 +0100 Subject: [PATCH 079/207] Fix image max-width on US comments --- app/styles/modules/common/history.scss | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/app/styles/modules/common/history.scss b/app/styles/modules/common/history.scss index 1cfc957d..fb6d97d8 100644 --- a/app/styles/modules/common/history.scss +++ b/app/styles/modules/common/history.scss @@ -213,10 +213,10 @@ margin-bottom: .5rem; } .activity-user { - flex-basis: 50px; - flex-grow: 1; + flex-basis: 60px; + flex-shrink: 0; + margin-right: 1rem; img { - max-width: 70px; width: 100%; } } @@ -224,10 +224,9 @@ color: $green-taiga; margin-bottom: .5rem; } - .activity-content { - flex-basis: 150px; - flex-grow: 20; + flex-shrink: 0; + max-width: calc(100% - 80px); } .changes { background: $whitish; From 1ec53294d1b4f2ab7275935cffbe2ebffa2d74da Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 17 Feb 2015 08:37:37 +0100 Subject: [PATCH 080/207] Wiki summary flexboxed --- app/partials/wiki/wiki-summary.jade | 21 ++++++----- app/styles/modules/wiki/wiki-summary.scss | 45 +++++++++++------------ 2 files changed, 32 insertions(+), 34 deletions(-) diff --git a/app/partials/wiki/wiki-summary.jade b/app/partials/wiki/wiki-summary.jade index 68b2624d..7fb31db1 100644 --- a/app/partials/wiki/wiki-summary.jade +++ b/app/partials/wiki/wiki-summary.jade @@ -1,13 +1,14 @@ -ul - li - span.number <%- totalEditions %> - span.description times
edited - li - span.number <%- lastModifiedDate %> - span.description last
edit +div.wiki-times-edited + span.number <%- totalEditions %> + span.description times
edited - li.username-edition - figure.avatar - img(src!="<%- user.imgUrl %>" alt!="<%- user.name %>") +div.wiki-last-modified + span.number <%- lastModifiedDate %> + span.description last
edit + +div.wiki-username-edition + figure.avatar + img(src!="<%- user.imgUrl %>" alt!="<%- user.name %>") + div.wiki-user-modification span.description last modification span.username <%- user.name %> diff --git a/app/styles/modules/wiki/wiki-summary.scss b/app/styles/modules/wiki/wiki-summary.scss index 7d83451f..200f7621 100644 --- a/app/styles/modules/wiki/wiki-summary.scss +++ b/app/styles/modules/wiki/wiki-summary.scss @@ -1,31 +1,28 @@ .wiki-summary { - @include clearfix(); - figure { - float: left; - margin-right: .5rem; - vertical-align: sub; - width: 32px; - } - ul { - align-items: flex-start; + align-items: center; + justify-content: flex-start; + flex-wrap: wrap; + div { display: flex; - flex-direction: row; + justify-content: space-between; + margin-right: 1rem; + } + .number { + line-height: 2rem; + top: 0; + } + .wiki-user-modification { + display: flex; + flex-direction: column; justify-content: flex-start; } - .username-edition { - min-width: 240px; - span { - display: block; - float: none; - } - .username { - @extend %large; - color: $fresh-taiga; - white-space: nowrap; - } + figure { + margin-right: .3rem; + width: 32px; } - .button { - color: $white; - float: right; + .username { + @extend %large; + color: $fresh-taiga; + white-space: nowrap; } } From 3239b8757b438513c42900344e1c7f3f4c094a3c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 17 Feb 2015 09:35:31 +0100 Subject: [PATCH 081/207] Remove wiki edition ir pre or secondary click --- app/coffee/modules/wiki/main.coffee | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/wiki/main.coffee b/app/coffee/modules/wiki/main.coffee index 6ef71c78..5b1d75bb 100644 --- a/app/coffee/modules/wiki/main.coffee +++ b/app/coffee/modules/wiki/main.coffee @@ -245,8 +245,9 @@ EditableWikiContentDirective = ($window, $document, $repo, $confirm, $loading, $ # not the currentTarget target = angular.element(event.target) return if not isEditable() - return if target.is('a') + return if target.is('a', '.codehilite', 'pre') return if getSelectedText() + return if event.button == 2 if target.is('pre') prevPos = target.data("scroll-pos") target.data("scroll-pos", null) From 956b851db68e9678ddc09a491de883d14144b3f7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 17 Feb 2015 09:37:06 +0100 Subject: [PATCH 082/207] Fix scss lint --- app/styles/modules/wiki/wiki-summary.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/modules/wiki/wiki-summary.scss b/app/styles/modules/wiki/wiki-summary.scss index 200f7621..0328f1eb 100644 --- a/app/styles/modules/wiki/wiki-summary.scss +++ b/app/styles/modules/wiki/wiki-summary.scss @@ -1,7 +1,7 @@ .wiki-summary { align-items: center; - justify-content: flex-start; flex-wrap: wrap; + justify-content: flex-start; div { display: flex; justify-content: space-between; From 1cc3d34e1aff6a8c44118a8b81e93fa73d7b709b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Tue, 10 Feb 2015 13:08:01 +0100 Subject: [PATCH 083/207] Standardize title attributes for uss/tasks/issues --- app/partials/includes/components/taskboard-task.jade | 2 +- app/partials/includes/modules/issues-table.jade | 2 +- app/partials/kanban/kanban-task.jade | 2 +- app/partials/task/related-task-row.jade | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/app/partials/includes/components/taskboard-task.jade b/app/partials/includes/components/taskboard-task.jade index 0dd6bbdf..7460a74f 100644 --- a/app/partials/includes/components/taskboard-task.jade +++ b/app/partials/includes/components/taskboard-task.jade @@ -5,7 +5,7 @@ div.taskboard-task-inner p.taskboard-text a.task-assigned(href="", title="Assign task") span.task-num(tg-bo-ref="task.ref") - a.task-name(href="", title="See task details", ng-bind="task.subject", + a.task-name(href="", title="#{{ ::task.ref }} {{ ::task.subject }}", ng-bind="task.subject", tg-nav="project-tasks-detail:project=project.slug,ref=task.ref") a.icon.icon-edit(tg-check-permission="modify_task", href="", title="Edit task") diff --git a/app/partials/includes/modules/issues-table.jade b/app/partials/includes/modules/issues-table.jade index 68682860..0c75f311 100644 --- a/app/partials/includes/modules/issues-table.jade +++ b/app/partials/includes/modules/issues-table.jade @@ -12,7 +12,7 @@ section.issues-table.basic-table(ng-class="{empty: !issues.length}") div.level-field(tg-listitem-severity="issue") div.level-field(tg-listitem-priority="issue") div.subject - a(href="", tg-nav="project-issues-detail:project=project.slug,ref=issue.ref", title="{{ ::issue.subject }}") + a(href="", tg-nav="project-issues-detail:project=project.slug,ref=issue.ref", title="#{{ ::issue.ref }} {{ ::issue.subject }}") span(tg-bo-ref="issue.ref") span(ng-bind="issue.subject") diff --git a/app/partials/kanban/kanban-task.jade b/app/partials/kanban/kanban-task.jade index df075a13..68d2fd19 100644 --- a/app/partials/kanban/kanban-task.jade +++ b/app/partials/kanban/kanban-task.jade @@ -4,7 +4,7 @@ div.kanban-task-inner(ng-class="{'task-archived': us.isArchived}") div.task-text(ng-hide="us.isArchived") a.task-assigned(href="", title="Assign User Story") span.task-num(tg-bo-ref="us.ref") - a.task-name(href="", title="See user story detail", ng-bind="us.subject", + a.task-name(href="", title="#{{ ::us.ref }} {{ us.subject }}", ng-bind="us.subject", tg-nav="project-userstories-detail:project=project.slug,ref=us.ref") p.task-points(href="", title="Total Us points") diff --git a/app/partials/task/related-task-row.jade b/app/partials/task/related-task-row.jade index 9b708579..d384c9a0 100644 --- a/app/partials/task/related-task-row.jade +++ b/app/partials/task/related-task-row.jade @@ -1,7 +1,7 @@ div(class="tasks") div(class="task-name") span(class="icon icon-iocaine") - a(tg-nav="project-tasks-detail:project=project.slug,ref=task.ref" title!="<%- task.ref %> <%- task.subject %>" class="clickable") + a(tg-nav="project-tasks-detail:project=project.slug,ref=task.ref" title!="#<%- task.ref %> <%- task.subject %>" class="clickable") span #<%- task.ref %>  span <%- task.subject %> div(class="task-settings") From bf36e4329bead086bab1191f46c4fd4f4c27e856 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Feb 2015 15:43:41 +0100 Subject: [PATCH 084/207] speed up gulfile - add gulp-cache - replace gulp-ruby-sass by gulp-sass - convert gulpfile to js --- ...lite.github.scss => codehilite.github.css} | 0 gulpfile.coffee | 351 --------------- gulpfile.js | 409 ++++++++++++++++++ package.json | 11 +- scsslint.yml | 6 - 5 files changed, 414 insertions(+), 363 deletions(-) rename app/styles/vendor/{codehilite.github.scss => codehilite.github.css} (100%) delete mode 100644 gulpfile.coffee create mode 100644 gulpfile.js diff --git a/app/styles/vendor/codehilite.github.scss b/app/styles/vendor/codehilite.github.css similarity index 100% rename from app/styles/vendor/codehilite.github.scss rename to app/styles/vendor/codehilite.github.css diff --git a/gulpfile.coffee b/gulpfile.coffee deleted file mode 100644 index c4ae3ea8..00000000 --- a/gulpfile.coffee +++ /dev/null @@ -1,351 +0,0 @@ -gulp = require("gulp") -jade = require("gulp-jade") -coffee = require("gulp-coffee") -concat = require("gulp-concat") -uglify = require("gulp-uglify") -plumber = require("gulp-plumber") -wrap = require("gulp-wrap") -rename = require("gulp-rename") -flatten = require("gulp-flatten") -gulpif = require("gulp-if") -replace = require("gulp-replace") -sass = require("gulp-ruby-sass") -csslint = require("gulp-csslint") -minifyCSS = require("gulp-minify-css") -scsslint = require("gulp-scss-lint") -cache = require("gulp-cached") -jadeInheritance = require("gulp-jade-inheritance") -sourcemaps = require("gulp-sourcemaps") -insert = require("gulp-insert") -imagemin = require("gulp-imagemin") -autoprefixer = require("gulp-autoprefixer") -templateCache = require("gulp-angular-templatecache") -changed = require("gulp-changed") - -runSequence = require("run-sequence") -lazypipe = require("lazypipe") -del = require("del") - -mainSass = require("./main-sass").files - -paths = {} -paths.app = "app/" -paths.dist = "dist/" -paths.tmp = "tmp/" -paths.extras = "extras/" - -paths.jade = [ - "#{paths.app}**/*.jade", - "!#{paths.app}partial/includes/**", -] - -paths.htmlPartials = [ - "#{paths.tmp}partials/**/*.html", - "#{paths.tmp}plugins/**/*.html" -] - -paths.images = "#{paths.app}images/**/*" -paths.svg = "#{paths.app}svg/**/*" -paths.css = "#{paths.app}styles/vendor/*.css" -paths.locales = "#{paths.app}locales/**/*.json" - -paths.sass = [ - "#{paths.app}**/*.scss" - "!#{paths.app}/styles/bourbon/**/*.scss" - "!#{paths.app}/styles/dependencies/**/*.scss" - "!#{paths.app}/styles/extras/**/*.scss" -] - -paths.coffee = "#{paths.app}**/*.coffee" - -paths.js = [ - "#{paths.tmp}coffee/app.js", - "#{paths.tmp}coffee/*.js", - "#{paths.tmp}coffee/modules/controllerMixins.js", - "#{paths.tmp}coffee/modules/*.js", - "#{paths.tmp}coffee/modules/common/*.js", - "#{paths.tmp}coffee/modules/backlog/*.js", - "#{paths.tmp}coffee/modules/taskboard/*.js", - "#{paths.tmp}coffee/modules/kanban/*.js", - "#{paths.tmp}coffee/modules/issues/*.js", - "#{paths.tmp}coffee/modules/userstories/*.js", - "#{paths.tmp}coffee/modules/tasks/*.js", - "#{paths.tmp}coffee/modules/team/*.js", - "#{paths.tmp}coffee/modules/wiki/*.js", - "#{paths.tmp}coffee/modules/admin/*.js", - "#{paths.tmp}coffee/modules/projects/*.js", - "#{paths.tmp}coffee/modules/locales/*.js", - "#{paths.tmp}coffee/modules/base/*.js", - "#{paths.tmp}coffee/modules/resources/*.js", - "#{paths.tmp}coffee/modules/user-settings/*.js", - "#{paths.tmp}coffee/modules/integrations/*.js", - "#{paths.tmp}plugins/**/*.js" -] - -paths.libs = [ - "#{paths.app}vendor/jquery/dist/jquery.js", - "#{paths.app}vendor/lodash/dist/lodash.js", - "#{paths.app}vendor/emoticons/lib/emoticons.js", - "#{paths.app}vendor/underscore.string/lib/underscore.string.js", - "#{paths.app}vendor/angular/angular.js", - "#{paths.app}vendor/angular-route/angular-route.js", - "#{paths.app}vendor/angular-sanitize/angular-sanitize.js", - "#{paths.app}vendor/angular-animate/angular-animate.js", - "#{paths.app}vendor/i18next/i18next.js", - "#{paths.app}vendor/moment/min/moment-with-langs.js", - "#{paths.app}vendor/checksley/checksley.js", - "#{paths.app}vendor/pikaday/pikaday.js", - "#{paths.app}vendor/jquery-flot/jquery.flot.js", - "#{paths.app}vendor/jquery-flot/jquery.flot.pie.js", - "#{paths.app}vendor/jquery-flot/jquery.flot.time.js", - "#{paths.app}vendor/flot-axislabels/jquery.flot.axislabels.js", - "#{paths.app}vendor/flot.tooltip/js/jquery.flot.tooltip.js", - "#{paths.app}vendor/jquery-textcomplete/jquery.textcomplete.js", - "#{paths.app}vendor/markitup-1x/markitup/jquery.markitup.js", - "#{paths.app}vendor/malihu-custom-scrollbar-plugin/jquery.mCustomScrollbar.concat.min.js", - "#{paths.app}vendor/raven-js/dist/raven.js", - "#{paths.app}vendor/l.js/l.js", - "#{paths.app}js/jquery.ui.git-custom.js", - "#{paths.app}js/jquery-ui.drag-multiple-custom.js", - "#{paths.app}js/sha1-custom.js", -] - -isDeploy = process.argv[process.argv.length - 1] == "deploy" - -############################################################################ -# Layout/CSS Related tasks -############################################################################## - -gulp.task "jade", -> - gulp.src(paths.jade) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".html"})) - .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "jade-inheritance", -> - gulp.src(paths.jade) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".html"})) - .pipe(jadeInheritance({basedir: "./app/"})) - .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "copy-index", -> - gulp.src(paths.tmp + "index.html") - .pipe(gulp.dest(paths.dist)) - -gulp.task "template-cache", -> - gulp.src(paths.htmlPartials) - .pipe(templateCache({standalone: true})) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "jade-deploy", (cb) -> - runSequence("jade", "copy-index", "template-cache", cb) - -gulp.task "jade-watch", (cb) -> - runSequence("jade-inheritance", "copy-index", "template-cache", cb) - -############################################################################## -# CSS Related tasks -############################################################################## - -gulp.task "scss-lint", -> - gulp.src(paths.sass.concat("!#{paths.app}/styles/shame/**/*.scss")) - .pipe(cache("scsslint")) - .pipe(gulpif(!isDeploy, scsslint({config: "scsslint.yml"}))) - -gulp.task "sass-compile", ["scss-lint"], -> - gulp.src(paths.sass) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".css"})) - .pipe(insert.prepend('@import "dependencies";')) - .pipe(sass({ - "sourcemap=none": true, - loadPath: [ - "#{paths.app}styles/extras/" - ] - })) - .pipe(gulp.dest(paths.tmp)) - -csslintChannel = lazypipe() - .pipe(csslint, "csslintrc.json") - .pipe(csslint.reporter) - -gulp.task "css-lint-app", -> - gulp.src(mainSass.concat(["#{paths.tmp}plugins/**/*.css"])) - .pipe(cache("csslint")) - .pipe(gulpif(!isDeploy, csslintChannel())) - -gulp.task "css-join", ["css-lint-app"], -> - gulp.src(mainSass.concat(["#{paths.tmp}plugins/**/*.css"])) - .pipe(concat("app.css")) - .pipe(autoprefixer({ - cascade: false - })) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "css-app", (cb) -> - runSequence("sass-compile", "css-join", cb) - -gulp.task "css-vendor", -> - gulp.src(paths.css) - .pipe(concat("vendor.css")) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "styles", ["css-app", "css-vendor"], -> - _paths = [ - paths.tmp + "vendor.css", - paths.tmp + "app.css" - ] - - gulp.src(_paths) - .pipe(concat("main.css")) - .pipe(gulpif(isDeploy, minifyCSS({noAdvanced: true}))) - .pipe(gulp.dest(paths.dist + "styles/")) - -############################################################################## -# JS Related tasks -############################################################################## - -gulp.task "conf", -> - gulp.src(["conf/conf.example.json"]) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "app-loader", -> - gulp.src("app-loader/app-loader.coffee") - .pipe(replace("___VERSION___", (new Date()).getTime())) - .pipe(coffee()) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "locales", -> - gulp.src("app/locales/en/app.json") - .pipe(wrap("angular.module('taigaBase').value('localesEn', <%= contents %>);", {}, {parse: false})) - .pipe(rename("locales.en.js")) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "coffee", -> - gulp.src(paths.coffee) - .pipe(plumber()) - .pipe(changed(paths.tmp, {extension: ".js"})) - .pipe(coffee()) - .pipe(gulp.dest(paths.tmp)) - -gulp.task "plugins-js", -> - gulp.src("#{paths.app}plugins/**/*.js") - .pipe(gulp.dest(paths.tmp)) - -gulp.task "jslibs-watch", -> - gulp.src(paths.libs) - .pipe(plumber()) - .pipe(concat("libs.js")) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "jslibs-deploy", -> - gulp.src(paths.libs) - .pipe(plumber()) - .pipe(sourcemaps.init()) - .pipe(concat("libs.js")) - .pipe(uglify({mangle:false, preserveComments: false})) - .pipe(sourcemaps.write("./")) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "app-watch", ["coffee", "plugins-js", "conf", "locales", "app-loader"], -> - _paths = paths.js.concat("#{paths.tmp}locales.en.js") - - gulp.src(_paths) - .pipe(concat("app.js")) - .pipe(gulp.dest(paths.dist + "js/")) - -gulp.task "app-deploy", ["coffee", "plugins-js", "conf", "locales", "app-loader"], -> - _paths = paths.js.concat("#{paths.tmp}locales.en.js") - - gulp.src(_paths) - .pipe(sourcemaps.init()) - .pipe(concat("app.js")) - .pipe(uglify({mangle:false, preserveComments: false})) - .pipe(sourcemaps.write("./")) - .pipe(gulp.dest(paths.dist + "js/")) - -############################################################################## -# Common tasks -############################################################################## - -# SVG -gulp.task "copy-svg", -> - gulp.src("#{paths.app}/svg/**/*") - .pipe(gulp.dest("#{paths.dist}/svg/")) - -gulp.task "copy-fonts", -> - gulp.src("#{paths.app}/fonts/*") - .pipe(gulp.dest("#{paths.dist}/fonts/")) - -gulp.task "copy-images", -> - gulp.src("#{paths.app}/images/**/*") - .pipe(gulpif(isDeploy, imagemin({progressive: true}))) - .pipe(gulp.dest("#{paths.dist}/images/")) - - gulp.src("#{paths.app}/plugins/**/images/*") - .pipe(flatten()) - .pipe(gulp.dest("#{paths.dist}/images/")) - -gulp.task "copy-plugin-templates", -> - gulp.src("#{paths.app}/plugins/**/templates/**/*.html") - .pipe(gulp.dest("#{paths.dist}/plugins/")) - -gulp.task "copy-extras", -> - gulp.src("#{paths.extras}/*") - .pipe(gulp.dest("#{paths.dist}/")) - -gulp.task "copy", ["copy-fonts", "copy-images", "copy-plugin-templates", "copy-svg", "copy-extras"] - -gulp.task "express", -> - express = require("express") - app = express() - - app.use("/js", express.static("#{__dirname}/dist/js")) - app.use("/styles", express.static("#{__dirname}/dist/styles")) - app.use("/images", express.static("#{__dirname}/dist/images")) - app.use("/svg", express.static("#{__dirname}/dist/svg")) - app.use("/partials", express.static("#{__dirname}/dist/partials")) - app.use("/fonts", express.static("#{__dirname}/dist/fonts")) - app.use("/plugins", express.static("#{__dirname}/dist/plugins")) - - app.all "/*", (req, res, next) -> - # Just send the index.html for other files to support HTML5Mode - res.sendFile("index.html", {root: "#{__dirname}/dist/"}) - - app.listen(9001) - -# Rerun the task when a file changes -gulp.task "watch", -> - gulp.watch(paths.jade, ["jade-watch"]) - gulp.watch(paths.sass, ["styles"]) - gulp.watch(paths.svg, ["copy-svg"]) - gulp.watch(paths.coffee, ["app-watch"]) - gulp.watch(paths.js, ["jslibs-watch"]) - gulp.watch(paths.locales, ["app-watch"]) - gulp.watch(paths.images, ["copy-images"]) - gulp.watch(paths.fonts, ["copy-fonts"]) - -if isDeploy - del.sync(paths.tmp) - -gulp.task "deploy", [ - "copy", - "jade-deploy", - "app-deploy", - "jslibs-deploy", - "styles" -] - -# The default task (called when you run gulp from cli) -gulp.task "default", [ - "copy", - "styles", - "app-watch", - "jslibs-watch", - "jade-deploy", - "express", - "watch" -] diff --git a/gulpfile.js b/gulpfile.js new file mode 100644 index 00000000..252cb353 --- /dev/null +++ b/gulpfile.js @@ -0,0 +1,409 @@ +var gulp = require("gulp"), + jade = require("gulp-jade"), + coffee = require("gulp-coffee"), + concat = require("gulp-concat"), + uglify = require("gulp-uglify"), + plumber = require("gulp-plumber"), + wrap = require("gulp-wrap"), + rename = require("gulp-rename"), + flatten = require("gulp-flatten"), + gulpif = require("gulp-if"), + replace = require("gulp-replace"), + sass = require("gulp-sass"), + csslint = require("gulp-csslint"), + minifyCSS = require("gulp-minify-css"), + scsslint = require("gulp-scss-lint"), + cache = require("gulp-cache"), + cached = require("gulp-cached"), + jadeInheritance = require("gulp-jade-inheritance"), + sourcemaps = require("gulp-sourcemaps"), + insert = require("gulp-insert"), + autoprefixer = require("gulp-autoprefixer"), + templateCache = require("gulp-angular-templatecache"), + runSequence = require("run-sequence"), + del = require("del"); + +var mainSass = require("./main-sass").files; + +var paths = {}; +paths.app = "app/"; +paths.dist = "dist/"; +paths.tmp = "tmp/"; +paths.extras = "extras/"; + +paths.jade = [ + paths.app + "**/*.jade", + "!" + paths.app + "partial/includes/**", +]; + +paths.htmlPartials = [ + paths.tmp + "partials/**/*.html", + paths.tmp + "plugins/**/*.html" +]; + +paths.images = paths.app + "images/**/*"; +paths.svg = paths.app + "svg/**/*"; +paths.css = paths.app + "styles/vendor/*.css"; +paths.locales = paths.app + "locales/**/*.json"; + +paths.sass = [ + paths.app + "**/*.scss", + "!" + paths.app + "/styles/bourbon/**/*.scss", + "!" + paths.app + "/styles/dependencies/**/*.scss", + "!" + paths.app + "/styles/extras/**/*.scss" +]; + +paths.coffee = paths.app + "**/*.coffee"; + +paths.js = [ + paths.tmp + "coffee/app.js", + paths.tmp + "coffee/*.js", + paths.tmp + "coffee/modules/controllerMixins.js", + paths.tmp + "coffee/modules/*.js", + paths.tmp + "coffee/modules/common/*.js", + paths.tmp + "coffee/modules/backlog/*.js", + paths.tmp + "coffee/modules/taskboard/*.js", + paths.tmp + "coffee/modules/kanban/*.js", + paths.tmp + "coffee/modules/issues/*.js", + paths.tmp + "coffee/modules/userstories/*.js", + paths.tmp + "coffee/modules/tasks/*.js", + paths.tmp + "coffee/modules/team/*.js", + paths.tmp + "coffee/modules/wiki/*.js", + paths.tmp + "coffee/modules/admin/*.js", + paths.tmp + "coffee/modules/projects/*.js", + paths.tmp + "coffee/modules/locales/*.js", + paths.tmp + "coffee/modules/base/*.js", + paths.tmp + "coffee/modules/resources/*.js", + paths.tmp + "coffee/modules/user-settings/*.js", + paths.tmp + "coffee/modules/integrations/*.js", + paths.tmp + "plugins/**/*.js" +]; + +paths.libs = [ + paths.app + "vendor/jquery/dist/jquery.js", + paths.app + "vendor/lodash/dist/lodash.js", + paths.app + "vendor/emoticons/lib/emoticons.js", + paths.app + "vendor/underscore.string/lib/underscore.string.js", + paths.app + "vendor/angular/angular.js", + paths.app + "vendor/angular-route/angular-route.js", + paths.app + "vendor/angular-sanitize/angular-sanitize.js", + paths.app + "vendor/angular-animate/angular-animate.js", + paths.app + "vendor/i18next/i18next.js", + paths.app + "vendor/moment/min/moment-with-langs.js", + paths.app + "vendor/checksley/checksley.js", + paths.app + "vendor/pikaday/pikaday.js", + paths.app + "vendor/jquery-flot/jquery.flot.js", + paths.app + "vendor/jquery-flot/jquery.flot.pie.js", + paths.app + "vendor/jquery-flot/jquery.flot.time.js", + paths.app + "vendor/flot-axislabels/jquery.flot.axislabels.js", + paths.app + "vendor/flot.tooltip/js/jquery.flot.tooltip.js", + paths.app + "vendor/jquery-textcomplete/jquery.textcomplete.js", + paths.app + "vendor/markitup-1x/markitup/jquery.markitup.js", + paths.app + "vendor/malihu-custom-scrollbar-plugin/jquery.mCustomScrollbar.concat.min.js", + paths.app + "vendor/raven-js/dist/raven.js", + paths.app + "vendor/l.js/l.js", + paths.app + "js/jquery.ui.git-custom.js", + paths.app + "js/jquery-ui.drag-multiple-custom.js", + paths.app + "js/sha1-custom.js" +]; + +var isDeploy = process.argv[process.argv.length - 1] == "deploy"; + +/* +############################################################################ +# Layout/CSS Related tasks +############################################################################## +*/ + +gulp.task("jade", function() { + return gulp.src(paths.jade) + .pipe(plumber()) + .pipe(cached("jade")) + .pipe(cache(jade({pretty: true, locals:{v:(new Date()).getTime()}}))) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("jade-inheritance", function() { + return gulp.src(paths.jade) + .pipe(plumber()) + .pipe(cached('jade')) + .pipe(jadeInheritance({basedir: "./app/"})) + .pipe(cache(jade({pretty: true, locals:{v:(new Date()).getTime()}}))) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("copy-index", function() { + return gulp.src(paths.tmp + "index.html") + .pipe(gulp.dest(paths.dist)); +}); + +gulp.task("template-cache", function() { + return gulp.src(paths.htmlPartials) + .pipe(templateCache({standalone: true})) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("jade-deploy", function(cb) { + return runSequence("jade", "copy-index", "template-cache", cb); +}); + +gulp.task("jade-watch", function(cb) { + return runSequence("jade-inheritance", "copy-index", "template-cache", cb); +}); + +/* +############################################################################## +# CSS Related tasks +############################################################################## +*/ + +gulp.task("scss-lint", [], function() { + var ignore = [ + "!" + paths.app + "/styles/shame/**/*.scss", + "!" + paths.app + "/styles/components/markitup.scss" + ]; + + return gulp.src(paths.sass.concat(ignore)) + .pipe(gulpif(!isDeploy, cache(scsslint({endless: true, sync: true, config: "scsslint.yml"}), { + success: function(scsslintFile) { + return scsslintFile.scsslint.success; + }, + value: function(scsslintFile) { + return { + scsslint: scsslintFile.scsslint + }; + } + }))) +}); + +gulp.task("sass-compile", ["scss-lint"], function() { + return gulp.src(paths.sass) + .pipe(plumber()) + .pipe(insert.prepend('@import "dependencies";')) + .pipe(cache(sass({ + includePaths: [ + paths.app + "styles/extras/" + ] + }))) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("css-lint-app", function() { + return gulp.src(mainSass.concat([paths.tmp + "plugins/**/*.css"])) + .pipe(gulpif(!isDeploy, cache(csslint("csslintrc.json"), { + success: function(csslintFile) { + return csslintFile.csslint.success; + }, + value: function(csslintFile) { + return { + csslint: csslintFile.csslint + }; + } + }))) + .pipe(csslint.reporter()); +}); + +gulp.task("css-join", ["css-lint-app"], function() { + return gulp.src(mainSass.concat([paths.tmp + "plugins/**/*.css"])) + .pipe(concat("app.css")) + .pipe(autoprefixer({ + cascade: false + })) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("css-app", function(cb) { + return runSequence("sass-compile", "css-join", cb); +}); + +gulp.task("css-vendor", function() { + return gulp.src(paths.css) + .pipe(concat("vendor.css")) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("styles", ["css-app", "css-vendor"], function() { + var _paths = [ + paths.tmp + "vendor.css", + paths.tmp + "app.css" + ]; + + return gulp.src(_paths) + .pipe(concat("main.css")) + .pipe(gulpif(isDeploy, minifyCSS({noAdvanced: true}))) + .pipe(gulp.dest(paths.dist + "styles/")) +}); + +/* +############################################################################## +# JS Related tasks +############################################################################## +*/ +gulp.task("conf", function() { + return gulp.src(["conf/conf.example.json"]) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("app-loader", function() { + return gulp.src("app-loader/app-loader.coffee") + .pipe(replace("___VERSION___", (new Date()).getTime())) + .pipe(coffee()) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("locales", function() { + return gulp.src("app/locales/en/app.json") + .pipe(wrap("angular.module('taigaBase').value('localesEn', <%= contents %>);", {}, {parse: false})) + .pipe(rename("locales.en.js")) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("coffee", function() { + return gulp.src(paths.coffee) + .pipe(plumber()) + .pipe(cache(coffee())) + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("plugins-js", function() { + return gulp.src(paths.app + "plugins/**/*.js") + .pipe(gulp.dest(paths.tmp)); +}); + +gulp.task("jslibs-watch", function() { + return gulp.src(paths.libs) + .pipe(plumber()) + .pipe(concat("libs.js")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("jslibs-deploy", function() { + return gulp.src(paths.libs) + .pipe(plumber()) + .pipe(sourcemaps.init()) + .pipe(concat("libs.js")) + .pipe(uglify({mangle:false, preserveComments: false})) + .pipe(sourcemaps.write("./")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("app-watch", ["coffee", "plugins-js", "conf", "locales", "app-loader"], function() { + var _paths = paths.js.concat(paths.tmp + "locales.en.js") + + return gulp.src(_paths) + .pipe(concat("app.js")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +gulp.task("app-deploy", ["coffee", "plugins-js", "conf", "locales", "app-loader"], function() { + var _paths = paths.js.concat(paths.tmp + "locales.en.js") + + return gulp.src(_paths) + .pipe(sourcemaps.init()) + .pipe(concat("app.js")) + .pipe(uglify({mangle:false, preserveComments: false})) + .pipe(sourcemaps.write("./")) + .pipe(gulp.dest(paths.dist + "js/")); +}); + +/* +############################################################################## +# Common tasks +############################################################################## +*/ +gulp.task("clear", function(done) { + del.sync(paths.tmp); + + return cache.clearAll(done); +}); + +//SVG +gulp.task("copy-svg", function() { + return gulp.src(paths.app + "/svg/**/*") + .pipe(gulp.dest(paths.dist + "/svg/")); +}); + +gulp.task("copy-fonts", function() { + return gulp.src(paths.app + "/fonts/*") + .pipe(gulp.dest(paths.dist + "/fonts/")); +}); + +gulp.task("copy-images", function() { + var imageMin = gulp.src(paths.app + "/images/**/*"); + + if (isDeploy) { + //require imagemin is very slow + var imagemin = require("gulp-imagemin"); + imageMin.pipe(imagemin({progressive: true})) + } + + imageMin.pipe(gulp.dest(paths.dist + "/images/")) + + return gulp.src(paths.app + "/plugins/**/images/*") + .pipe(flatten()) + .pipe(gulp.dest(paths.dist + "/images/")); +}); + +gulp.task("copy-plugin-templates", function() { + return gulp.src(paths.app + "/plugins/**/templates/**/*.html") + .pipe(gulp.dest(paths.dist + "/plugins/")); +}); + +gulp.task("copy-extras", function() { + return gulp.src(paths.extras + "/*") + .pipe(gulp.dest(paths.dist + "/")); +}); + +gulp.task("copy", ["copy-fonts", "copy-images", "copy-plugin-templates", "copy-svg", "copy-extras"]); + +gulp.task("express", function() { + var express = require("express"); + var app = express(); + + app.use("/js", express.static(__dirname + "/dist/js")); + app.use("/styles", express.static(__dirname + "/dist/styles")); + app.use("/images", express.static(__dirname + "/dist/images")); + app.use("/svg", express.static(__dirname + "/dist/svg")); + app.use("/partials", express.static(__dirname + "/dist/partials")); + app.use("/fonts", express.static(__dirname + "/dist/fonts")); + app.use("/plugins", express.static(__dirname + "/dist/plugins")); + + app.all("/*", function(req, res, next) { + //Just send the index.html for other files to support HTML5Mode + res.sendFile("index.html", {root: __dirname + "/dist/"}); + }); + + app.listen(9001); +}); + +//Rerun the task when a file changes +gulp.task("watch", function() { + gulp.watch(paths.jade, ["jade-watch"]); + gulp.watch(paths.sass, ["styles"]); + gulp.watch(paths.svg, ["copy-svg"]); + gulp.watch(paths.coffee, ["app-watch"]); + gulp.watch(paths.libs, ["jslibs-watch"]); + gulp.watch(paths.locales, ["app-watch"]); + gulp.watch(paths.images, ["copy-images"]); + gulp.watch(paths.fonts, ["copy-fonts"]); +}); + +gulp.task("deploy", function(cb) { + runSequence("clear", [ + "copy", + "jade-deploy", + "app-deploy", + "jslibs-deploy", + "styles" + ], cb); +}); +//The default task (called when you run gulp from cli) +gulp.task("default", [ + "copy", + "styles", + "app-watch", + "jslibs-watch", + "jade-deploy", + "express", + "watch" +]); diff --git a/package.json b/package.json index c5b6d869..a1f81bd5 100644 --- a/package.json +++ b/package.json @@ -23,8 +23,8 @@ "gulp": "^3.8.10", "gulp-angular-templatecache": "^1.5.0", "gulp-autoprefixer": "^2.1.0", + "gulp-cache": "^0.2.4", "gulp-cached": "1.0.2", - "gulp-changed": "^1.1.1", "gulp-coffee": "^2.3.1", "gulp-coffeelint": "~0.4.0", "gulp-concat": "^2.4.3", @@ -38,16 +38,15 @@ "gulp-minify-css": "^0.4.4", "gulp-plumber": "^0.6.6", "gulp-rename": "^1.2.0", - "gulp-ruby-sass": "^0.7.1", - "gulp-scss-lint": "0.1.6", + "gulp-replace": "^0.5.2", + "gulp-sass": "^1.3.2", + "gulp-scss-lint": "0.1.7", "gulp-sourcemaps": "^1.3.0", "gulp-template": "^2.1.0", "gulp-uglify": "~1.1.0", "gulp-wrap": "^0.10.1", - "lazypipe": "^0.2.2", "readable-stream": "~1.0.33", "run-sequence": "^1.0.2", - "through2": "~0.6.3", - "gulp-replace": "^0.5.2" + "through2": "~0.6.3" } } diff --git a/scsslint.yml b/scsslint.yml index e8543b80..42a06f1c 100644 --- a/scsslint.yml +++ b/scsslint.yml @@ -1,8 +1,3 @@ -exclude: - - 'app/styles/components/markitup.scss' - - 'app/styles/bourbon/**' - - 'app/styles/vendor/**' - linters: BorderZero: enabled: true @@ -144,4 +139,3 @@ linters: Compass::*: enabled: false - From 99aa3a195155e01cd6fc458b73eb02e08f8f6271 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 16 Feb 2015 11:31:37 +0100 Subject: [PATCH 085/207] Fixed related tasks layout on small resolution --- app/styles/modules/common/related-tasks.scss | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/styles/modules/common/related-tasks.scss b/app/styles/modules/common/related-tasks.scss index d6617bac..13286580 100644 --- a/app/styles/modules/common/related-tasks.scss +++ b/app/styles/modules/common/related-tasks.scss @@ -53,11 +53,11 @@ flex-grow: 10; } .status { - flex-basis: 10%; + flex-basis: 100px; } .assigned-to { cursor: pointer; - flex-basis: 10%; + flex-basis: 150px; } } .related-task-create-form { From a9ceffe041ed6399ca46b2671b8dc60ed8c1fdf3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 17 Feb 2015 13:25:34 +0100 Subject: [PATCH 086/207] Add left padding in all watchers --- app/styles/components/watchers.scss | 1 + 1 file changed, 1 insertion(+) diff --git a/app/styles/components/watchers.scss b/app/styles/components/watchers.scss index bb37f04b..5c456568 100644 --- a/app/styles/components/watchers.scss +++ b/app/styles/components/watchers.scss @@ -40,6 +40,7 @@ .watcher-avatar { flex-basis: 3rem; max-width: 3rem; + padding-left: .3rem; img { width: 100%; } From c83cc76be82d584b47de34fb4e0ba1a6816af33a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 17 Feb 2015 14:35:26 +0100 Subject: [PATCH 087/207] Fix bug in chrome caused by a nonsense reason --- app/coffee/modules/wiki/main.coffee | 21 ++++++--------------- app/styles/components/wysiwyg.scss | 7 ++++++- 2 files changed, 12 insertions(+), 16 deletions(-) diff --git a/app/coffee/modules/wiki/main.coffee b/app/coffee/modules/wiki/main.coffee index 5b1d75bb..6a84e194 100644 --- a/app/coffee/modules/wiki/main.coffee +++ b/app/coffee/modules/wiki/main.coffee @@ -235,24 +235,15 @@ EditableWikiContentDirective = ($window, $document, $repo, $confirm, $loading, $ $loading.finish($el.find('.save-container')) $el.on "mousedown", ".view-wiki-content", (event) -> - # Prepare the scroll movement detection - target = angular.element(event.target) - if target.is('pre') - target.data("scroll-pos", target[0].scrollLeft) - - $el.on "mouseup", ".view-wiki-content", (event) -> - # We want to dettect the a inside the div so we use the target and - # not the currentTarget target = angular.element(event.target) return if not isEditable() - return if target.is('a', '.codehilite', 'pre') - return if getSelectedText() return if event.button == 2 - if target.is('pre') - prevPos = target.data("scroll-pos") - target.data("scroll-pos", null) - if prevPos != target[0].scrollLeft - return + + $el.on "mouseup", ".view-wiki-content", (event) -> + target = angular.element(event.target) + return if getSelectedText() + return if target.is('a') + return if target.is('pre') switchToEditMode() diff --git a/app/styles/components/wysiwyg.scss b/app/styles/components/wysiwyg.scss index 45906f7c..5e906637 100644 --- a/app/styles/components/wysiwyg.scss +++ b/app/styles/components/wysiwyg.scss @@ -48,13 +48,18 @@ line-height: 1.4rem; margin-bottom: 1rem; } + .codehilite { + overflow: auto; + } pre, code { @extend %small; - background: $whitish; + background: lighten($grayer, 10%); + color: $whitish; direction: ltr; font-family: 'courier new', 'monospace'; margin-bottom: 1rem; + overflow: auto; unicode-bidi: embed; white-space: pre; } From 2a682057ac069db694108ba969616ae67b343128 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Tue, 10 Feb 2015 15:39:38 +0100 Subject: [PATCH 088/207] Refactoring estimation points selector --- app/coffee/modules/backlog/main.coffee | 176 +++------ app/coffee/modules/common/estimation.coffee | 341 ++++++++---------- .../estimation/us-estimation-total.jade | 5 + .../includes/components/backlog-row.jade | 2 - .../modules/lightbox-us-create-edit.jade | 2 +- app/styles/modules/backlog/backlog-table.scss | 2 +- 6 files changed, 213 insertions(+), 315 deletions(-) create mode 100644 app/partials/common/estimation/us-estimation-total.jade diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index c76c736f..681e1ddb 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -733,7 +733,6 @@ UsRolePointsSelectorDirective = ($rootscope, $template) -> $el.on "click", ".role", (event) -> event.preventDefault() event.stopPropagation() - target = angular.element(event.currentTarget) rolScope = target.scope() $rootscope.$broadcast("uspoints:select", target.data("role-id"), target.text()) @@ -746,170 +745,107 @@ UsRolePointsSelectorDirective = ($rootscope, $template) -> module.directive("tgUsRolePointsSelector", ["$rootScope", "$tgTemplate", UsRolePointsSelectorDirective]) -UsPointsDirective = ($repo, $tgTemplate) -> +UsPointsDirective = ($tgEstimationsService, $repo, $tgTemplate) -> rolesTemplate = $tgTemplate.get("common/estimation/us-points-roles-popover.html", true) - pointsTemplate = $tgTemplate.get("common/estimation/us-estimation-points.html", true) link = ($scope, $el, $attrs) -> $ctrl = $el.controller() - - us = $scope.$eval($attrs.tgBacklogUsPoints) - updatingSelectedRoleId = null selectedRoleId = null - numberOfRoles = _.size(us.points) + filteringRoleId = null + estimationProcess = null - # Preselect the role if we have only one - if numberOfRoles == 1 - selectedRoleId = _.keys(us.points)[0] + $scope.$on "uspoints:select", (ctx, roleId, roleName) -> + us = $scope.$eval($attrs.tgBacklogUsPoints) + selectedRoleId = roleId + estimationProcess.render() - roles = [] - updatePointsRoles = -> - roles = _.map computableRoles, (role) -> - pointId = us.points[role.id] - pointObj = $scope.pointsById[pointId] + $scope.$on "uspoints:clear-selection", (ctx) -> + us = $scope.$eval($attrs.tgBacklogUsPoints) + selectedRoleId = null + estimationProcess.render() - role = _.clone(role, true) - role.points = if pointObj.value? then pointObj.value else "?" - return role + $scope.$watch $attrs.tgBacklogUsPoints, (us) -> + if us + estimationProcess = $tgEstimationsService.create($el, us, $scope.project) - computableRoles = _.filter($scope.project.roles, "computable") - updatePointsRoles() + # Update roles + roles = estimationProcess.calculateRoles() + if roles.length == 0 + $el.find(".icon-arrow-bottom").remove() + $el.find("a.us-points").addClass("not-clickable") - if roles.length == 0 - $el.find(".icon-arrow-bottom").remove() - $el.find("a.us-points").addClass("not-clickable") + else if roles.length == 1 + # Preselect the role if we have only one + selectedRoleId = _.keys(us.points)[0] - renderPointsSelector = (us, roleId) -> - # Prepare data for rendering - points = _.map $scope.project.points, (point) -> - point = _.clone(point, true) - point.selected = if us.points[roleId] == point.id then false else true - return point + if estimationProcess.isEditable + bindClickElements() - html = pointsTemplate({"points": points, "roleId": roleId}) + estimationProcess.onSelectedPointForRole = (roleId, pointId) -> + @save(roleId, pointId).then -> + $ctrl.loadProjectStats() - # Remove any prevous state - $el.find(".popover").popover().close() - $el.find(".pop-points-open").remove() + estimationProcess.render = () -> + totalPoints = @calculateTotalPoints() + if not selectedRoleId? or roles.length == 1 + text = totalPoints + title = totalPoints + else + pointId = @us.points[selectedRoleId] + pointObj = @pointsById[pointId] + text = "#{pointObj.name} / #{totalPoints}" + title = "#{pointObj.name} / #{totalPoints}" - # Render into DOM and show the new created element - $el.append(html) + ctx = { + totalPoints: totalPoints + roles: @calculateRoles() + editable: @isEditable + text: text + title: title + } + mainTemplate = "common/estimation/us-estimation-total.html" + template = $tgTemplate.get(mainTemplate, true) + html = template(ctx) + @$el.html(html) - # If not showing role selection let's move to the left - if not $el.find(".pop-role:visible").css("left")? - $el.find(".pop-points-open").css("left", "110px") - - $el.find(".pop-points-open").popover().open() - - renderRolesSelector = (us) -> - updatePointsRoles() + estimationProcess.render() + renderRolesSelector = () -> + roles = estimationProcess.calculateRoles() html = rolesTemplate({"roles": roles}) - # Render into DOM and show the new created element $el.append(html) $el.find(".pop-role").popover().open(() -> $(this).remove()) - renderPoints = (us, roleId) -> - dom = $el.find("a > span.points-value") - - if roleId == null or numberOfRoles == 1 - totalPoints = if us.total_points? then us.total_points else "?" - dom.text(totalPoints) - dom.parent().prop("title", totalPoints) - else - pointId = us.points[roleId] - pointObj = $scope.pointsById[pointId] - dom.html("#{pointObj.name} / #{us.total_points}") - dom.parent().prop("title", "#{pointObj.name} / #{us.total_points}") - - calculateTotalPoints = -> - values = _.map(us.points, (v, k) -> $scope.pointsById[v].value) - values = _.filter(values, (num) -> num?) - - if values.length == 0 - return "?" - - return _.reduce(values, (acc, num) -> acc + num) - - $scope.$watch $attrs.tgBacklogUsPoints, (us) -> - renderPoints(us, selectedRoleId) if us - - $scope.$on "uspoints:select", (ctx, roleId, roleName) -> - us = $scope.$eval($attrs.tgBacklogUsPoints) - renderPoints(us, roleId) - selectedRoleId = roleId - - $scope.$on "uspoints:clear-selection", (ctx) -> - us = $scope.$eval($attrs.tgBacklogUsPoints) - renderPoints(us, null) - selectedRoleId = null - - if roles.length > 0 + bindClickElements = () -> $el.on "click", "a.us-points span", (event) -> event.preventDefault() event.stopPropagation() - us = $scope.$eval($attrs.tgBacklogUsPoints) updatingSelectedRoleId = selectedRoleId - if selectedRoleId? - renderPointsSelector(us, selectedRoleId) + estimationProcess.renderPointsSelector(selectedRoleId) else - renderRolesSelector(us) + renderRolesSelector() $el.on "click", ".role", (event) -> event.preventDefault() event.stopPropagation() target = angular.element(event.currentTarget) - us = $scope.$eval($attrs.tgBacklogUsPoints) - updatingSelectedRoleId = target.data("role-id") - popRolesDom = $el.find(".pop-role") popRolesDom.find("a").removeClass("active") popRolesDom.find("a[data-role-id='#{updatingSelectedRoleId}']").addClass("active") - - renderPointsSelector(us, updatingSelectedRoleId) - - $el.on "click", ".point", (event) -> - event.preventDefault() - event.stopPropagation() - - target = angular.element(event.currentTarget) - $el.find(".pop-points-open").hide() - $el.find(".pop-role").hide() - - us = $scope.$eval($attrs.tgBacklogUsPoints) - - points = _.clone(us.points, true) - points[updatingSelectedRoleId] = target.data("point-id") - - $scope.$apply -> - us.points = points - us.total_points = calculateTotalPoints(us) - - renderPoints(us, selectedRoleId) - - $repo.save(us).then -> - # Little Hack for refresh. - $repo.refresh(us).then -> - $ctrl.loadProjectStats() - - bindOnce $scope, "project", (project) -> - # If the user has not enough permissions the click events are unbinded - if project.my_permissions.indexOf("modify_us") == -1 - $el.unbind("click") - $el.find("a").addClass("not-clickable") + estimationProcess.renderPointsSelector(updatingSelectedRoleId) $scope.$on "$destroy", -> $el.off() return {link: link} -module.directive("tgBacklogUsPoints", ["$tgRepo", "$tgTemplate", UsPointsDirective]) +module.directive("tgBacklogUsPoints", ["$tgEstimationsService", "$tgRepo", "$tgTemplate", UsPointsDirective]) ############################################################################# ## Burndown graph directive diff --git a/app/coffee/modules/common/estimation.coffee b/app/coffee/modules/common/estimation.coffee index 655d3daa..3b03a587 100644 --- a/app/coffee/modules/common/estimation.coffee +++ b/app/coffee/modules/common/estimation.coffee @@ -20,6 +20,7 @@ ### taiga = @.taiga +groupBy = @.taiga.groupBy module = angular.module("taigaCommon") @@ -27,7 +28,53 @@ module = angular.module("taigaCommon") ## User story estimation directive (for Lightboxes) ############################################################################# -LbUsEstimationDirective = ($rootScope, $repo, $confirm, $template) -> +LbUsEstimationDirective = ($tgEstimationsService, $rootScope, $repo, $confirm, $template) -> + # Display the points of a US and you can edit it. + # + # Example: + # tg-lb-us-estimation-progress-bar(ng-model="us") + # + # Requirements: + # - Us object (ng-model) + # - scope.project object + + link = ($scope, $el, $attrs, $model) -> + $scope.$watch $attrs.ngModel, (us) -> + if us + estimationProcess = $tgEstimationsService.create($el, us, $scope.project) + estimationProcess.onSelectedPointForRole = (roleId, pointId) -> + $scope.$apply -> + $model.$setViewValue(us) + + estimationProcess.render = () -> + ctx = { + totalPoints: @calculateTotalPoints() + roles: @calculateRoles() + editable: @isEditable + } + mainTemplate = "common/estimation/us-estimation-points-per-role.html" + template = $template.get(mainTemplate, true) + html = template(ctx) + @$el.html(html) + + estimationProcess.render() + $scope.$on "$destroy", -> + $el.off() + + return { + link: link + restrict: "EA" + require: "ngModel" + } + +module.directive("tgLbUsEstimation", ["$tgEstimationsService", "$rootScope", "$tgRepo", "$tgConfirm", "$tgTemplate", LbUsEstimationDirective]) + + +############################################################################# +## User story estimation directive +############################################################################# + +UsEstimationDirective = ($tgEstimationsService, $rootScope, $repo, $confirm, $qqueue, $template) -> # Display the points of a US and you can edit it. # # Example: @@ -37,91 +84,26 @@ LbUsEstimationDirective = ($rootScope, $repo, $confirm, $template) -> # - Us object (ng-model) # - scope.project object - mainTemplate = $template.get("common/estimation/us-estimation-points-per-role.html", true) - pointsTemplate = $template.get("common/estimation/us-estimation-points.html", true) - link = ($scope, $el, $attrs, $model) -> - render = (points) -> - totalPoints = calculateTotalPoints(points) or 0 - computableRoles = _.filter($scope.project.roles, "computable") + $scope.$watch $attrs.ngModel, (us) -> + if us + estimationProcess = $tgEstimationsService.create($el, us, $scope.project) + estimationProcess.onSelectedPointForRole = (roleId, pointId) -> + @save(roleId, pointId).then -> + $rootScope.$broadcast("history:reload") - roles = _.map computableRoles, (role) -> - pointId = points[role.id] - pointObj = $scope.pointsById[pointId] + estimationProcess.render = () -> + ctx = { + totalPoints: @calculateTotalPoints() + roles: @calculateRoles() + editable: @isEditable + } + mainTemplate = "common/estimation/us-estimation-points-per-role.html" + template = $template.get(mainTemplate, true) + html = template(ctx) + @$el.html(html) - role = _.clone(role, true) - role.points = if pointObj? and pointObj.name? then pointObj.name else "?" - return role - - ctx = { - totalPoints: totalPoints - roles: roles - editable: true - } - html = mainTemplate(ctx) - $el.html(html) - - renderPoints = (target, usPoints, roleId) -> - points = _.map $scope.project.points, (point) -> - point = _.clone(point, true) - point.selected = if usPoints[roleId] == point.id then false else true - return point - - html = pointsTemplate({"points": points, roleId: roleId}) - - # Remove any prevous state - $el.find(".popover").popover().close() - $el.find(".pop-points-open").remove() - - # If not showing role selection let's move to the left - if not $el.find(".pop-role:visible").css("left")? - $el.find(".pop-points-open").css("left", "110px") - - $el.find(".pop-points-open").remove() - - # Render into DOM and show the new created element - $el.find(target).append(html) - - $el.find(".pop-points-open").popover().open(-> $(this).removeClass("active")) - $el.find(".pop-points-open").show() - - calculateTotalPoints = (points) -> - values = _.map(points, (v, k) -> $scope.pointsById[v]?.value or 0) - if values.length == 0 - return "0" - return _.reduce(values, (acc, num) -> acc + num) - - $el.on "click", ".total.clickable", (event) -> - event.preventDefault() - event.stopPropagation() - - target = angular.element(event.currentTarget) - roleId = target.data("role-id") - - points = $model.$modelValue - renderPoints(target, points, roleId) - - target.siblings().removeClass('active') - target.addClass('active') - - $el.on "click", ".point", (event) -> - event.preventDefault() - event.stopPropagation() - - target = angular.element(event.currentTarget) - roleId = target.data("role-id") - pointId = target.data("point-id") - - $el.find(".popover").popover().close() - - points = _.clone($model.$modelValue, true) - points[roleId] = pointId - - $scope.$apply -> - $model.$setViewValue(points) - - $scope.$watch $attrs.ngModel, (points) -> - render(points) if points + estimationProcess.render() $scope.$on "$destroy", -> $el.off() @@ -132,81 +114,46 @@ LbUsEstimationDirective = ($rootScope, $repo, $confirm, $template) -> require: "ngModel" } -module.directive("tgLbUsEstimation", ["$rootScope", "$tgRepo", "$tgConfirm", "$tgTemplate", LbUsEstimationDirective]) +module.directive("tgUsEstimation", ["$tgEstimationsService", "$rootScope", "$tgRepo", "$tgConfirm", "$tgQqueue", "$tgTemplate", + UsEstimationDirective]) ############################################################################# -## User story estimation directive +## Estimations service ############################################################################# -UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> - # Display the points of a US and you can edit it. - # - # Example: - # tg-us-estimation-progress-bar(ng-model="us") - # - # Requirements: - # - Us object (ng-model) - # - scope.project object - - mainTemplate = $template.get("common/estimation/us-estimation-points-per-role.html", true) +EstimationsService = ($template, $qqueue, $repo, $confirm, $q) -> pointsTemplate = $template.get("common/estimation/us-estimation-points.html", true) - link = ($scope, $el, $attrs, $model) -> - isEditable = -> - return $scope.project.my_permissions.indexOf("modify_us") != -1 + class EstimationProcess + constructor: (@$el, @us, @project) -> + @isEditable = @project.my_permissions.indexOf("modify_us") != -1 + @roles = @project.roles + @points = @project.points + @pointsById = groupBy(@points, (x) -> x.id) + @onSelectedPointForRole = (roleId, pointId) -> + @render = () -> - render = (us) -> - totalPoints = calculateTotalPoints(us.points) or "?" - computableRoles = _.filter($scope.project.roles, "computable") + save: (roleId, pointId) -> + deferred = $q.defer() + $qqueue.add () => + onSuccess = => + deferred.resolve() + $confirm.notify("success") - roles = _.map computableRoles, (role) -> - pointId = us.points[role.id] - pointObj = $scope.pointsById[pointId] + onError = => + $confirm.notify("error") + @us.revert() + @render() + deferred.reject() - role = _.clone(role, true) - role.points = if pointObj? and pointObj.name? then pointObj.name else "?" - return role + $repo.save(@us).then(onSuccess, onError) - ctx = { - totalPoints: totalPoints - roles: roles - editable: isEditable() - } - html = mainTemplate(ctx) - $el.html(html) + return deferred.promise - renderPoints = (target, us, roleId) -> - points = _.map $scope.project.points, (point) -> - point = _.clone(point, true) - point.selected = if us.points[roleId] == point.id then false else true - return point + calculateTotalPoints: () -> + values = _.map(@us.points, (v, k) => @pointsById[v]?.value) - html = pointsTemplate({"points": points, roleId: roleId}) - - # Remove any prevous state - $el.find(".popover").popover().close() - $el.find(".pop-points-open").remove() - - # If not showing role selection let's move to the left - if not $el.find(".pop-role:visible").css("left")? - $el.find(".pop-points-open").css("left", "110px") - - $el.find(".pop-points-open").remove() - - # Render into DOM and show the new created element - $el.find(target).append(html) - - $el.find(".pop-points-open").popover().open -> - $(this) - .removeClass("active") - .closest("li").removeClass("active") - - - $el.find(".pop-points-open").show() - - calculateTotalPoints = (points) -> - values = _.map(points, (v, k) -> $scope.pointsById[v]?.value) if values.length == 0 return "0" @@ -216,62 +163,74 @@ UsEstimationDirective = ($rootScope, $repo, $confirm, $qqueue, $template) -> return _.reduce(notNullValues, (acc, num) -> acc + num) - save = $qqueue.bindAdd (roleId, pointId) => - $el.find(".popover").popover().close() + calculateRoles: () -> + computableRoles = _.filter(@project.roles, "computable") + roles = _.map computableRoles, (role) => + pointId = @us.points[role.id] + pointObj = @pointsById[pointId] + role = _.clone(role, true) + role.points = if pointObj? and pointObj.name? then pointObj.name else "?" + return role - points = _.clone($model.$modelValue.points, true) - points[roleId] = pointId + return roles - us = $model.$modelValue.clone() - us.points = points - $model.$setViewValue(us) + bindClickEvents: => + @$el.on "click", ".total.clickable", (event) => + event.preventDefault() + event.stopPropagation() + target = angular.element(event.currentTarget) + roleId = target.data("role-id") + @renderPointsSelector(roleId, target) + target.siblings().removeClass('active') + target.addClass('active') - onSuccess = -> - $confirm.notify("success") - $rootScope.$broadcast("history:reload") - onError = -> - $confirm.notify("error") - us.revert() - $model.$setViewValue(us) + @$el.on "click", ".point", (event) => + event.preventDefault() + event.stopPropagation() + target = angular.element(event.currentTarget) + roleId = target.data("role-id") + pointId = target.data("point-id") + @$el.find(".popover").popover().close() + points = _.clone(@us.points, true) + points[roleId] = pointId + @us.points = points + @render() + @onSelectedPointForRole(roleId, pointId) - $repo.save(us).then(onSuccess, onError) + renderPointsSelector: (roleId, target) -> + points = _.map @points, (point) => + point = _.clone(point, true) + point.selected = if @us.points[roleId] == point.id then false else true + return point - $el.on "click", ".total.clickable", (event) -> - event.preventDefault() - event.stopPropagation() - return if not isEditable() + html = pointsTemplate({"points": points, roleId: roleId}) + # Remove any previous state + @$el.find(".popover").popover().close() + @$el.find(".pop-points-open").remove() + # Render into DOM and show the new created element + if target? + @$el.find(target).append(html) + else + @$el.append(html) - target = angular.element(event.currentTarget) - roleId = target.data("role-id") + @$el.find(".pop-points-open").popover().open -> + $(this) + .removeClass("active") + .closest("li").removeClass("active") - us = $model.$modelValue - renderPoints(target, us, roleId) + @$el.find(".pop-points-open").show() - target.siblings().removeClass('active') - target.addClass('active') + create = ($el, us, project) -> + estimationProcess = new EstimationProcess($el, us, project) + if estimationProcess.isEditable + estimationProcess.bindClickEvents() + else + $el.unbind("click") - $el.on "click", ".point", (event) -> - event.preventDefault() - event.stopPropagation() - return if not isEditable() - - target = angular.element(event.currentTarget) - roleId = target.data("role-id") - pointId = target.data("point-id") - - save(roleId, pointId) - - $scope.$watch $attrs.ngModel, (us) -> - render(us) if us - - $scope.$on "$destroy", -> - $el.off() + return estimationProcess return { - link: link - restrict: "EA" - require: "ngModel" + create: create } -module.directive("tgUsEstimation", ["$rootScope", "$tgRepo", "$tgConfirm", "$tgQqueue", "$tgTemplate", - UsEstimationDirective]) +module.factory("$tgEstimationsService", ["$tgTemplate", "$tgQqueue", "$tgRepo", "$tgConfirm", "$q", EstimationsService]) diff --git a/app/partials/common/estimation/us-estimation-total.jade b/app/partials/common/estimation/us-estimation-total.jade new file mode 100644 index 00000000..235494bb --- /dev/null +++ b/app/partials/common/estimation/us-estimation-total.jade @@ -0,0 +1,5 @@ +a.us-points(href="", title!="<%= title %>", class!="<% if (!editable) { %>not-clickable<% } %>") + span.points-value <%= text %> + <% if (editable) { %> + span.icon.icon-arrow-bottom(tg-check-permission="modify_us") + <% } %> diff --git a/app/partials/includes/components/backlog-row.jade b/app/partials/includes/components/backlog-row.jade index a340e1ae..7fbe7dbe 100644 --- a/app/partials/includes/components/backlog-row.jade +++ b/app/partials/includes/components/backlog-row.jade @@ -20,7 +20,5 @@ div.row.us-item-row(ng-repeat="us in visibleUserstories track by us.id", tg-drag div.points(tg-backlog-us-points="us") a.us-points(href="", title="Points") - span.points-value 0 - span.icon.icon-arrow-bottom(tg-check-permission="modify_us") a.icon.icon-drag-v(tg-check-permission="modify_us", href="", title="Drag") diff --git a/app/partials/includes/modules/lightbox-us-create-edit.jade b/app/partials/includes/modules/lightbox-us-create-edit.jade index 0a6d73e7..deb5a41d 100644 --- a/app/partials/includes/modules/lightbox-us-create-edit.jade +++ b/app/partials/includes/modules/lightbox-us-create-edit.jade @@ -7,7 +7,7 @@ form data-required="true", data-maxlength="500") fieldset.estimation - tg-lb-us-estimation(ng-model="us.points") + tg-lb-us-estimation(ng-model="us") fieldset select(name="status", ng-model="us.status", ng-options="s.id as s.name for s in usStatusList", diff --git a/app/styles/modules/backlog/backlog-table.scss b/app/styles/modules/backlog/backlog-table.scss index d5a1341e..c9dd613a 100644 --- a/app/styles/modules/backlog/backlog-table.scss +++ b/app/styles/modules/backlog/backlog-table.scss @@ -77,7 +77,7 @@ padding-right: 3rem; } .pop-points-open { - @include popover(200px, 0, 260px, '', ''); + @include popover(200px, 0, 30px, '', ''); li { display: inline-block; width: 23%; From c100c8b6b0440b790bd28da8f86ebd2bc7b75bd4 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 18 Feb 2015 08:39:20 +0100 Subject: [PATCH 089/207] use setViewValue to trigger wiki watchers --- app/coffee/modules/wiki/main.coffee | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/app/coffee/modules/wiki/main.coffee b/app/coffee/modules/wiki/main.coffee index 6a84e194..381c4848 100644 --- a/app/coffee/modules/wiki/main.coffee +++ b/app/coffee/modules/wiki/main.coffee @@ -159,9 +159,6 @@ WikiSummaryDirective = ($log, $template) -> return if not wikiPage render(wikiPage) - $scope.$on "wiki:edit", (event, wikiPage) -> - render(wikiPage) - $scope.$on "$destroy", -> $el.off() @@ -215,8 +212,7 @@ EditableWikiContentDirective = ($window, $document, $repo, $confirm, $loading, $ if not wiki.id? $analytics.trackEvent("wikipage", "create", "create wiki page", 1) - $model.$modelValue = wikiPage - $scope.$broadcast("wiki:edit", wikiPage) + $model.$setViewValue wikiPage $confirm.notify("success") switchToReadMode() From 3f69d8813194ef189c5c9f2be3e1f4b73033a2dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 18 Feb 2015 09:55:36 +0100 Subject: [PATCH 090/207] Fix manage members roles change problem --- app/coffee/modules/admin/memberships.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/memberships.coffee b/app/coffee/modules/admin/memberships.coffee index dc21cfa3..14d481d6 100644 --- a/app/coffee/modules/admin/memberships.coffee +++ b/app/coffee/modules/admin/memberships.coffee @@ -307,7 +307,7 @@ MembershipsRowRoleSelectorDirective = ($log, $repo, $confirm) -> member = $scope.$eval($attrs.tgMembershipsRowRoleSelector) html = render(member) - $el.on "click", "select", (event) => + $el.on "change", "select", (event) => onSuccess = -> $confirm.notify("success") From bea8aa848c163d322a543917043e19a26b215bf4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 18 Feb 2015 10:15:30 +0100 Subject: [PATCH 091/207] Fix add new choice after hide new choice form in admin panel --- app/coffee/modules/admin/project-values.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 188daba2..5e9a56fd 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -218,7 +218,7 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> $el.on "click", ".delete-new", (event) -> event.preventDefault() - $el.find(".new-value").hide() + $el.find(".new-value").addClass("hidden") initializeNewValue() $el.on "click", ".edit-value", (event) -> From 3b96ef1778513ba17ae69b09a002c92d3ef89514 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 18 Feb 2015 10:48:59 +0100 Subject: [PATCH 092/207] Don't reload values on new value added and removed unnecesary code --- .../modules/admin/project-values.coffee | 27 ++++--------------- 1 file changed, 5 insertions(+), 22 deletions(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 188daba2..ecf83672 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -149,15 +149,7 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> if focus $(".new-value input").focus() - submit = debounce 2000, => - promise = $repo.save($scope.project) - promise.then -> - $confirm.notify("success") - - promise.then null, (data) -> - $confirm.notify("error", data._error_message) - - saveValue = debounce 2000, (target) -> + saveValue = (target) -> form = target.parents("form").checksley() return if not form.validate() @@ -180,14 +172,6 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> value.revert() row.siblings(".visualization").removeClass('hidden') - $el.on "submit", "form", (event) -> - event.preventDefault() - submit() - - $el.on "click", "form a.button-green", (event) -> - event.preventDefault() - submit() - $el.on "click", ".show-add-new", (event) -> event.preventDefault() $el.find(".new-value").removeClass('hidden') @@ -204,12 +188,11 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> $scope.newValue.order = if $scope.maxValueOrder then $scope.maxValueOrder + 1 else 1 promise = $repo.create(valueType, $scope.newValue) - promise.then => - $ctrl.loadValues().then -> - animationFrame.add () -> - goToBottomList() - + promise.then (data) => $el.find(".new-value").addClass("hidden") + + $scope.values.push(data) + $scope.maxValueOrder = data.order initializeNewValue() promise.then null, (data) -> From e7280686ac9b68477ca96831645fc77675e8d0b8 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 18 Feb 2015 16:53:48 +0100 Subject: [PATCH 093/207] remove gulp-cache on jade --- gulpfile.js | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/gulpfile.js b/gulpfile.js index 252cb353..6d0756d5 100644 --- a/gulpfile.js +++ b/gulpfile.js @@ -32,13 +32,13 @@ paths.tmp = "tmp/"; paths.extras = "extras/"; paths.jade = [ - paths.app + "**/*.jade", - "!" + paths.app + "partial/includes/**", + paths.app + "**/*.jade" ]; paths.htmlPartials = [ paths.tmp + "partials/**/*.html", - paths.tmp + "plugins/**/*.html" + paths.tmp + "plugins/**/*.html", + "!" + paths.tmp + "partials/includes/**/*.html" ]; paths.images = paths.app + "images/**/*"; @@ -115,20 +115,22 @@ var isDeploy = process.argv[process.argv.length - 1] == "deploy"; ############################################################################## */ +var jadeIncludes = paths.app +'partials/includes/**/*'; + gulp.task("jade", function() { return gulp.src(paths.jade) .pipe(plumber()) .pipe(cached("jade")) - .pipe(cache(jade({pretty: true, locals:{v:(new Date()).getTime()}}))) + .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) .pipe(gulp.dest(paths.tmp)); }); gulp.task("jade-inheritance", function() { return gulp.src(paths.jade) .pipe(plumber()) - .pipe(cached('jade')) + .pipe(cached("jade")) .pipe(jadeInheritance({basedir: "./app/"})) - .pipe(cache(jade({pretty: true, locals:{v:(new Date()).getTime()}}))) + .pipe(jade({pretty: true, locals:{v:(new Date()).getTime()}})) .pipe(gulp.dest(paths.tmp)); }); From 017a81ae51dcec11bf8b78ba5154666360147747 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 19 Feb 2015 09:04:14 +0100 Subject: [PATCH 094/207] fix #2172 - horizontal popover with long point names --- app/coffee/modules/common/estimation.coffee | 5 ++++- .../common/estimation/us-estimation-points.jade | 2 +- app/styles/components/popover-points.scss | 10 ++++++++++ app/styles/layout/us-detail.scss | 1 + main-sass.js | 1 + 5 files changed, 17 insertions(+), 2 deletions(-) create mode 100644 app/styles/components/popover-points.scss diff --git a/app/coffee/modules/common/estimation.coffee b/app/coffee/modules/common/estimation.coffee index 3b03a587..f8666078 100644 --- a/app/coffee/modules/common/estimation.coffee +++ b/app/coffee/modules/common/estimation.coffee @@ -203,7 +203,10 @@ EstimationsService = ($template, $qqueue, $repo, $confirm, $q) -> point.selected = if @us.points[roleId] == point.id then false else true return point - html = pointsTemplate({"points": points, roleId: roleId}) + maxPointLength = 5 + horizontalList = _.some points, (point) => point.name.length > maxPointLength + + html = pointsTemplate({"points": points, roleId: roleId, horizontal: horizontalList}) # Remove any previous state @$el.find(".popover").popover().close() @$el.find(".pop-points-open").remove() diff --git a/app/partials/common/estimation/us-estimation-points.jade b/app/partials/common/estimation/us-estimation-points.jade index 1fb05d0b..8440a616 100644 --- a/app/partials/common/estimation/us-estimation-points.jade +++ b/app/partials/common/estimation/us-estimation-points.jade @@ -1,4 +1,4 @@ -ul.popover.pop-points-open +ul.popover.pop-points-open(class!="<% if (horizontal) { %>horizontal<% }; %>") <% _.each(points, function(point) { %> li <% if (point.selected) { %> diff --git a/app/styles/components/popover-points.scss b/app/styles/components/popover-points.scss new file mode 100644 index 00000000..63903eee --- /dev/null +++ b/app/styles/components/popover-points.scss @@ -0,0 +1,10 @@ +// This file should contain in future all the common styles for the points popover + +.popover.pop-points-open { + &.horizontal { + li { + white-space: nowrap; + width: 100%; + } + } +} diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index 1ff3c9f1..ae06ec79 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -323,6 +323,7 @@ @include popover(200px, $top: 105%, $left: -160px, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 90%, $arrow-height: 10px); } } + } .duty-data-container { diff --git a/main-sass.js b/main-sass.js index 1f266882..780eb2e7 100644 --- a/main-sass.js +++ b/main-sass.js @@ -56,6 +56,7 @@ exports.files = function () { 'components/beta', 'components/markitup', 'components/markdown-help', + 'components/popover-points', //################################################# From 4e7c61201db6260711f6d4352421c90d46d84883 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 07:58:05 +0100 Subject: [PATCH 095/207] Comment button broken --- app/partials/common/history/history-base.jade | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/partials/common/history/history-base.jade b/app/partials/common/history/history-base.jade index cd3cfc41..383c21ab 100644 --- a/app/partials/common/history/history-base.jade +++ b/app/partials/common/history/history-base.jade @@ -11,13 +11,13 @@ section.history section.history-comments .comments-list div(tg-check-permission!="modify_<%- type %>", tg-toggle-comment, class="add-comment") - textarea(placeholder="Type a new comment here", - ng-model!="<%- ngmodel %>.comment", tg-markitup="tg-markitup") + textarea(placeholder="Type a new comment here", ng-model!="<%- ngmodel %>.comment", tg-markitup="tg-markitup") <% if (mode !== "edit") { %> a(class="help-markdown", href="https://taiga.io/support/taiga-markdown-syntax/", target="_blank", title="Mardown syntax help") span.icon.icon-help span Markdown syntax help - a(href="", title="Comment", class="button button-green save-comment") Comment + a(href="", title="Comment", class="button button-green save-comment") + span Comment <% } %> section.history-activity.hidden .changes-list From 4c2d628fe2fe374a23182697c298fc62fa0bc74c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 09:09:23 +0100 Subject: [PATCH 096/207] Fixed weird assigned to default margin --- app/styles/modules/common/assigned-to.scss | 1 - 1 file changed, 1 deletion(-) diff --git a/app/styles/modules/common/assigned-to.scss b/app/styles/modules/common/assigned-to.scss index f68e5126..ee87db88 100644 --- a/app/styles/modules/common/assigned-to.scss +++ b/app/styles/modules/common/assigned-to.scss @@ -26,7 +26,6 @@ .assigned-to { flex-grow: 3; margin-left: 1rem; - margin-top: 15px; .assigned-title { @extend %small; color: $gray-light; From 166e1af6e8ff0bc6d6d2839e4a0289b10b79260c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 09:11:30 +0100 Subject: [PATCH 097/207] Fix history margin in title --- app/styles/modules/common/history.scss | 1 + 1 file changed, 1 insertion(+) diff --git a/app/styles/modules/common/history.scss b/app/styles/modules/common/history.scss index fb6d97d8..ad14a78f 100644 --- a/app/styles/modules/common/history.scss +++ b/app/styles/modules/common/history.scss @@ -40,6 +40,7 @@ .history-tabs { @extend %title; border-bottom: 3px solid $gray-light; + margin-bottom: 0; padding: .5rem 0; li { @extend %large; From 62a787771944a0ac8092126721470fce890dba15 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 09:25:13 +0100 Subject: [PATCH 098/207] Fix wiki link button --- app/partials/includes/modules/admin/default-values.jade | 3 ++- app/partials/wiki/wiki-nav.jade | 5 +++-- app/styles/modules/wiki/wiki-nav.scss | 2 +- 3 files changed, 6 insertions(+), 4 deletions(-) diff --git a/app/partials/includes/modules/admin/default-values.jade b/app/partials/includes/modules/admin/default-values.jade index d0e91e80..6cff329a 100644 --- a/app/partials/includes/modules/admin/default-values.jade +++ b/app/partials/includes/modules/admin/default-values.jade @@ -36,4 +36,5 @@ section.default-values ng-options="s.id as s.name for s in issueStatusList") fieldset - button.button-green.submit-button(type="submit", title="Save") Save + button.button-green.submit-button(type="submit", title="Save") + span Save diff --git a/app/partials/wiki/wiki-nav.jade b/app/partials/wiki/wiki-nav.jade index ecafc1ca..759bccaa 100644 --- a/app/partials/wiki/wiki-nav.jade +++ b/app/partials/wiki/wiki-nav.jade @@ -15,5 +15,6 @@ nav li.new.hidden input(type="text" placeholder="name") <% if (addWikiLinkPermission) { %> -a(href="" title="Add link" class="add-button button button-gray") Add link -<% } %> \ No newline at end of file +a(href="" title="Add link" class="add-button button-gray") + span Add link +<% } %> diff --git a/app/styles/modules/wiki/wiki-nav.scss b/app/styles/modules/wiki/wiki-nav.scss index e09fd0f8..d80724ab 100644 --- a/app/styles/modules/wiki/wiki-nav.scss +++ b/app/styles/modules/wiki/wiki-nav.scss @@ -39,7 +39,7 @@ width: 100%; } } - .button { + .add-button { color: $white; display: block; margin-bottom: .5rem; From c0f77374ee67324b11a8fc1022c92e598f22ef69 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 14:20:04 +0100 Subject: [PATCH 099/207] Add contrib slack styles --- app/styles/modules/admin/contrib.scss | 24 ++++++++++++++++-------- 1 file changed, 16 insertions(+), 8 deletions(-) diff --git a/app/styles/modules/admin/contrib.scss b/app/styles/modules/admin/contrib.scss index bea56e3c..58d998d0 100644 --- a/app/styles/modules/admin/contrib.scss +++ b/app/styles/modules/admin/contrib.scss @@ -4,23 +4,31 @@ max-width: 700px; width: 100%; } - input, - textarea { - @extend %title; - } fieldset { margin-bottom: 1rem; } + .contrib-input { + flex: 1; + } + .contrib-test { + flex-basis: 7.5rem; + display: flex; + align-items: flex-end; + margin-left: .5rem; + text-align: center; + a { + padding: 0.6rem 2.5rem; + } + } label { @extend %title; display: block; margin-bottom: .2rem; } - textarea { - height: 10rem; + .contrib-form-wrapper { + display: flex; } - .button-green { - color: $white; + .submit-button { display: block; text-align: center; } From ea9d10a65da6fffd5e50f77045d976562200b471 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 24 Feb 2015 08:29:26 +0100 Subject: [PATCH 100/207] Fix scss lint errors. Please DO NOT MERGE if there are lint errors --- app/styles/modules/admin/contrib.scss | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/styles/modules/admin/contrib.scss b/app/styles/modules/admin/contrib.scss index 58d998d0..0581bf82 100644 --- a/app/styles/modules/admin/contrib.scss +++ b/app/styles/modules/admin/contrib.scss @@ -11,13 +11,13 @@ flex: 1; } .contrib-test { - flex-basis: 7.5rem; - display: flex; align-items: flex-end; + display: flex; + flex-basis: 7.5rem; margin-left: .5rem; text-align: center; a { - padding: 0.6rem 2.5rem; + padding: .6rem 2.5rem; } } label { From 5e8ffda0f17d19b2a0768fc8dd62891c72521b24 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 25 Feb 2015 08:44:52 +0100 Subject: [PATCH 101/207] fix gulp-cache with coffee --- gulpfile.js | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gulpfile.js b/gulpfile.js index 6d0756d5..8e257762 100644 --- a/gulpfile.js +++ b/gulpfile.js @@ -262,8 +262,11 @@ gulp.task("locales", function() { gulp.task("coffee", function() { return gulp.src(paths.coffee) - .pipe(plumber()) .pipe(cache(coffee())) + .on("error", function(err) { + console.log(err.toString()); + this.emit("end"); + }) .pipe(gulp.dest(paths.tmp)); }); From ad1ebdd7ea706b1c53751fe2d987b10cc599e8f7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 25 Feb 2015 12:08:52 +0100 Subject: [PATCH 102/207] Adding the hipchat plugin to the changelog --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4a3c2ea6..eaf817c5 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,11 +7,11 @@ - ... ### Misc +- New contrib plugin for hipchat (by Δndrea Stagi) - Plugin based authentication. - Added Taiga Style Guide in support Pages to enhance open source design. - Lots of small and not so small bugfixes. - ## 1.5.0 Betula Pendula - FOSDEM 2015 (2015-01-29) ### Features From dad75078788b06d941457140b7c7323688e58ddd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 25 Feb 2015 16:23:40 +0100 Subject: [PATCH 103/207] Fixed typo --- app/coffee/modules/admin/project-profile.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/project-profile.coffee b/app/coffee/modules/admin/project-profile.coffee index 2cc35374..a8da32e6 100644 --- a/app/coffee/modules/admin/project-profile.coffee +++ b/app/coffee/modules/admin/project-profile.coffee @@ -231,7 +231,7 @@ ProjectExportDirective = ($window, $rs, $confirm) -> resultTitleEl = $el.find(".result-title") setLoadingTitle = -> resultTitleEl.html("We are generating your dump file") # TODO: i18n setAsyncTitle = -> resultTitleEl.html("We are generating your dump file") # TODO: i18n - setSyncTitle = -> resultTitleEl.html("Your dump file ir ready!") # TODO: i18n + setSyncTitle = -> resultTitleEl.html("Your dump file is ready!") # TODO: i18n resultMessageEl = $el.find(".result-message ") setLoadingMessage = -> resultMessageEl.html("Please don't close this page.") # TODO: i18n From b03c9df9686db9bfca43e5962c882061e986755c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 25 Feb 2015 17:34:06 +0100 Subject: [PATCH 104/207] Add link to support page of import/export --- app/partials/admin/admin-project-export.jade | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/app/partials/admin/admin-project-export.jade b/app/partials/admin/admin-project-export.jade index 807897e8..3274b08a 100644 --- a/app/partials/admin/admin-project-export.jade +++ b/app/partials/admin/admin-project-export.jade @@ -20,3 +20,7 @@ div.wrapper(ng-controller="ProjectProfileController as ctrl", img(src="/svg/spinner-circle.svg", alt="loading...") h3.result-title p.result-message + + a.help-button(href="https://taiga.io/support/import-export-projects/", target="_blank") + span.icon.icon-help + span Do you need help? Check out our support page! From 1ed29e9496cd650d8d414b7fdf2f76077505342e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Mar 2015 14:26:29 +0100 Subject: [PATCH 105/207] Minor fix for arrow --- app/styles/modules/common/lightbox.scss | 5 ----- 1 file changed, 5 deletions(-) diff --git a/app/styles/modules/common/lightbox.scss b/app/styles/modules/common/lightbox.scss index 9824ce43..7a9f4adb 100644 --- a/app/styles/modules/common/lightbox.scss +++ b/app/styles/modules/common/lightbox.scss @@ -95,11 +95,6 @@ display: none; } } - .points-per-role { - .popover { - @include popover(200px, $top: 105%, $left: 35%, $arrow-width: 10px, $arrow-top: -5px, $arrow-left: 10px); - } - } } .lightbox-generic-bulk { From 20941d5de155bfd4baa022f5bf842ca079177b49 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Mar 2015 14:35:11 +0100 Subject: [PATCH 106/207] Add margin to import/export help --- app/styles/modules/admin/admin-project-export.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/modules/admin/admin-project-export.scss b/app/styles/modules/admin/admin-project-export.scss index b4f31b45..d87a6279 100644 --- a/app/styles/modules/admin/admin-project-export.scss +++ b/app/styles/modules/admin/admin-project-export.scss @@ -1,5 +1,5 @@ .admin-project-export-buttons { - margin-top: 2rem; + margin: 2rem 0 1rem; } .admin-project-export-result { From 3338dc2e9231d1c52b1e64e26b942943c8df94af Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 2 Mar 2015 10:24:54 +0100 Subject: [PATCH 107/207] scss-lint git hook --- gulpfile.js | 3 +++ package.json | 9 ++++++++- 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/gulpfile.js b/gulpfile.js index 8e257762..0d9ae11c 100644 --- a/gulpfile.js +++ b/gulpfile.js @@ -165,6 +165,8 @@ gulp.task("scss-lint", [], function() { "!" + paths.app + "/styles/components/markitup.scss" ]; + var fail = process.argv.indexOf("--fail") !== -1; + return gulp.src(paths.sass.concat(ignore)) .pipe(gulpif(!isDeploy, cache(scsslint({endless: true, sync: true, config: "scsslint.yml"}), { success: function(scsslintFile) { @@ -176,6 +178,7 @@ gulp.task("scss-lint", [], function() { }; } }))) + .pipe(gulpif(fail, scsslint.failReporter())) }); gulp.task("sass-compile", ["scss-lint"], function() { diff --git a/package.json b/package.json index a1f81bd5..318a93a3 100644 --- a/package.json +++ b/package.json @@ -16,6 +16,9 @@ "url": "https://github.com/taigaio/taiga-front/blob/master/LICENSE" } ], + "scripts": { + "scss-lint": "gulp scss-lint --fail" + }, "devDependencies": { "coffee-script": "^1.9.0", "del": "^1.1.1", @@ -45,8 +48,12 @@ "gulp-template": "^2.1.0", "gulp-uglify": "~1.1.0", "gulp-wrap": "^0.10.1", + "pre-commit": "^1.0.5", "readable-stream": "~1.0.33", "run-sequence": "^1.0.2", "through2": "~0.6.3" - } + }, + "pre-commit": [ + "scss-lint" + ] } From f45dc4531338e275b912b8fe70e9637032f5d051 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 27 Feb 2015 14:49:45 +0100 Subject: [PATCH 108/207] upgrade node dependencies --- package.json | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/package.json b/package.json index 318a93a3..0b5bd476 100644 --- a/package.json +++ b/package.json @@ -20,34 +20,34 @@ "scss-lint": "gulp scss-lint --fail" }, "devDependencies": { - "coffee-script": "^1.9.0", + "coffee-script": "^1.9.1", "del": "^1.1.1", - "express": "^4.11.2", - "gulp": "^3.8.10", + "express": "^4.12.0", + "gulp": "^3.8.11", "gulp-angular-templatecache": "^1.5.0", "gulp-autoprefixer": "^2.1.0", - "gulp-cache": "^0.2.4", + "gulp-cache": "^0.2.8", "gulp-cached": "1.0.2", "gulp-coffee": "^2.3.1", "gulp-coffeelint": "~0.4.0", - "gulp-concat": "^2.4.3", + "gulp-concat": "^2.5.2", "gulp-csslint": "^0.1.5", "gulp-flatten": "0.0.4", "gulp-if": "^1.2.5", - "gulp-imagemin": "^2.1.0", + "gulp-imagemin": "^2.2.1", "gulp-insert": "^0.4.0", - "gulp-jade": "^0.11.0", + "gulp-jade": "^1.0.0", "gulp-jade-inheritance": "0.5.0", - "gulp-minify-css": "^0.4.4", + "gulp-minify-css": "^0.4.6", "gulp-plumber": "^0.6.6", "gulp-rename": "^1.2.0", - "gulp-replace": "^0.5.2", - "gulp-sass": "^1.3.2", - "gulp-scss-lint": "0.1.7", - "gulp-sourcemaps": "^1.3.0", - "gulp-template": "^2.1.0", + "gulp-replace": "^0.5.3", + "gulp-sass": "^1.3.3", + "gulp-scss-lint": "0.1.9", + "gulp-sourcemaps": "^1.5.0", + "gulp-template": "^3.0.0", "gulp-uglify": "~1.1.0", - "gulp-wrap": "^0.10.1", + "gulp-wrap": "^0.11.0", "pre-commit": "^1.0.5", "readable-stream": "~1.0.33", "run-sequence": "^1.0.2", From 6ce89577492a550f67c734c2d9412ab2d864ba3b Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 19 Feb 2015 11:29:13 +0100 Subject: [PATCH 109/207] prevent location search if the url has the same parameters --- app/coffee/modules/base/location.coffee | 4 ++++ app/coffee/modules/controllerMixins.coffee | 17 ++++++++++------- 2 files changed, 14 insertions(+), 7 deletions(-) diff --git a/app/coffee/modules/base/location.coffee b/app/coffee/modules/base/location.coffee index f99f0391..a6c3fc46 100644 --- a/app/coffee/modules/base/location.coffee +++ b/app/coffee/modules/base/location.coffee @@ -28,6 +28,10 @@ locationFactory = ($location, $route, $rootscope) -> un() return $location + + $location.isInCurrentRouteParams = (name, value) -> + return $route.current.params[name] == value + return $location diff --git a/app/coffee/modules/controllerMixins.coffee b/app/coffee/modules/controllerMixins.coffee index cf63d08e..68cced92 100644 --- a/app/coffee/modules/controllerMixins.coffee +++ b/app/coffee/modules/controllerMixins.coffee @@ -62,7 +62,7 @@ taiga.PageMixin = PageMixin ############################################################################# ## Filters Mixin ############################################################################# -# This mixin requires @location ($tgLocation) and @scope +# This mixin requires @location ($tgLocation), and @scope class FiltersMixin selectFilter: (name, value, load=false) -> @@ -73,16 +73,19 @@ class FiltersMixin existing = _.compact(existing) value = joinStr(",", _.uniq(existing)) - location = if load then @location else @location.noreload(@scope) - location.search(name, value) + if !@location.isInCurrentRouteParams(name, value) + location = if load then @location else @location.noreload(@scope) + location.search(name, value) replaceFilter: (name, value, load=false) -> - location = if load then @location else @location.noreload(@scope) - location.search(name, value) + if !@location.isInCurrentRouteParams(name, value) + location = if load then @location else @location.noreload(@scope) + location.search(name, value) replaceAllFilters: (filters, load=false) -> - location = if load then @location else @location.noreload(@scope) - location.search(filters) + if !@location.isInCurrentRouteParams(name, value) + location = if load then @location else @location.noreload(@scope) + location.search(filters) unselectFilter: (name, value, load=false) -> params = @location.search() From 4a3e60e8343bb4dfe2ac768a6fcd1dd0252a2522 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 3 Mar 2015 09:00:31 +0100 Subject: [PATCH 110/207] reset page when a filter is applied --- app/coffee/modules/issues/list.coffee | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/coffee/modules/issues/list.coffee b/app/coffee/modules/issues/list.coffee index 7cff727a..f29c0848 100644 --- a/app/coffee/modules/issues/list.coffee +++ b/app/coffee/modules/issues/list.coffee @@ -530,6 +530,9 @@ IssuesFiltersDirective = ($log, $location, $rs, $confirm, $loading, $template) - selectQFilter = debounceLeading 100, (value) -> return if value is undefined + + $ctrl.replaceFilter("page", null) + if value.length == 0 $ctrl.replaceFilter("q", null) $ctrl.storeFilters() From 368c7505f4b9ff74d0079e2180c7b700de63dfb7 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 3 Mar 2015 09:41:59 +0100 Subject: [PATCH 111/207] fix leaving taiga button --- app/partials/includes/modules/cancel-account-form.jade | 3 +-- app/partials/user/cancel-account.jade | 2 +- app/styles/modules/auth/cancel-account.scss | 5 +++++ main-sass.js | 1 + 4 files changed, 8 insertions(+), 3 deletions(-) create mode 100644 app/styles/modules/auth/cancel-account.scss diff --git a/app/partials/includes/modules/cancel-account-form.jade b/app/partials/includes/modules/cancel-account-form.jade index 28f34d34..979dc25a 100644 --- a/app/partials/includes/modules/cancel-account-form.jade +++ b/app/partials/includes/modules/cancel-account-form.jade @@ -8,5 +8,4 @@ div.change-email-form-container(tg-cancel-account) input(type="hidden", name="cancel_token", ng-model="data.cancel_token", data-required="true", placeholder="cancel account token") - a.button-cancel-account.button-gray(href="", title="Yes, I'm leaving") Yes, I'm leaving! - button(type="submit", class="hidden") + button.button-cancel-account.button-gray(type="submit", title="Yes, I'm leaving!") Yes, I'm leaving! diff --git a/app/partials/user/cancel-account.jade b/app/partials/user/cancel-account.jade index c333188a..1735da1e 100644 --- a/app/partials/user/cancel-account.jade +++ b/app/partials/user/cancel-account.jade @@ -1,4 +1,4 @@ -div.wrapper +div.wrapper.cancel-account div.login-main div.login-container h1.logo diff --git a/app/styles/modules/auth/cancel-account.scss b/app/styles/modules/auth/cancel-account.scss new file mode 100644 index 00000000..52776464 --- /dev/null +++ b/app/styles/modules/auth/cancel-account.scss @@ -0,0 +1,5 @@ +.cancel-account { + fieldset { + text-align: center; + } +} diff --git a/main-sass.js b/main-sass.js index 780eb2e7..8db0d5bd 100644 --- a/main-sass.js +++ b/main-sass.js @@ -108,6 +108,7 @@ exports.files = function () { 'modules/auth/register-form', 'modules/auth/forgot-form', 'modules/auth/change-password-from-recovery', + 'modules/auth/cancel-account', //Wiki modules 'modules/wiki/wiki-nav', From d95f1c474a26b759a0d23b5b6e874e76e534eafe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 14:11:06 +0100 Subject: [PATCH 112/207] Basic custom fields structure --- app/coffee/app.coffee | 2 ++ app/coffee/modules/base.coffee | 1 + .../admin/admin-project-values-us-extras.jade | 20 +++++++++++++++++++ .../modules/admin-submenu-project-values.jade | 5 +++++ .../modules/admin/admin-us-extras.jade | 18 +++++++++++++++++ .../modules/admin/admin-custom-fields.scss | 3 +++ main-sass.js | 1 + 7 files changed, 50 insertions(+) create mode 100644 app/partials/admin/admin-project-values-us-extras.jade create mode 100644 app/partials/includes/modules/admin/admin-us-extras.jade create mode 100644 app/styles/modules/admin/admin-custom-fields.scss diff --git a/app/coffee/app.coffee b/app/coffee/app.coffee index e7f49f72..aaeb7abd 100644 --- a/app/coffee/app.coffee +++ b/app/coffee/app.coffee @@ -87,6 +87,8 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-project-values-us-status.html"}) $routeProvider.when("/project/:pslug/admin/project-values/us-points", {templateUrl: "admin/admin-project-values-us-points.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/us-extras", + {templateUrl: "admin/admin-project-values-us-extras.html"}) $routeProvider.when("/project/:pslug/admin/project-values/task-status", {templateUrl: "admin/admin-project-values-task-status.html"}) $routeProvider.when("/project/:pslug/admin/project-values/issue-status", diff --git a/app/coffee/modules/base.coffee b/app/coffee/modules/base.coffee index 3e44ac58..9324f20c 100644 --- a/app/coffee/modules/base.coffee +++ b/app/coffee/modules/base.coffee @@ -86,6 +86,7 @@ urls = { "project-admin-project-profile-export": "/project/:project/admin/project-profile/export" "project-admin-project-values-us-status": "/project/:project/admin/project-values/us-status" "project-admin-project-values-us-points": "/project/:project/admin/project-values/us-points" + "project-admin-project-values-us-extras": "/project/:project/admin/project-values/us-extras" "project-admin-project-values-task-status": "/project/:project/admin/project-values/task-status" "project-admin-project-values-issue-status": "/project/:project/admin/project-values/issue-status" "project-admin-project-values-issue-types": "/project/:project/admin/project-values/issue-types" diff --git a/app/partials/admin/admin-project-values-us-extras.jade b/app/partials/admin/admin-project-values-us-extras.jade new file mode 100644 index 00000000..88649141 --- /dev/null +++ b/app/partials/admin/admin-project-values-us-extras.jade @@ -0,0 +1,20 @@ +div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='userstories'; type='points'; sectionName='Us points'", + type="points") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-us-extras") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common + include ../includes/components/mainTitle + p.admin-subtitle Specify here user story custom fields. The new field will appear on your user story detail. + + div.webhooks-options + a.button.button-green.hidden.add-custom-us(href="",title="Add a custom field in user stories") Add custom field + + include ../includes/modules/admin/admin-us-extras + +div.lightbox.lightbox-generic-notion.notion-admin-project-values-us-points(id="notion-admin-project-values-us-points", tg-lb-notion) + include ../includes/modules/help-notions/lightbox-notion-admin-project-values-us-points diff --git a/app/partials/includes/modules/admin-submenu-project-values.jade b/app/partials/includes/modules/admin-submenu-project-values.jade index 47cc1134..681b6520 100644 --- a/app/partials/includes/modules/admin-submenu-project-values.jade +++ b/app/partials/includes/modules/admin-submenu-project-values.jade @@ -14,6 +14,11 @@ section.admin-submenu span.title US points span.icon.icon-arrow-right + li#adminmenu-values-us-extras + a(href="", tg-nav="project-admin-project-values-us-extras:project=project.slug") + span.title US extras + span.icon.icon-arrow-right + li#adminmenu-values-task-status a(href="", tg-nav="project-admin-project-values-task-status:project=project.slug") span.title Task statuses diff --git a/app/partials/includes/modules/admin/admin-us-extras.jade b/app/partials/includes/modules/admin/admin-us-extras.jade new file mode 100644 index 00000000..e4758637 --- /dev/null +++ b/app/partials/includes/modules/admin/admin-us-extras.jade @@ -0,0 +1,18 @@ +section.custom-fields-table.basic-table + div.table-header + div.row + div.custom-name Name + div.custom-description Description + div.custom-options + div.table-body + div.row + div.custom-name + div.custom-description Description + div.custom-options + form.row + fieldset.custom-name + input(type="text") + fieldset.custom-description Description + input(type="text") + fieldset.custom-options + diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-fields.scss new file mode 100644 index 00000000..95f74aba --- /dev/null +++ b/app/styles/modules/admin/admin-custom-fields.scss @@ -0,0 +1,3 @@ +.custom-fields-table { + +} diff --git a/main-sass.js b/main-sass.js index 8db0d5bd..909931e1 100644 --- a/main-sass.js +++ b/main-sass.js @@ -125,6 +125,7 @@ exports.files = function () { 'modules/admin/admin-membership-table', 'modules/admin/admin-project-profile', 'modules/admin/default-values', + 'modules/admin/admin-custom-fields', 'modules/admin/project-values', 'modules/admin/third-parties', 'modules/admin/admin-third-parties-webhooks', From e2696d090e3b5cb77952b2c0a6a695453d85b8ab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 30 Jan 2015 15:17:20 +0100 Subject: [PATCH 113/207] Basic custom field styles --- .../modules/admin/admin-us-extras.jade | 16 +++++--- .../modules/admin/admin-custom-fields.scss | 37 +++++++++++++++++++ 2 files changed, 48 insertions(+), 5 deletions(-) diff --git a/app/partials/includes/modules/admin/admin-us-extras.jade b/app/partials/includes/modules/admin/admin-us-extras.jade index e4758637..37a24a0f 100644 --- a/app/partials/includes/modules/admin/admin-us-extras.jade +++ b/app/partials/includes/modules/admin/admin-us-extras.jade @@ -5,14 +5,20 @@ section.custom-fields-table.basic-table div.custom-description Description div.custom-options div.table-body - div.row - div.custom-name + div.row.single-custom-field + div.custom-name Name div.custom-description Description div.custom-options + div.custom-options-wrapper + a.edit-webhook.icon.icon-edit(href="", title="Edit Custom Field") + a.delete-webhook.icon.icon-delete(href="", title="Delete Custom Field") form.row fieldset.custom-name - input(type="text") - fieldset.custom-description Description - input(type="text") + input(type="text", placeholder="Set your custom field name") + fieldset.custom-description + input(type="text", placeholder="Set your custom field description") fieldset.custom-options + div.custom-options-wrapper + a.edit-webhook.icon.icon-floppy(href="", title="Save Custom Field") + a.delete-webhook.icon.icon-delete(href="", title="Delete Custom Field") diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-fields.scss index 95f74aba..b7cfb36f 100644 --- a/app/styles/modules/admin/admin-custom-fields.scss +++ b/app/styles/modules/admin/admin-custom-fields.scss @@ -1,3 +1,40 @@ .custom-fields-table { + .row { + border-bottom: 0; + padding: .5rem 0; + &:hover { + .custom-options-wrapper { + opacity: 1; + transition: opacity .2s linear; + } + } + } + .table-header { + @extend %bold; + border-bottom: 1px solid $gray-light; + } + .single-custom-field { + border-bottom: 1px solid $whitish; + color: $gray; + } + .custom-name, + .custom-description { + color: $gray; + margin-right: .5rem; + } + .custom-name { + flex-grow: 1; + } + .custom-description { + flex-grow: 2; + } + .custom-options { + flex-basis: 200px; + flex-grow: 0; + } + .custom-options-wrapper { + opacity: 0; + transition: opacity .3s linear; + } } From 0f4168f68c98ed8605d672f7d1d55789c44089d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Feb 2015 08:29:54 +0100 Subject: [PATCH 114/207] Us custom fields --- .../admin/admin-project-values-us-extras.jade | 4 +-- .../modules/admin/admin-us-extras.jade | 6 ++-- .../modules/admin/admin-custom-fields.scss | 31 +++++++++++++++++-- 3 files changed, 33 insertions(+), 8 deletions(-) diff --git a/app/partials/admin/admin-project-values-us-extras.jade b/app/partials/admin/admin-project-values-us-extras.jade index 88649141..d5674a0b 100644 --- a/app/partials/admin/admin-project-values-us-extras.jade +++ b/app/partials/admin/admin-project-values-us-extras.jade @@ -11,8 +11,8 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", include ../includes/components/mainTitle p.admin-subtitle Specify here user story custom fields. The new field will appear on your user story detail. - div.webhooks-options - a.button.button-green.hidden.add-custom-us(href="",title="Add a custom field in user stories") Add custom field + div.custom-field-options + a.button.button-green.add-custom-field(href="",title="Add a custom field in user stories") Add custom field include ../includes/modules/admin/admin-us-extras diff --git a/app/partials/includes/modules/admin/admin-us-extras.jade b/app/partials/includes/modules/admin/admin-us-extras.jade index 37a24a0f..a844a656 100644 --- a/app/partials/includes/modules/admin/admin-us-extras.jade +++ b/app/partials/includes/modules/admin/admin-us-extras.jade @@ -6,13 +6,13 @@ section.custom-fields-table.basic-table div.custom-options div.table-body div.row.single-custom-field - div.custom-name Name - div.custom-description Description + div.custom-name Custom field name + div.custom-description Custom field looong Description div.custom-options div.custom-options-wrapper a.edit-webhook.icon.icon-edit(href="", title="Edit Custom Field") a.delete-webhook.icon.icon-delete(href="", title="Delete Custom Field") - form.row + form.row.single-custom-field fieldset.custom-name input(type="text", placeholder="Set your custom field name") fieldset.custom-description diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-fields.scss index b7cfb36f..93017908 100644 --- a/app/styles/modules/admin/admin-custom-fields.scss +++ b/app/styles/modules/admin/admin-custom-fields.scss @@ -1,3 +1,8 @@ +.custom-field-options { + margin-bottom: 1rem; + text-align: right; +} + .custom-fields-table { .row { border-bottom: 0; @@ -23,18 +28,38 @@ margin-right: .5rem; } .custom-name { - flex-grow: 1; + flex-basis: 25%; + flex-shrink: 0; } .custom-description { - flex-grow: 2; + @include ellipsis(100%); + flex-basis: 90%; + flex-grow: 8; } .custom-options { - flex-basis: 200px; + flex-basis: 100px; flex-grow: 0; + flex-shrink: 0; + text-align: center; + a { + color: $gray-light; + margin-right: 0.5rem; + transition: color .2s linear; + vertical-align: middle; + &:hover { + color: $green-taiga; + transition: color .2s linear; + } + } } .custom-options-wrapper { opacity: 0; transition: opacity .3s linear; } + form { + .custom-options-wrapper { + opacity: 1; + } + } } From d209718681e24d9363783cf9a47de4801df376db Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Feb 2015 08:32:17 +0100 Subject: [PATCH 115/207] Consistency styles --- app/styles/modules/admin/admin-custom-fields.scss | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-fields.scss index 93017908..782cd448 100644 --- a/app/styles/modules/admin/admin-custom-fields.scss +++ b/app/styles/modules/admin/admin-custom-fields.scss @@ -18,6 +18,11 @@ @extend %bold; border-bottom: 1px solid $gray-light; } + .table-body { + .custom-description { + color: $gray-light; + } + } .single-custom-field { border-bottom: 1px solid $whitish; color: $gray; From 9a7c900f2d1e709fc81b589c869ffbd06f457d5d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Feb 2015 08:48:17 +0100 Subject: [PATCH 116/207] Add interactions --- .../modules/admin/admin-us-extras.jade | 1 + .../modules/admin/admin-custom-fields.scss | 22 ++++++++++++++++++- 2 files changed, 22 insertions(+), 1 deletion(-) diff --git a/app/partials/includes/modules/admin/admin-us-extras.jade b/app/partials/includes/modules/admin/admin-us-extras.jade index a844a656..1655914a 100644 --- a/app/partials/includes/modules/admin/admin-us-extras.jade +++ b/app/partials/includes/modules/admin/admin-us-extras.jade @@ -6,6 +6,7 @@ section.custom-fields-table.basic-table div.custom-options div.table-body div.row.single-custom-field + span.icon.icon-drag-v div.custom-name Custom field name div.custom-description Custom field looong Description div.custom-options diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-fields.scss index 782cd448..bba0da2d 100644 --- a/app/styles/modules/admin/admin-custom-fields.scss +++ b/app/styles/modules/admin/admin-custom-fields.scss @@ -8,6 +8,10 @@ border-bottom: 0; padding: .5rem 0; &:hover { + background: rgba($fresh-taiga, .05); + cursor: move; + transition: background .2s linear; + .icon-drag-v, .custom-options-wrapper { opacity: 1; transition: opacity .2s linear; @@ -27,6 +31,18 @@ border-bottom: 1px solid $whitish; color: $gray; } + .icon-drag-v { + color: $gray-light; + opacity: 0; + padding: 0 .5rem; + transition: color .2s linear; + vertical-align: middle; + &:hover { + color: $gray; + cursor: move; + transition: color .2s linear; + } + } .custom-name, .custom-description { color: $gray; @@ -48,7 +64,7 @@ text-align: center; a { color: $gray-light; - margin-right: 0.5rem; + margin-right: .5rem; transition: color .2s linear; vertical-align: middle; &:hover { @@ -62,6 +78,10 @@ transition: opacity .3s linear; } form { + &.row:hover { + background: none; + cursor: default; + } .custom-options-wrapper { opacity: 1; } From f8929c3470d5b8470037d6d7b0ac2d92fe0e6438 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Feb 2015 09:05:21 +0100 Subject: [PATCH 117/207] Add drag&drop icon --- .../modules/admin/admin-us-extras.jade | 12 ++++--- .../modules/admin/admin-custom-fields.scss | 31 ++++++++++++------- 2 files changed, 27 insertions(+), 16 deletions(-) diff --git a/app/partials/includes/modules/admin/admin-us-extras.jade b/app/partials/includes/modules/admin/admin-us-extras.jade index 1655914a..94b2fef8 100644 --- a/app/partials/includes/modules/admin/admin-us-extras.jade +++ b/app/partials/includes/modules/admin/admin-us-extras.jade @@ -1,14 +1,18 @@ section.custom-fields-table.basic-table div.table-header div.row - div.custom-name Name - div.custom-description Description + div.custom-name + span Name + div.custom-description + span Description div.custom-options div.table-body div.row.single-custom-field span.icon.icon-drag-v - div.custom-name Custom field name - div.custom-description Custom field looong Description + div.custom-name + span Custom field name + div.custom-description + span Custom field looong Description div.custom-options div.custom-options-wrapper a.edit-webhook.icon.icon-edit(href="", title="Edit Custom Field") diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-fields.scss index bba0da2d..d110cf23 100644 --- a/app/styles/modules/admin/admin-custom-fields.scss +++ b/app/styles/modules/admin/admin-custom-fields.scss @@ -7,7 +7,18 @@ .row { border-bottom: 0; padding: .5rem 0; - &:hover { + + } + .table-header { + @extend %bold; + border-bottom: 1px solid $gray-light; + .custom-name span, + .custom-description span { + padding-left: 1.1rem; + } + } + .table-body { + .row:hover { background: rgba($fresh-taiga, .05); cursor: move; transition: background .2s linear; @@ -17,12 +28,12 @@ transition: opacity .2s linear; } } - } - .table-header { - @extend %bold; - border-bottom: 1px solid $gray-light; - } - .table-body { + form { + &.row:hover { + background: none; + cursor: default; + } + } .custom-description { color: $gray-light; } @@ -34,7 +45,7 @@ .icon-drag-v { color: $gray-light; opacity: 0; - padding: 0 .5rem; + padding: 0 .1rem; transition: color .2s linear; vertical-align: middle; &:hover { @@ -78,10 +89,6 @@ transition: opacity .3s linear; } form { - &.row:hover { - background: none; - cursor: default; - } .custom-options-wrapper { opacity: 1; } From 05a89bdf32d1bb931fb2d4245a86ab913ac90c75 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Feb 2015 11:34:29 +0100 Subject: [PATCH 118/207] Custom fields in US detail --- .../modules/common/custom-fields.jade | 21 +++++ app/partials/us/us-detail.jade | 3 + app/styles/modules/common/custom-fields.scss | 76 +++++++++++++++++++ main-sass.js | 1 + 4 files changed, 101 insertions(+) create mode 100644 app/partials/includes/modules/common/custom-fields.jade create mode 100644 app/styles/modules/common/custom-fields.scss diff --git a/app/partials/includes/modules/common/custom-fields.jade b/app/partials/includes/modules/common/custom-fields.jade new file mode 100644 index 00000000..cf2be606 --- /dev/null +++ b/app/partials/includes/modules/common/custom-fields.jade @@ -0,0 +1,21 @@ +section.duty-custom-fields + div.custom-fields-header + span Custom Fields + // Remove .open class on click on this button in both .icon and .custom-fields-body to close + a.icon.icon-arrow-bottom.open + div.custom-fields-body.open + div.custom-field-single + div.custom-field-data + span.custom-field-name Name + span.custom-field-description This is the description + div.custom-field-value + span Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Aenean commodo ligula eget dolor. Aenean massa. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Donec quam felis, ultricies nec, pellentesque eu, pretium quis, sem. Nulla consequat massa quis enim. Donec pede justo, fringilla vel, aliquet nec. + div.custom-field-options + a.icon.icon-edit(href="", title="Edit Custom Field") + form.custom-field-single + div.custom-field-data + label.custom-field-name(for="custom-field-description") Name + div.custom-field-value + input#custom-field-description(type="text", placeholder="This is the description") + div.custom-field-options + a.icon.icon-floppy(href="", title="Save Custom Field") diff --git a/app/partials/us/us-detail.jade b/app/partials/us/us-detail.jade index 5a78e15c..3c21553c 100644 --- a/app/partials/us/us-detail.jade +++ b/app/partials/us/us-detail.jade @@ -39,6 +39,9 @@ div.wrapper(ng-controller="UserStoryDetailController as ctrl", section.duty-content(tg-editable-description, ng-model="us", required-perm="modify_us") + // IF Custom Fields + include ../includes/modules/common/custom-fields + include ../includes/modules/related-tasks tg-attachments(ng-model="us", type="us") diff --git a/app/styles/modules/common/custom-fields.scss b/app/styles/modules/common/custom-fields.scss new file mode 100644 index 00000000..01105689 --- /dev/null +++ b/app/styles/modules/common/custom-fields.scss @@ -0,0 +1,76 @@ +.duty-custom-fields { + margin-bottom: 2rem; + .custom-fields-header { + @extend %bold; + align-content: space-between; + align-items: center; + background: $whitish; + display: flex; + justify-content: space-between; + padding: .5rem 1rem; + .icon-arrow-bottom { + @extend %large; + cursor: pointer; + transform: rotate(-90deg); + transition: transform .2s linear; + &.open { + transform: rotate(0); + transition: transform .2s linear; + } + } + } + .custom-fields-body { + @include slide(1000px, hidden, $min: 0); + } + .custom-field-single { + align-content: center; + align-items: center; + border-bottom: 1px solid $whitish; + display: flex; + padding: 1rem; + &:last-child { + border-bottom: 0; + } + &:hover { + .custom-field-options { + opacity: 1; + } + } + .custom-field-options { + opacity: 0; + transition: opacity .2s linear; + a { + color: $gray-light; + } + a:hover { + color: $green-taiga; + } + } + } + .custom-field-data { + flex: 0; + flex-basis: 200px; + .custom-field-name { + @extend %bold; + display: block; + } + .custom-field-description { + @extend %small; + color: $gray-light; + display: block; + line-height: .9rem; + } + } + .custom-field-value { + flex: 1; + padding-right: 2rem; + } + form { + label { + cursor: pointer; + } + input { + width: 100%; + } + } +} diff --git a/main-sass.js b/main-sass.js index 909931e1..f729d1e6 100644 --- a/main-sass.js +++ b/main-sass.js @@ -75,6 +75,7 @@ exports.files = function () { 'modules/common/history', 'modules/common/wizard', 'modules/common/external-reference', + 'modules/common/custom-fields', //Project modules 'modules/home-projects-list', From c45a51f3130b4381ab3d2880e96571669ea1b3dd Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Wed, 18 Feb 2015 15:16:11 +0100 Subject: [PATCH 119/207] Detail integration --- .../modules/common/custom-field-values.coffee | 190 ++++++++++++++++++ app/coffee/modules/resources.coffee | 6 + .../resources/custom-field-values.coffee | 35 ++++ .../custom-attribute-value-edit.jade | 14 ++ .../custom-attribute-value.jade | 17 ++ .../custom-attributes-values.jade | 7 + .../modules/common/custom-fields.jade | 21 -- app/partials/issue/issues-detail.jade | 3 + app/partials/task/task-detail.jade | 3 + app/partials/us/us-detail.jade | 4 +- 10 files changed, 277 insertions(+), 23 deletions(-) create mode 100644 app/coffee/modules/common/custom-field-values.coffee create mode 100644 app/coffee/modules/resources/custom-field-values.coffee create mode 100644 app/partials/custom-attributes/custom-attribute-value-edit.jade create mode 100644 app/partials/custom-attributes/custom-attribute-value.jade create mode 100644 app/partials/custom-attributes/custom-attributes-values.jade delete mode 100644 app/partials/includes/modules/common/custom-fields.jade diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee new file mode 100644 index 00000000..23689430 --- /dev/null +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -0,0 +1,190 @@ +### +# Copyright (C) 2014 Andrey Antukh +# Copyright (C) 2014 Jesús Espino Garcia +# Copyright (C) 2014 David Barragán Merino +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +# File: modules/common/custom-field-values.coffee +### + +taiga = @.taiga +bindMethods = @.taiga.bindMethods +bindOnce = @.taiga.bindOnce +debounce = @.taiga.debounce +generateHash = taiga.generateHash + +module = angular.module("taigaCommon") + + +class CustomAttributesValuesController extends taiga.Controller + @.$inject = ["$scope", "$rootScope", "$tgRepo", "$tgResources", "$tgConfirm", "$q"] + + constructor: (@scope, @rootscope, @repo, @rs, @confirm, @q) -> + bindMethods(@) + @.type = null + @.objectId = null + @.projectId = null + @.customAttributes = [] + @.customAttributesValues = null + + initialize: (type, objectId) -> + @.project = @scope.project + @.type = type + @.objectId = objectId + @.projectId = @scope.projectId + + loadCustomAttributesValues: -> + return @.customAttributesValues if not @.objectId + return @rs.customAttributesValues.get(@.type, @.objectId).then (customAttributesValues) => + @.customAttributes = @.project["#{@.type}_custom_attributes"] + @.customAttributesValues = customAttributesValues + return customAttributesValues + + getAttributeValue: (attribute) -> + attributeValue = _.clone(attribute, false) + attributeValue.value = @.customAttributesValues.attributes_values[attribute.id] + return attributeValue + + updateAttributeValue: (attributeValue) -> + onSuccess = => + onError = (response) => + @confirm.notify("error") + return @q.reject() + + # We need to update the full array so angular understand the model is modified + attributesValues = _.clone(@.customAttributesValues.attributes_values, true) + attributesValues[attributeValue.id] = attributeValue.value + @.customAttributesValues.attributes_values = attributesValues + @.customAttributesValues.id = @.objectId + return @repo.save(@.customAttributesValues).then(onSuccess, onError) + +CustomAttributesValuesDirective = ($templates, $storage) -> + template = $templates.get("custom-attributes/custom-attributes-values.html", true) + collapsedHash = generateHash(["custom-attributes-collapsed"]) + + link = ($scope, $el, $attrs, $ctrls) -> + $ctrl = $ctrls[0] + $model = $ctrls[1] + + bindOnce $scope, $attrs.ngModel, (value) -> + $ctrl.initialize($attrs.type, value.id) + $ctrl.loadCustomAttributesValues() + + $el.on "click", ".custom-fields-header a", -> + collapsed = not($storage.get(collapsedHash) or false) + $storage.set(collapsedHash, collapsed) + if collapsed + $el.find(".custom-fields-header a").removeClass("open") + $el.find(".custom-fields-body").removeClass("open") + else + $el.find(".custom-fields-header a").addClass("open") + $el.find(".custom-fields-body").addClass("open") + + $scope.$on "$destroy", -> + $el.off() + + templateFn = ($el, $attrs) -> + collapsed = $storage.get(collapsedHash) or false + + return template({ + requiredEditionPerm: $attrs.requiredEditionPerm + collapsed: collapsed + }) + + return { + require: ["tgCustomAttributesValues", "ngModel"] + controller: CustomAttributesValuesController + controllerAs: "ctrl" + restrict: "AE" + scope: true + link: link + template: templateFn + } + +module.directive("tgCustomAttributesValues", ["$tgTemplate", "$tgStorage", CustomAttributesValuesDirective]) + + +CustomAttributeValueDirective = ($template) -> + template = $template.get("custom-attributes/custom-attribute-value.html", true) + templateEdit = $template.get("custom-attributes/custom-attribute-value-edit.html", true) + + link = ($scope, $el, $attrs, $ctrl) -> + render = (attributeValue, edit=false) -> + ctx = { + id: attributeValue.id + name: attributeValue.name + description: attributeValue.description + value: attributeValue.value + isEditable: isEditable() + } + + if edit + html = templateEdit(ctx) + else + html = template(ctx) + + $el.html(html) + + isEditable = -> + permissions = $scope.project.my_permissions + requiredEditionPerm = $attrs.requiredEditionPerm + return permissions.indexOf(requiredEditionPerm) > -1 + + saveAttributeValue = -> + attributeValue.value = $el.find("input").val() + + $scope.$apply -> + $ctrl.updateAttributeValue(attributeValue).then -> + render(attributeValue, false) + + $el.on "keyup", "input[name=description]", (event) -> + if event.keyCode == 13 + submit(event) + else if event.keyCode == 27 + render(attributeValue, false) + + ## Actions (on view mode) + $el.on "click", ".custom-field-value.read-mode", -> + return if not isEditable() + render(attributeValue, true) + $el.find("input[name='description']").focus().select() + + $el.on "click", "a.icon-edit", (event) -> + event.preventDefault() + render(attributeValue, true) + $el.find("input[name='description']").focus().select() + + ## Actions (on edit mode) + submit = debounce 2000, (event) => + event.preventDefault() + saveAttributeValue() + + $el.on "submit", "form", submit + $el.on "click", "a.icon-floppy", submit + + $scope.$on "$destroy", -> + $el.off() + + # Bootstrap + attributeValue = $scope.$eval($attrs.tgCustomAttributeValue) + render(attributeValue) + + return { + link: link + require: "^tgCustomAttributesValues" + restrict: "AE" + } + +module.directive("tgCustomAttributeValue", ["$tgTemplate", CustomAttributeValueDirective]) diff --git a/app/coffee/modules/resources.coffee b/app/coffee/modules/resources.coffee index 9f067e78..3c84802c 100644 --- a/app/coffee/modules/resources.coffee +++ b/app/coffee/modules/resources.coffee @@ -102,6 +102,11 @@ urls = { "attachments/task": "/tasks/attachments" "attachments/wiki_page": "/wiki/attachments" + # Custom field values + "custom-attributes-values/userstory": "/userstories/custom-attributes-values" + "custom-attributes-values/issue": "/issues/custom-attributes-values" + "custom-attributes-values/task": "/tasks/custom-attributes-values" + # Feedback "feedback": "/feedback" @@ -145,6 +150,7 @@ module.run([ "$tgWikiResourcesProvider", "$tgSearchResourcesProvider", "$tgAttachmentsResourcesProvider", + "$tgCustomAttributesValuesResourcesProvider", "$tgMdRenderResourcesProvider", "$tgHistoryResourcesProvider", "$tgKanbanResourcesProvider", diff --git a/app/coffee/modules/resources/custom-field-values.coffee b/app/coffee/modules/resources/custom-field-values.coffee new file mode 100644 index 00000000..cb0415b3 --- /dev/null +++ b/app/coffee/modules/resources/custom-field-values.coffee @@ -0,0 +1,35 @@ +### +# Copyright (C) 2014 Andrey Antukh +# Copyright (C) 2014 Jesús Espino Garcia +# Copyright (C) 2014 David Barragán Merino +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +# File: modules/resources/custom-field-values.coffee +### + +taiga = @.taiga + +resourceProvider = ($rootScope, $config, $urls, $model, $repo, $auth, $q) -> + service = {} + + service.get = (type, objectId) -> + return $repo.queryOne("custom-attributes-values/#{type}", objectId) + + return (instance) -> + instance.customAttributesValues = service + +module = angular.module("taigaResources") +module.factory("$tgCustomAttributesValuesResourcesProvider", ["$rootScope", "$tgConfig", "$tgUrls", "$tgModel", "$tgRepo", + "$tgAuth", "$q", resourceProvider]) diff --git a/app/partials/custom-attributes/custom-attribute-value-edit.jade b/app/partials/custom-attributes/custom-attribute-value-edit.jade new file mode 100644 index 00000000..675fd11e --- /dev/null +++ b/app/partials/custom-attributes/custom-attribute-value-edit.jade @@ -0,0 +1,14 @@ +form.custom-field-single + div.custom-field-data + label.custom-field-name(for="custom-field-description") + <%- name %> + <% if (description){ %> + span.custom-field-description + <%- description %> + <% } %> + + div.custom-field-value + input#custom-field-description(name="description", type="text", placeholder!="<%- value %>") + + div.custom-field-options + a.icon.icon-floppy(href="", title="Save Custom Field") diff --git a/app/partials/custom-attributes/custom-attribute-value.jade b/app/partials/custom-attributes/custom-attribute-value.jade new file mode 100644 index 00000000..b2502c04 --- /dev/null +++ b/app/partials/custom-attributes/custom-attribute-value.jade @@ -0,0 +1,17 @@ +div.custom-field-single + div.custom-field-data + span.custom-field-name + <%- name %> + <% if (description){ %> + span.custom-field-description + <%- description %> + <% } %> + + div.custom-field-value.read-mode + span + <%- value %> + + <% if (isEditable) { %> + div.custom-field-options + a.icon.icon-edit(href="", title="Edit Custom Field") + <% } %> diff --git a/app/partials/custom-attributes/custom-attributes-values.jade b/app/partials/custom-attributes/custom-attributes-values.jade new file mode 100644 index 00000000..7062caed --- /dev/null +++ b/app/partials/custom-attributes/custom-attributes-values.jade @@ -0,0 +1,7 @@ +section.duty-custom-fields(ng-show="ctrl.customAttributesValues") + div.custom-fields-header + span Custom Fields + // Remove .open class on click on this button in both .icon and .custom-fields-body to close + a.icon.icon-arrow-bottom(class!="<% if (!collapsed) { %>open<% } %>") + div.custom-fields-body(class!="<% if (!collapsed) { %>open<% } %>") + div(ng-repeat="att in ctrl.customAttributes", tg-custom-attribute-value="ctrl.getAttributeValue(att)", required-edition-perm!="<%- requiredEditionPerm %>") diff --git a/app/partials/includes/modules/common/custom-fields.jade b/app/partials/includes/modules/common/custom-fields.jade deleted file mode 100644 index cf2be606..00000000 --- a/app/partials/includes/modules/common/custom-fields.jade +++ /dev/null @@ -1,21 +0,0 @@ -section.duty-custom-fields - div.custom-fields-header - span Custom Fields - // Remove .open class on click on this button in both .icon and .custom-fields-body to close - a.icon.icon-arrow-bottom.open - div.custom-fields-body.open - div.custom-field-single - div.custom-field-data - span.custom-field-name Name - span.custom-field-description This is the description - div.custom-field-value - span Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Aenean commodo ligula eget dolor. Aenean massa. Cum sociis natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus. Donec quam felis, ultricies nec, pellentesque eu, pretium quis, sem. Nulla consequat massa quis enim. Donec pede justo, fringilla vel, aliquet nec. - div.custom-field-options - a.icon.icon-edit(href="", title="Edit Custom Field") - form.custom-field-single - div.custom-field-data - label.custom-field-name(for="custom-field-description") Name - div.custom-field-value - input#custom-field-description(type="text", placeholder="This is the description") - div.custom-field-options - a.icon.icon-floppy(href="", title="Save Custom Field") diff --git a/app/partials/issue/issues-detail.jade b/app/partials/issue/issues-detail.jade index 8c90aeb9..ab528bc9 100644 --- a/app/partials/issue/issues-detail.jade +++ b/app/partials/issue/issues-detail.jade @@ -35,6 +35,9 @@ div.wrapper(ng-controller="IssueDetailController as ctrl", section.duty-content(tg-editable-description, ng-model="issue", required-perm="modify_issue") + // Custom Fields + tg-custom-attributes-values(ng-model="issue", type="issue", project="project", required-edition-perm="modify_issue") + tg-attachments(ng-model="issue", type="issue") tg-history(ng-model="issue", type="issue") diff --git a/app/partials/task/task-detail.jade b/app/partials/task/task-detail.jade index dd0075a0..4d149454 100644 --- a/app/partials/task/task-detail.jade +++ b/app/partials/task/task-detail.jade @@ -40,6 +40,9 @@ div.wrapper(ng-controller="TaskDetailController as ctrl", section.duty-content(tg-editable-description, ng-model="task", required-perm="modify_task") + // Custom Fields + tg-custom-attributes-values(ng-model="task", type="task", project="project", required-edition-perm="modify_task") + tg-attachments(ng-model="task", type="task") tg-history(ng-model="task", type="task") diff --git a/app/partials/us/us-detail.jade b/app/partials/us/us-detail.jade index 3c21553c..8c8708a1 100644 --- a/app/partials/us/us-detail.jade +++ b/app/partials/us/us-detail.jade @@ -39,8 +39,8 @@ div.wrapper(ng-controller="UserStoryDetailController as ctrl", section.duty-content(tg-editable-description, ng-model="us", required-perm="modify_us") - // IF Custom Fields - include ../includes/modules/common/custom-fields + // Custom Fields + tg-custom-attributes-values(ng-model="us", type="userstory", project="project", required-edition-perm="modify_us") include ../includes/modules/related-tasks From c919ae22d45d266c952328198a9f7ea7df9bc43c Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Thu, 19 Feb 2015 13:58:07 +0100 Subject: [PATCH 120/207] Show custom attributes when project have got --- app/partials/custom-attributes/custom-attributes-values.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/custom-attributes/custom-attributes-values.jade b/app/partials/custom-attributes/custom-attributes-values.jade index 7062caed..cadbb100 100644 --- a/app/partials/custom-attributes/custom-attributes-values.jade +++ b/app/partials/custom-attributes/custom-attributes-values.jade @@ -1,4 +1,4 @@ -section.duty-custom-fields(ng-show="ctrl.customAttributesValues") +section.duty-custom-fields(ng-show="ctrl.customAttributes.length") div.custom-fields-header span Custom Fields // Remove .open class on click on this button in both .icon and .custom-fields-body to close From 74331bbbc0d380129b3ddfeed88bab6b8016861b Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 20 Feb 2015 08:57:11 +0100 Subject: [PATCH 121/207] Fixing issuaes when displaying custom fields on detail --- app/coffee/modules/common/custom-field-values.coffee | 10 ++++++---- .../custom-attributes/custom-attribute-value-edit.jade | 2 +- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index 23689430..26aabacf 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -116,21 +116,22 @@ CustomAttributesValuesDirective = ($templates, $storage) -> module.directive("tgCustomAttributesValues", ["$tgTemplate", "$tgStorage", CustomAttributesValuesDirective]) -CustomAttributeValueDirective = ($template) -> +CustomAttributeValueDirective = ($template, $selectedText) -> template = $template.get("custom-attributes/custom-attribute-value.html", true) templateEdit = $template.get("custom-attributes/custom-attribute-value-edit.html", true) link = ($scope, $el, $attrs, $ctrl) -> render = (attributeValue, edit=false) -> + value = attributeValue.value ctx = { id: attributeValue.id name: attributeValue.name description: attributeValue.description - value: attributeValue.value + value: value isEditable: isEditable() } - if edit + if edit or not value html = templateEdit(ctx) else html = template(ctx) @@ -158,6 +159,7 @@ CustomAttributeValueDirective = ($template) -> ## Actions (on view mode) $el.on "click", ".custom-field-value.read-mode", -> return if not isEditable() + return if $selectedText.get().length render(attributeValue, true) $el.find("input[name='description']").focus().select() @@ -187,4 +189,4 @@ CustomAttributeValueDirective = ($template) -> restrict: "AE" } -module.directive("tgCustomAttributeValue", ["$tgTemplate", CustomAttributeValueDirective]) +module.directive("tgCustomAttributeValue", ["$tgTemplate", "$selectedText", CustomAttributeValueDirective]) diff --git a/app/partials/custom-attributes/custom-attribute-value-edit.jade b/app/partials/custom-attributes/custom-attribute-value-edit.jade index 675fd11e..63fdd4b7 100644 --- a/app/partials/custom-attributes/custom-attribute-value-edit.jade +++ b/app/partials/custom-attributes/custom-attribute-value-edit.jade @@ -8,7 +8,7 @@ form.custom-field-single <% } %> div.custom-field-value - input#custom-field-description(name="description", type="text", placeholder!="<%- value %>") + input#custom-field-description(name="description", type="text", value!="<%- value %>") div.custom-field-options a.icon.icon-floppy(href="", title="Save Custom Field") From e1c0e2e7afa3bb0e7fd48ca1098fdd143b8d4a21 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 08:57:49 +0100 Subject: [PATCH 122/207] Edit basic custom field style and visual behavior --- .../modules/common/custom-field-values.coffee | 2 ++ app/styles/modules/common/custom-fields.scss | 13 +++++++------ 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index 26aabacf..231929a9 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -145,6 +145,7 @@ CustomAttributeValueDirective = ($template, $selectedText) -> saveAttributeValue = -> attributeValue.value = $el.find("input").val() + $el.find('.custom-field-single').removeClass('editable') $scope.$apply -> $ctrl.updateAttributeValue(attributeValue).then -> @@ -167,6 +168,7 @@ CustomAttributeValueDirective = ($template, $selectedText) -> event.preventDefault() render(attributeValue, true) $el.find("input[name='description']").focus().select() + $el.find('.custom-field-single').addClass('editable') ## Actions (on edit mode) submit = debounce 2000, (event) => diff --git a/app/styles/modules/common/custom-fields.scss b/app/styles/modules/common/custom-fields.scss index 01105689..2856188a 100644 --- a/app/styles/modules/common/custom-fields.scss +++ b/app/styles/modules/common/custom-fields.scss @@ -23,19 +23,20 @@ @include slide(1000px, hidden, $min: 0); } .custom-field-single { - align-content: center; - align-items: center; border-bottom: 1px solid $whitish; display: flex; padding: 1rem; - &:last-child { - border-bottom: 0; - } &:hover { .custom-field-options { opacity: 1; } } + &.editable { + .custom-field-options { + align-items: center; + display: flex; + } + } .custom-field-options { opacity: 0; transition: opacity .2s linear; @@ -63,7 +64,7 @@ } .custom-field-value { flex: 1; - padding-right: 2rem; + padding: 0 1rem 0 2rem; } form { label { From 9f6f080a3932b69e2d011a6afe093f098c29fca6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 20 Feb 2015 09:02:26 +0100 Subject: [PATCH 123/207] Fixed custom attribute edition template --- app/coffee/modules/common/custom-field-values.coffee | 2 -- app/partials/custom-attributes/custom-attribute-value-edit.jade | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index 231929a9..26aabacf 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -145,7 +145,6 @@ CustomAttributeValueDirective = ($template, $selectedText) -> saveAttributeValue = -> attributeValue.value = $el.find("input").val() - $el.find('.custom-field-single').removeClass('editable') $scope.$apply -> $ctrl.updateAttributeValue(attributeValue).then -> @@ -168,7 +167,6 @@ CustomAttributeValueDirective = ($template, $selectedText) -> event.preventDefault() render(attributeValue, true) $el.find("input[name='description']").focus().select() - $el.find('.custom-field-single').addClass('editable') ## Actions (on edit mode) submit = debounce 2000, (event) => diff --git a/app/partials/custom-attributes/custom-attribute-value-edit.jade b/app/partials/custom-attributes/custom-attribute-value-edit.jade index 63fdd4b7..d3c3aabc 100644 --- a/app/partials/custom-attributes/custom-attribute-value-edit.jade +++ b/app/partials/custom-attributes/custom-attribute-value-edit.jade @@ -1,4 +1,4 @@ -form.custom-field-single +form.custom-field-single.editable div.custom-field-data label.custom-field-name(for="custom-field-description") <%- name %> From 4d2fe26be9453474f127203f69ffa1b08c9a2cf6 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 20 Feb 2015 09:46:31 +0100 Subject: [PATCH 124/207] Fixing hash generation --- app/coffee/modules/common/custom-field-values.coffee | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index 26aabacf..a9aecefd 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -72,7 +72,8 @@ class CustomAttributesValuesController extends taiga.Controller CustomAttributesValuesDirective = ($templates, $storage) -> template = $templates.get("custom-attributes/custom-attributes-values.html", true) - collapsedHash = generateHash(["custom-attributes-collapsed"]) + collapsedHash = (type) -> + return generateHash(["custom-attributes-collapsed", type]) link = ($scope, $el, $attrs, $ctrls) -> $ctrl = $ctrls[0] @@ -83,8 +84,9 @@ CustomAttributesValuesDirective = ($templates, $storage) -> $ctrl.loadCustomAttributesValues() $el.on "click", ".custom-fields-header a", -> - collapsed = not($storage.get(collapsedHash) or false) - $storage.set(collapsedHash, collapsed) + hash = collapsedHash($attrs.type) + collapsed = not($storage.get(hash) or false) + $storage.set(hash, collapsed) if collapsed $el.find(".custom-fields-header a").removeClass("open") $el.find(".custom-fields-body").removeClass("open") @@ -96,7 +98,7 @@ CustomAttributesValuesDirective = ($templates, $storage) -> $el.off() templateFn = ($el, $attrs) -> - collapsed = $storage.get(collapsedHash) or false + collapsed = $storage.get(collapsedHash($attrs.type)) or false return template({ requiredEditionPerm: $attrs.requiredEditionPerm From 408c6f95ccb0f4f1e4b650aad7f9351f5174b8b9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Fri, 20 Feb 2015 16:25:12 +0100 Subject: [PATCH 125/207] Update, Delete and Order Custom Attributes --- app/coffee/app.coffee | 25 ++- .../modules/admin/project-values.coffee | 194 ++++++++++++++++++ app/coffee/modules/base.coffee | 2 + app/coffee/modules/resources.coffee | 10 +- ...coffee => custom-attributes-values.coffee} | 0 .../resources/custom-attributes.coffee | 48 +++++ .../admin-project-values-issue-extras.jade | 16 ++ .../admin-project-values-task-extras.jade | 16 ++ .../admin/admin-project-values-us-extras.jade | 12 +- .../modules/admin-submenu-project-values.jade | 10 + .../admin/admin-custom-attributes.jade | 46 +++++ .../modules/admin/admin-us-extras.jade | 29 --- ...elds.scss => admin-custom-attributes.scss} | 0 main-sass.js | 2 +- 14 files changed, 365 insertions(+), 45 deletions(-) rename app/coffee/modules/resources/{custom-field-values.coffee => custom-attributes-values.coffee} (100%) create mode 100644 app/coffee/modules/resources/custom-attributes.coffee create mode 100644 app/partials/admin/admin-project-values-issue-extras.jade create mode 100644 app/partials/admin/admin-project-values-task-extras.jade create mode 100644 app/partials/includes/modules/admin/admin-custom-attributes.jade delete mode 100644 app/partials/includes/modules/admin/admin-us-extras.jade rename app/styles/modules/admin/{admin-custom-fields.scss => admin-custom-attributes.scss} (100%) diff --git a/app/coffee/app.coffee b/app/coffee/app.coffee index aaeb7abd..76e82774 100644 --- a/app/coffee/app.coffee +++ b/app/coffee/app.coffee @@ -39,17 +39,23 @@ taiga.sessionId = taiga.generateUniqueSessionIdentifier() configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEventsProvider, tgLoaderProvider) -> $routeProvider.when("/", {templateUrl: "project/projects.html", resolve: {loader: tgLoaderProvider.add()}}) + $routeProvider.when("/project/:pslug/", {templateUrl: "project/project.html"}) - $routeProvider.when("/project/:pslug/backlog", - {templateUrl: "backlog/backlog.html", resolve: {loader: tgLoaderProvider.add()}}) - $routeProvider.when("/project/:pslug/taskboard/:sslug", - {templateUrl: "taskboard/taskboard.html", resolve: {loader: tgLoaderProvider.add()}}) + $routeProvider.when("/project/:pslug/search", {templateUrl: "search/search.html", reloadOnSearch: false}) + + $routeProvider.when("/project/:pslug/backlog", + {templateUrl: "backlog/backlog.html", resolve: {loader: tgLoaderProvider.add()}}) + $routeProvider.when("/project/:pslug/kanban", {templateUrl: "kanban/kanban.html", resolve: {loader: tgLoaderProvider.add()}}) + # Milestone + $routeProvider.when("/project/:pslug/taskboard/:sslug", + {templateUrl: "taskboard/taskboard.html", resolve: {loader: tgLoaderProvider.add()}}) + # User stories $routeProvider.when("/project/:pslug/us/:usref", {templateUrl: "us/us-detail.html", resolve: {loader: tgLoaderProvider.add()}}) @@ -74,7 +80,7 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven $routeProvider.when("/project/:pslug/issue/:issueref", {templateUrl: "issue/issues-detail.html", resolve: {loader: tgLoaderProvider.add()}}) - # Admin + # Admin - Project Profile $routeProvider.when("/project/:pslug/admin/project-profile/details", {templateUrl: "admin/admin-project-profile.html"}) $routeProvider.when("/project/:pslug/admin/project-profile/default-values", @@ -83,6 +89,7 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-project-modules.html"}) $routeProvider.when("/project/:pslug/admin/project-profile/export", {templateUrl: "admin/admin-project-export.html"}) + # Admin Project Values $routeProvider.when("/project/:pslug/admin/project-values/us-status", {templateUrl: "admin/admin-project-values-us-status.html"}) $routeProvider.when("/project/:pslug/admin/project-values/us-points", @@ -91,6 +98,8 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-project-values-us-extras.html"}) $routeProvider.when("/project/:pslug/admin/project-values/task-status", {templateUrl: "admin/admin-project-values-task-status.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/task-extras", + {templateUrl: "admin/admin-project-values-task-extras.html"}) $routeProvider.when("/project/:pslug/admin/project-values/issue-status", {templateUrl: "admin/admin-project-values-issue-status.html"}) $routeProvider.when("/project/:pslug/admin/project-values/issue-types", @@ -99,10 +108,15 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-project-values-issue-priorities.html"}) $routeProvider.when("/project/:pslug/admin/project-values/issue-severities", {templateUrl: "admin/admin-project-values-issue-severities.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/issue-extras", + {templateUrl: "admin/admin-project-values-issue-extras.html"}) + # Admin - Memberships $routeProvider.when("/project/:pslug/admin/memberships", {templateUrl: "admin/admin-memberships.html"}) + # Admin - Roles $routeProvider.when("/project/:pslug/admin/roles", {templateUrl: "admin/admin-roles.html"}) + # Admin - Third Parties $routeProvider.when("/project/:pslug/admin/third-parties/webhooks", {templateUrl: "admin/admin-third-parties-webhooks.html"}) $routeProvider.when("/project/:pslug/admin/third-parties/github", @@ -111,6 +125,7 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-third-parties-gitlab.html"}) $routeProvider.when("/project/:pslug/admin/third-parties/bitbucket", {templateUrl: "admin/admin-third-parties-bitbucket.html"}) + # Admin - Contrib Plugins $routeProvider.when("/project/:pslug/admin/contrib/:plugin", {templateUrl: "contrib/main.html"}) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index bee3d41c..6cd085af 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -320,3 +320,197 @@ ColorSelectionDirective = () -> } module.directive("tgColorSelection", ColorSelectionDirective) + + +############################################################################# +## Custom Attributes Controller +############################################################################# + +class ProjectCustomAttributesController extends mixOf(taiga.Controller, taiga.PageMixin) + @.$inject = [ + "$scope", + "$rootScope", + "$tgRepo", + "$tgResources", + "$routeParams", + "$q", + "$tgLocation", + "$tgNavUrls", + "$appTitle", + ] + + constructor: (@scope, @rootscope, @repo, @rs, @params, @q, @location, @navUrls, @appTitle) -> + @scope.project = {} + + promise = @.loadInitialData() + + promise.then () => + @appTitle.set("Project Custom Attributes - " + @scope.sectionName + " - " + @scope.project.name) + + promise.then null, @.onInitialDataError.bind(@) + + loadInitialData: => + promise = @repo.resolve({pslug: @params.pslug}).then (data) => + @scope.projectId = data.project + return data + + return promise.then( => @q.all([ + @.loadProject(), + @.loadCustomAttributes(), + ])) + + ######################### + # Project + ######################### + + loadProject: => + return @rs.projects.get(@scope.projectId).then (project) => + @scope.project = project + @scope.$emit('project:loaded', project) + return project + + + ######################### + # Custom Attribute + ######################### + + loadCustomAttributes: => + return @rs.customAttributes[@scope.type].list(@scope.projectId).then (customAttributes) => + @scope.customAttributes = customAttributes + @scope.maxOrder = _.max(customAttributes, "order").order + return customAttributes + + + moveCustomAttributes: (attrModel, newIndex) => + customAttributes = @scope.customAttributes + r = customAttributes.indexOf(attrModel) + customAttributes.splice(r, 1) + customAttributes.splice(newIndex, 0, attrModel) + + _.each customAttributes, (val, idx) -> + val.order = idx + + @repo.saveAll(customAttributes) + + deleteCustomAttribute: (attrModel) => + return @repo.remove(attrModel) + + saveCustomAttribute: (attrModel) => + return @repo.save(attrModel) + +module.controller("ProjectCustomAttributesController", ProjectCustomAttributesController) + + +############################################################################# +## Custom Attributes Directive +############################################################################# + +ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> + link = ($scope, $el, $attrs) -> + $ctrl = $el.controller() + + $scope.$on "$destroy", -> + $el.off() + + ################################## + # Drag & Drop + ################################## + sortableEl = $el.find(".js-sortable") + + sortableEl.sortable({ + handle: ".js-view-custom-field", + dropOnEmpty: true + revert: 400 + axis: "y" + }) + + sortableEl.on "sortstop", (event, ui) -> + itemEl = ui.item + itemAttr = itemEl.scope().attr + itemIndex = itemEl.index() + $ctrl.moveCustomAttributes(itemAttr, itemIndex) + + ################################## + # New custom attribute + ################################## + + ################################## + # Edit custom attribute + ################################## + + showEditForm = (formEl) -> + formEl.find(".js-view-custom-field").addClass("hidden") + formEl.find(".js-edit-custom-field").removeClass("hidden") + + hideEditForm = (formEl) -> + formEl.find(".js-edit-custom-field").addClass("hidden") + formEl.find(".js-view-custom-field").removeClass("hidden") + + revertChangesInCustomAttribute = (formEl) -> + $scope.$apply -> + formEl.scope().attr.revert() + + update = (formEl) -> + onSucces = -> + $ctrl.loadCustomAttributes() + hideEditForm(formEl) + $confirm.notify("success") + + onError = -> + $confirm.notify("error") + + attr = formEl.scope().attr + $ctrl.saveCustomAttribute(attr).then(onSucces, onError) + + $el.on "click", ".js-edit-custom-field-button", (event) -> + event.preventDefault() + target = angular.element(event.currentTarget) + formEl = target.closest("form") + + showEditForm(formEl) + + $el.on "click", ".js-cancel-edit-custom-field-button", (event) -> + event.preventDefault() + target = angular.element(event.currentTarget) + formEl = target.closest("form") + + hideEditForm(formEl) + revertChangesInCustomAttribute(formEl) + + $el.on "click", ".js-update-custom-field-button", (event) -> + event.preventDefault() + target = angular.element(event.currentTarget) + formEl = target.closest("form") + + update(formEl) + + ################################## + # Delete custom attribute + ################################## + + deleteCustomAttribute = (formEl) -> + attr = formEl.scope().attr + + title = "Delete custom attribute" # i18n + message = attr.name + $confirm.askOnDelete(title, message).then (finish) -> + onSucces = -> + $ctrl.loadCustomAttributes().finally -> + finish() + + onError = -> + finish(false) + $confirm.notify("error", null, "We have not been able to delete '#{message}'.") + + $ctrl.deleteCustomAttribute(attr).then(onSucces, onError) + + $el.on "click", ".js-delete-custom-field-button", (event) -> + event.preventDefault() + target = angular.element(event.currentTarget) + formEl = target.closest("form") + + deleteCustomAttribute(formEl) + + return {link: link} + +module.directive("tgProjectCustomAttributes", ["$log", "$tgConfirm", "animationFrame", ProjectCustomAttributesDirective]) diff --git a/app/coffee/modules/base.coffee b/app/coffee/modules/base.coffee index 9324f20c..2ae8983e 100644 --- a/app/coffee/modules/base.coffee +++ b/app/coffee/modules/base.coffee @@ -88,10 +88,12 @@ urls = { "project-admin-project-values-us-points": "/project/:project/admin/project-values/us-points" "project-admin-project-values-us-extras": "/project/:project/admin/project-values/us-extras" "project-admin-project-values-task-status": "/project/:project/admin/project-values/task-status" + "project-admin-project-values-task-extras": "/project/:project/admin/project-values/task-extras" "project-admin-project-values-issue-status": "/project/:project/admin/project-values/issue-status" "project-admin-project-values-issue-types": "/project/:project/admin/project-values/issue-types" "project-admin-project-values-issue-priorities": "/project/:project/admin/project-values/issue-priorities" "project-admin-project-values-issue-severities": "/project/:project/admin/project-values/issue-severities" + "project-admin-project-values-issue-extras": "/project/:project/admin/project-values/issue-extras" "project-admin-memberships": "/project/:project/admin/memberships" "project-admin-roles": "/project/:project/admin/roles" "project-admin-third-parties-webhooks": "/project/:project/admin/third-parties/webhooks" diff --git a/app/coffee/modules/resources.coffee b/app/coffee/modules/resources.coffee index 3c84802c..a519d869 100644 --- a/app/coffee/modules/resources.coffee +++ b/app/coffee/modules/resources.coffee @@ -102,8 +102,13 @@ urls = { "attachments/task": "/tasks/attachments" "attachments/wiki_page": "/wiki/attachments" + # Custom Attributess + "custom-attributes/us": "/userstory-custom-attributes" + "custom-attributes/issue": "/issue-custom-attributes" + "custom-attributes/task": "/task-custom-attributes" + # Custom field values - "custom-attributes-values/userstory": "/userstories/custom-attributes-values" + "custom-attributes-values/us": "/userstories/custom-attributes-values" "custom-attributes-values/issue": "/issues/custom-attributes-values" "custom-attributes-values/task": "/tasks/custom-attributes-values" @@ -138,6 +143,8 @@ module.run([ "$log", "$tgResources", "$tgProjectsResourcesProvider", + "$tgCustomAttributesResourcesProvider", + "$tgCustomAttributesValuesResourcesProvider", "$tgMembershipsResourcesProvider", "$tgNotifyPoliciesResourcesProvider", "$tgInvitationsResourcesProvider", @@ -150,7 +157,6 @@ module.run([ "$tgWikiResourcesProvider", "$tgSearchResourcesProvider", "$tgAttachmentsResourcesProvider", - "$tgCustomAttributesValuesResourcesProvider", "$tgMdRenderResourcesProvider", "$tgHistoryResourcesProvider", "$tgKanbanResourcesProvider", diff --git a/app/coffee/modules/resources/custom-field-values.coffee b/app/coffee/modules/resources/custom-attributes-values.coffee similarity index 100% rename from app/coffee/modules/resources/custom-field-values.coffee rename to app/coffee/modules/resources/custom-attributes-values.coffee diff --git a/app/coffee/modules/resources/custom-attributes.coffee b/app/coffee/modules/resources/custom-attributes.coffee new file mode 100644 index 00000000..dde0e637 --- /dev/null +++ b/app/coffee/modules/resources/custom-attributes.coffee @@ -0,0 +1,48 @@ +### +# Copyright (C) 2014 Andrey Antukh +# Copyright (C) 2014 Jesús Espino Garcia +# Copyright (C) 2014 David Barragán Merino +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU Affero General Public License as +# published by the Free Software Foundation, either version 3 of the +# License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Affero General Public License for more details. +# +# You should have received a copy of the GNU Affero General Public License +# along with this program. If not, see . +# +# File: modules/resources/projects.coffee +### + + +taiga = @.taiga +sizeFormat = @.taiga.sizeFormat + + +resourceProvider = ($repo) -> + _list = (projectId, resource) -> + return $repo.queryMany(resource, {project: projectId}) + + service = { + us:{ + list: (projectId) -> _list(projectId, "custom-attributes/us") + } + task:{ + list: (projectId) -> _list(projectId, "custom-attributes/task") + } + issue: { + list: (projectId) -> _list(projectId, "custom-attributes/issue") + } + } + + return (instance) -> + instance.customAttributes = service + + +module = angular.module("taigaResources") +module.factory("$tgCustomAttributesResourcesProvider", ["$tgRepo", resourceProvider]) diff --git a/app/partials/admin/admin-project-values-issue-extras.jade b/app/partials/admin/admin-project-values-issue-extras.jade new file mode 100644 index 00000000..dc187831 --- /dev/null +++ b/app/partials/admin/admin-project-values-issue-extras.jade @@ -0,0 +1,16 @@ +div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="section='admin'; type='issue'; sectionName='Issue extra'") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-issue-extras") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common + include ../includes/components/mainTitle + p.admin-subtitle Specify here issue custom fields. The new field will appear on your issue detail. + + div.custom-field-options + a.button.button-green.js-add-custom-field(href="",title="Add a custom field in issues") Add custom field + + include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-task-extras.jade b/app/partials/admin/admin-project-values-task-extras.jade new file mode 100644 index 00000000..3e64934a --- /dev/null +++ b/app/partials/admin/admin-project-values-task-extras.jade @@ -0,0 +1,16 @@ +div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="section='admin'; type='task'; sectionName='Task extra'") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-task-extras") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common + include ../includes/components/mainTitle + p.admin-subtitle Specify here task custom fields. The new field will appear on your task detail. + + div.custom-field-options + a.button.button-green.js-add-custom-field(href="",title="Add a custom field in tasks") Add custom field + + include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-us-extras.jade b/app/partials/admin/admin-project-values-us-extras.jade index d5674a0b..ae41d124 100644 --- a/app/partials/admin/admin-project-values-us-extras.jade +++ b/app/partials/admin/admin-project-values-us-extras.jade @@ -1,6 +1,5 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='userstories'; type='points'; sectionName='Us points'", - type="points") +div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="section='admin'; type='us'; sectionName='US extra'") sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") include ../includes/modules/admin-menu @@ -12,9 +11,6 @@ div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", p.admin-subtitle Specify here user story custom fields. The new field will appear on your user story detail. div.custom-field-options - a.button.button-green.add-custom-field(href="",title="Add a custom field in user stories") Add custom field + a.button.button-green.js-add-custom-field(href="",title="Add a custom field in user stories") Add custom field - include ../includes/modules/admin/admin-us-extras - -div.lightbox.lightbox-generic-notion.notion-admin-project-values-us-points(id="notion-admin-project-values-us-points", tg-lb-notion) - include ../includes/modules/help-notions/lightbox-notion-admin-project-values-us-points + include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/includes/modules/admin-submenu-project-values.jade b/app/partials/includes/modules/admin-submenu-project-values.jade index 681b6520..31d45ae9 100644 --- a/app/partials/includes/modules/admin-submenu-project-values.jade +++ b/app/partials/includes/modules/admin-submenu-project-values.jade @@ -24,6 +24,11 @@ section.admin-submenu span.title Task statuses span.icon.icon-arrow-right + li#adminmenu-values-task-extras + a(href="", tg-nav="project-admin-project-values-task-extras:project=project.slug") + span.title Task extras + span.icon.icon-arrow-right + li#adminmenu-values-issue-status a(href="", tg-nav="project-admin-project-values-issue-status:project=project.slug") span.title Issue statuses @@ -43,3 +48,8 @@ section.admin-submenu a(href="", tg-nav="project-admin-project-values-issue-severities:project=project.slug") span.title Issue Severities span.icon.icon-arrow-right + + li#adminmenu-values-issue-extras + a(href="", tg-nav="project-admin-project-values-issue-extras:project=project.slug") + span.title Issue extras + span.icon.icon-arrow-right diff --git a/app/partials/includes/modules/admin/admin-custom-attributes.jade b/app/partials/includes/modules/admin/admin-custom-attributes.jade new file mode 100644 index 00000000..f9f9123f --- /dev/null +++ b/app/partials/includes/modules/admin/admin-custom-attributes.jade @@ -0,0 +1,46 @@ +section.custom-fields-table.basic-table + div.table-header + div.row + div.custom-name + span Name + div.custom-description + span Description + div.custom-options + + div.table-body + div.js-sortable + form.js-form(ng-repeat="attr in customAttributes track by attr.id") + div.row.single-custom-field.js-view-custom-field + span.icon.icon-drag-v + div.custom-name + span {{ attr.name }} + div.custom-description + span {{ attr.description }} + div.custom-options + div.custom-options-wrapper + a.js-edit-custom-field-button.icon.icon-edit(href="", title="Edit Custom Field") + a.js-delete-custom-field-button.icon.icon-delete(href="", title="Delete Custom Field") + + div.row.single-custom-field.js-edit-custom-field.hidden + fieldset.custom-name + input(type="text", placeholder="Set your custom field name", ng-model="attr.name", + data-required="true" data-maxlength="64") + fieldset.custom-description + input(type="text", placeholder="Set your custom field description", ng-model="attr.description") + + fieldset.custom-options + div.custom-options-wrapper + a.js-update-custom-field-button.icon.icon-floppy(href="", title="Update Custom Field") + a.js-cancel-edit-custom-field-button.icon.icon-delete(href="", title="Cancel edition") + + form.row.single-custom-field.js-new-custom-field.hidden(tg-new-custom-attribute) + fieldset.custom-name + input(type="text", placeholder="Set your custom field name", ng-model="newAttr.name", + data-required="true", data-maxlength="64") + fieldset.custom-description + input(type="text", placeholder="Set your custom field description", ng-model="newAttr.description") + + fieldset.custom-options + div.custom-options-wrapper + a.js-save-custom-field-button.icon.icon-floppy(href="", title="Save Custom Field") + a.js-cancel-new-custom-field-button.icon.icon-delete(href="", title="Cancel creation") diff --git a/app/partials/includes/modules/admin/admin-us-extras.jade b/app/partials/includes/modules/admin/admin-us-extras.jade deleted file mode 100644 index 94b2fef8..00000000 --- a/app/partials/includes/modules/admin/admin-us-extras.jade +++ /dev/null @@ -1,29 +0,0 @@ -section.custom-fields-table.basic-table - div.table-header - div.row - div.custom-name - span Name - div.custom-description - span Description - div.custom-options - div.table-body - div.row.single-custom-field - span.icon.icon-drag-v - div.custom-name - span Custom field name - div.custom-description - span Custom field looong Description - div.custom-options - div.custom-options-wrapper - a.edit-webhook.icon.icon-edit(href="", title="Edit Custom Field") - a.delete-webhook.icon.icon-delete(href="", title="Delete Custom Field") - form.row.single-custom-field - fieldset.custom-name - input(type="text", placeholder="Set your custom field name") - fieldset.custom-description - input(type="text", placeholder="Set your custom field description") - fieldset.custom-options - div.custom-options-wrapper - a.edit-webhook.icon.icon-floppy(href="", title="Save Custom Field") - a.delete-webhook.icon.icon-delete(href="", title="Delete Custom Field") - diff --git a/app/styles/modules/admin/admin-custom-fields.scss b/app/styles/modules/admin/admin-custom-attributes.scss similarity index 100% rename from app/styles/modules/admin/admin-custom-fields.scss rename to app/styles/modules/admin/admin-custom-attributes.scss diff --git a/main-sass.js b/main-sass.js index f729d1e6..e8314453 100644 --- a/main-sass.js +++ b/main-sass.js @@ -126,7 +126,7 @@ exports.files = function () { 'modules/admin/admin-membership-table', 'modules/admin/admin-project-profile', 'modules/admin/default-values', - 'modules/admin/admin-custom-fields', + 'modules/admin/admin-custom-attributes', 'modules/admin/project-values', 'modules/admin/third-parties', 'modules/admin/admin-third-parties-webhooks', From c8ad480846ff2693f38599ea72476bfa6b5f983b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Tue, 24 Feb 2015 08:53:10 +0100 Subject: [PATCH 126/207] Create new custom attributes --- .../modules/admin/project-values.coffee | 137 +++++++++++++++--- .../admin-project-values-issue-extras.jade | 3 +- .../admin-project-values-task-extras.jade | 3 +- .../admin/admin-project-values-us-extras.jade | 3 +- .../admin/admin-custom-attributes.jade | 18 ++- 5 files changed, 135 insertions(+), 29 deletions(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 6cd085af..3b4882cf 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -369,7 +369,6 @@ class ProjectCustomAttributesController extends mixOf(taiga.Controller, taiga.Pa @scope.$emit('project:loaded', project) return project - ######################### # Custom Attribute ######################### @@ -380,6 +379,14 @@ class ProjectCustomAttributesController extends mixOf(taiga.Controller, taiga.Pa @scope.maxOrder = _.max(customAttributes, "order").order return customAttributes + createCustomAttribute: (attrValues) => + return @repo.create("custom-attributes/#{@scope.type}", attrValues) + + saveCustomAttribute: (attrModel) => + return @repo.save(attrModel) + + deleteCustomAttribute: (attrModel) => + return @repo.remove(attrModel) moveCustomAttributes: (attrModel, newIndex) => customAttributes = @scope.customAttributes @@ -392,11 +399,6 @@ class ProjectCustomAttributesController extends mixOf(taiga.Controller, taiga.Pa @repo.saveAll(customAttributes) - deleteCustomAttribute: (attrModel) => - return @repo.remove(attrModel) - - saveCustomAttribute: (attrModel) => - return @repo.save(attrModel) module.controller("ProjectCustomAttributesController", ProjectCustomAttributesController) @@ -434,6 +436,88 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> # New custom attribute ################################## + showCreateForm = -> + $el.find(".js-new-custom-field").removeClass("hidden") + + hideCreateForm = -> + $el.find(".js-new-custom-field").addClass("hidden") + + showAddButton = -> + $el.find(".js-add-custom-field-button").removeClass("hidden") + + hideAddButton = -> + $el.find(".js-add-custom-field-button").addClass("hidden") + + showCancelButton = -> + $el.find(".js-cancel-new-custom-field-button").removeClass("hidden") + + hideCancelButton = -> + $el.find(".js-cancel-new-custom-field-button").addClass("hidden") + + resetNewAttr = -> + $scope.newAttr = {} + + create = (formEl) -> + form = formEl.checksley() + return if not form.validate() + + onSucces = => + $ctrl.loadCustomAttributes() + hideCreateForm() + resetNewAttr() + $confirm.notify("success") + + onError = (data) => + form.setErrors(data) + $confirm.notify("error") + + attr = $scope.newAttr + attr.project = $scope.projectId + attr.order = if $scope.maxOrder then $scope.maxOrder + 1 else 1 + + $ctrl.createCustomAttribute(attr).then(onSucces, onError) + + cancelCreate = -> + hideCreateForm() + resetNewAttr() + + $scope.$watch "customAttributes", (customAttributes) -> + return if not customAttributes + + if customAttributes.length == 0 + hideCancelButton() + hideAddButton() + showCreateForm() + else + hideCreateForm() + showAddButton() + showCancelButton() + + $el.on "click", ".js-add-custom-field-button", (event) -> + event.preventDefault() + + showCreateForm() + + $el.on "click", ".js-create-custom-field-button", debounce 2000, (event) -> + event.preventDefault() + target = angular.element(event.currentTarget) + formEl = target.closest("form") + + create(formEl) + + $el.on "click", ".js-cancel-new-custom-field-button", (event) -> + event.preventDefault() + + cancelCreate() + + $el.on "keyup", ".js-new-custom-field input", (event) -> + if event.keyCode == 13 # Enter + target = angular.element(event.currentTarget) + formEl = target.closest("form") + create(formEl) + else if event.keyCode == 27 # Esc + cancelCreate() + ################################## # Edit custom attribute ################################## @@ -451,17 +535,25 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> formEl.scope().attr.revert() update = (formEl) -> - onSucces = -> + form = formEl.checksley() + return if not form.validate() + + onSucces = => $ctrl.loadCustomAttributes() hideEditForm(formEl) $confirm.notify("success") - onError = -> + onError = (data) => + form.setErrors(data) $confirm.notify("error") attr = formEl.scope().attr $ctrl.saveCustomAttribute(attr).then(onSucces, onError) + cancelUpdate = (formEl) -> + hideEditForm(formEl) + revertChangesInCustomAttribute(formEl) + $el.on "click", ".js-edit-custom-field-button", (event) -> event.preventDefault() target = angular.element(event.currentTarget) @@ -469,21 +561,30 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> showEditForm(formEl) - $el.on "click", ".js-cancel-edit-custom-field-button", (event) -> - event.preventDefault() - target = angular.element(event.currentTarget) - formEl = target.closest("form") - - hideEditForm(formEl) - revertChangesInCustomAttribute(formEl) - - $el.on "click", ".js-update-custom-field-button", (event) -> + $el.on "click", ".js-update-custom-field-button", debounce 2000, (event) -> event.preventDefault() target = angular.element(event.currentTarget) formEl = target.closest("form") update(formEl) + $el.on "click", ".js-cancel-edit-custom-field-button", (event) -> + event.preventDefault() + target = angular.element(event.currentTarget) + formEl = target.closest("form") + + cancelUpdate(formEl) + + $el.on "keyup", ".js-edit-custom-field input", (event) -> + if event.keyCode == 13 # Enter + target = angular.element(event.currentTarget) + formEl = target.closest("form") + update(formEl) + else if event.keyCode == 27 # Esc + target = angular.element(event.currentTarget) + formEl = target.closest("form") + cancelUpdate(formEl) + ################################## # Delete custom attribute ################################## @@ -504,7 +605,7 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> $ctrl.deleteCustomAttribute(attr).then(onSucces, onError) - $el.on "click", ".js-delete-custom-field-button", (event) -> + $el.on "click", ".js-delete-custom-field-button", debounce 2000, (event) -> event.preventDefault() target = angular.element(event.currentTarget) formEl = target.closest("form") diff --git a/app/partials/admin/admin-project-values-issue-extras.jade b/app/partials/admin/admin-project-values-issue-extras.jade index dc187831..9335bfa3 100644 --- a/app/partials/admin/admin-project-values-issue-extras.jade +++ b/app/partials/admin/admin-project-values-issue-extras.jade @@ -11,6 +11,7 @@ div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributes p.admin-subtitle Specify here issue custom fields. The new field will appear on your issue detail. div.custom-field-options - a.button.button-green.js-add-custom-field(href="",title="Add a custom field in issues") Add custom field + a.button.button-green.js-add-custom-field-button(href="",title="Add a custom field in issues") + | Add custom field include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-task-extras.jade b/app/partials/admin/admin-project-values-task-extras.jade index 3e64934a..95b50a1d 100644 --- a/app/partials/admin/admin-project-values-task-extras.jade +++ b/app/partials/admin/admin-project-values-task-extras.jade @@ -11,6 +11,7 @@ div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributes p.admin-subtitle Specify here task custom fields. The new field will appear on your task detail. div.custom-field-options - a.button.button-green.js-add-custom-field(href="",title="Add a custom field in tasks") Add custom field + a.button.button-green.js-add-custom-field-button(href="",title="Add a custom field in tasks") + | Add custom field include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-us-extras.jade b/app/partials/admin/admin-project-values-us-extras.jade index ae41d124..55523d97 100644 --- a/app/partials/admin/admin-project-values-us-extras.jade +++ b/app/partials/admin/admin-project-values-us-extras.jade @@ -11,6 +11,7 @@ div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributes p.admin-subtitle Specify here user story custom fields. The new field will appear on your user story detail. div.custom-field-options - a.button.button-green.js-add-custom-field(href="",title="Add a custom field in user stories") Add custom field + a.button.button-green.js-add-custom-field-button(href="",title="Add a custom field in user stories") + | Add custom field include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/includes/modules/admin/admin-custom-attributes.jade b/app/partials/includes/modules/admin/admin-custom-attributes.jade index f9f9123f..318a60be 100644 --- a/app/partials/includes/modules/admin/admin-custom-attributes.jade +++ b/app/partials/includes/modules/admin/admin-custom-attributes.jade @@ -23,24 +23,26 @@ section.custom-fields-table.basic-table div.row.single-custom-field.js-edit-custom-field.hidden fieldset.custom-name - input(type="text", placeholder="Set your custom field name", ng-model="attr.name", - data-required="true" data-maxlength="64") + input(type="text", name="name", placeholder="Set your custom field name", + ng-model="attr.name", data-required="true" data-maxlength="64") fieldset.custom-description - input(type="text", placeholder="Set your custom field description", ng-model="attr.description") + input(type="text", name="description", placeholder="Set your custom field description", + ng-model="attr.description") fieldset.custom-options div.custom-options-wrapper a.js-update-custom-field-button.icon.icon-floppy(href="", title="Update Custom Field") a.js-cancel-edit-custom-field-button.icon.icon-delete(href="", title="Cancel edition") - form.row.single-custom-field.js-new-custom-field.hidden(tg-new-custom-attribute) + form.row.single-custom-field.js-new-custom-field.hidden fieldset.custom-name - input(type="text", placeholder="Set your custom field name", ng-model="newAttr.name", - data-required="true", data-maxlength="64") + input(type="text", name="name", placeholder="Set your custom field name", + ng-model="newAttr.name", data-required="true", data-maxlength="64") fieldset.custom-description - input(type="text", placeholder="Set your custom field description", ng-model="newAttr.description") + input(type="text", name="description", placeholder="Set your custom field description", + ng-model="newAttr.description") fieldset.custom-options div.custom-options-wrapper - a.js-save-custom-field-button.icon.icon-floppy(href="", title="Save Custom Field") + a.js-create-custom-field-button.icon.icon-floppy(href="", title="Save Custom Field") a.js-cancel-new-custom-field-button.icon.icon-delete(href="", title="Cancel creation") From 08f0a2262a9959f1ebb2ddd8713fe8336baa4f3b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Thu, 26 Feb 2015 12:34:48 +0100 Subject: [PATCH 127/207] Fix userstory custom attributes values --- .../modules/common/custom-field-values.coffee | 3 ++- app/coffee/modules/resources.coffee | 4 ++-- .../resources/custom-attributes-values.coffee | 21 +++++++++++++------ .../resources/custom-attributes.coffee | 4 ++-- .../admin/admin-project-values-us-extras.jade | 2 +- 5 files changed, 22 insertions(+), 12 deletions(-) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index a9aecefd..bb8c4042 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -47,7 +47,7 @@ class CustomAttributesValuesController extends taiga.Controller loadCustomAttributesValues: -> return @.customAttributesValues if not @.objectId - return @rs.customAttributesValues.get(@.type, @.objectId).then (customAttributesValues) => + return @rs.customAttributesValues[@.type].get(@.objectId).then (customAttributesValues) => @.customAttributes = @.project["#{@.type}_custom_attributes"] @.customAttributesValues = customAttributesValues return customAttributesValues @@ -70,6 +70,7 @@ class CustomAttributesValuesController extends taiga.Controller @.customAttributesValues.id = @.objectId return @repo.save(@.customAttributesValues).then(onSuccess, onError) + CustomAttributesValuesDirective = ($templates, $storage) -> template = $templates.get("custom-attributes/custom-attributes-values.html", true) collapsedHash = (type) -> diff --git a/app/coffee/modules/resources.coffee b/app/coffee/modules/resources.coffee index a519d869..1761ae39 100644 --- a/app/coffee/modules/resources.coffee +++ b/app/coffee/modules/resources.coffee @@ -103,12 +103,12 @@ urls = { "attachments/wiki_page": "/wiki/attachments" # Custom Attributess - "custom-attributes/us": "/userstory-custom-attributes" + "custom-attributes/userstory": "/userstory-custom-attributes" "custom-attributes/issue": "/issue-custom-attributes" "custom-attributes/task": "/task-custom-attributes" # Custom field values - "custom-attributes-values/us": "/userstories/custom-attributes-values" + "custom-attributes-values/userstory": "/userstories/custom-attributes-values" "custom-attributes-values/issue": "/issues/custom-attributes-values" "custom-attributes-values/task": "/tasks/custom-attributes-values" diff --git a/app/coffee/modules/resources/custom-attributes-values.coffee b/app/coffee/modules/resources/custom-attributes-values.coffee index cb0415b3..5322c639 100644 --- a/app/coffee/modules/resources/custom-attributes-values.coffee +++ b/app/coffee/modules/resources/custom-attributes-values.coffee @@ -21,15 +21,24 @@ taiga = @.taiga -resourceProvider = ($rootScope, $config, $urls, $model, $repo, $auth, $q) -> - service = {} +resourceProvider = ($repo) -> + _get = (objectId, resource) -> + return $repo.queryOne(resource, objectId) - service.get = (type, objectId) -> - return $repo.queryOne("custom-attributes-values/#{type}", objectId) + service = { + userstory: { + get: (objectId) -> _get(objectId, "custom-attributes-values/userstory") + } + task: { + get: (objectId) -> _get(objectId, "custom-attributes-values/task") + } + issue: { + get: (objectId) -> _get(objectId, "custom-attributes-values/issue") + } + } return (instance) -> instance.customAttributesValues = service module = angular.module("taigaResources") -module.factory("$tgCustomAttributesValuesResourcesProvider", ["$rootScope", "$tgConfig", "$tgUrls", "$tgModel", "$tgRepo", - "$tgAuth", "$q", resourceProvider]) +module.factory("$tgCustomAttributesValuesResourcesProvider", ["$tgRepo", resourceProvider]) diff --git a/app/coffee/modules/resources/custom-attributes.coffee b/app/coffee/modules/resources/custom-attributes.coffee index dde0e637..cf14c398 100644 --- a/app/coffee/modules/resources/custom-attributes.coffee +++ b/app/coffee/modules/resources/custom-attributes.coffee @@ -29,8 +29,8 @@ resourceProvider = ($repo) -> return $repo.queryMany(resource, {project: projectId}) service = { - us:{ - list: (projectId) -> _list(projectId, "custom-attributes/us") + userstory:{ + list: (projectId) -> _list(projectId, "custom-attributes/userstory") } task:{ list: (projectId) -> _list(projectId, "custom-attributes/task") diff --git a/app/partials/admin/admin-project-values-us-extras.jade b/app/partials/admin/admin-project-values-us-extras.jade index 55523d97..40339494 100644 --- a/app/partials/admin/admin-project-values-us-extras.jade +++ b/app/partials/admin/admin-project-values-us-extras.jade @@ -1,5 +1,5 @@ div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="section='admin'; type='us'; sectionName='US extra'") + ng-init="section='admin'; type='userstory'; sectionName='US extra'") sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") include ../includes/modules/admin-menu From 0a6d77f23fc2defae8ea42d7c663630c9513e526 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Thu, 26 Feb 2015 12:02:56 +0100 Subject: [PATCH 128/207] Update CHANGELOG --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index eaf817c5..7fb54d9f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,7 +4,7 @@ ## 1.6.0 ??? (Unreleased) ### Features -- ... +- Added custom fields per project for user stories, tasks and issues. ### Misc - New contrib plugin for hipchat (by Δndrea Stagi) From 910dac75b7948e69d4d4468a9809a862aec7bf77 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Mon, 2 Mar 2015 12:56:30 +0100 Subject: [PATCH 129/207] Minor style fixes in custom fields --- app/coffee/modules/admin/project-values.coffee | 3 ++- app/styles/modules/common/custom-fields.scss | 6 ++++-- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 3b4882cf..48f52d63 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -593,8 +593,9 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> attr = formEl.scope().attr title = "Delete custom attribute" # i18n + subtitle = "Remeber that all values in this custom field will be deleted.
Are you sure you want to continue?" message = attr.name - $confirm.askOnDelete(title, message).then (finish) -> + $confirm.ask(title, subtitle, message).then (finish) -> onSucces = -> $ctrl.loadCustomAttributes().finally -> finish() diff --git a/app/styles/modules/common/custom-fields.scss b/app/styles/modules/common/custom-fields.scss index 2856188a..9500491a 100644 --- a/app/styles/modules/common/custom-fields.scss +++ b/app/styles/modules/common/custom-fields.scss @@ -33,8 +33,7 @@ } &.editable { .custom-field-options { - align-items: center; - display: flex; + margin-top: .5rem; } } .custom-field-options { @@ -62,6 +61,9 @@ line-height: .9rem; } } + .custom-field-options { + margin: 0; + } .custom-field-value { flex: 1; padding: 0 1rem 0 2rem; From 82659f480914ba562c2c7f46e2c5cfba2f388014 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Wed, 4 Mar 2015 12:20:21 +0100 Subject: [PATCH 130/207] US #55: Custom fields - Fix history of custom attributes values in detail pages --- .../modules/common/custom-field-values.coffee | 2 ++ app/coffee/modules/common/history.coffee | 30 +++++++++++++++++++ app/coffee/modules/issues/detail.coffee | 3 ++ app/coffee/modules/tasks/detail.coffee | 2 ++ app/coffee/modules/userstories/detail.coffee | 3 ++ 5 files changed, 40 insertions(+) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index bb8c4042..dd3e661b 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -59,6 +59,8 @@ class CustomAttributesValuesController extends taiga.Controller updateAttributeValue: (attributeValue) -> onSuccess = => + @rootscope.$broadcast("custom-attributes-values:edit") + onError = (response) => @confirm.notify("error") return @q.reject() diff --git a/app/coffee/modules/common/history.coffee b/app/coffee/modules/common/history.coffee index 0f7651b8..fcd1d961 100644 --- a/app/coffee/modules/common/history.coffee +++ b/app/coffee/modules/common/history.coffee @@ -173,6 +173,34 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> return _.flatten(attachments).join("\n") + renderCustomAttributesEntry = (value) -> + customAttributes = _.map value, (changes, type) -> + if type == "new" + return _.map changes, (change) -> + return templateChangeGeneric({ + name: change.name, + from: formatChange(""), + to: formatChange(change.value) + }) + else if type == "deleted" + return _.map changes, (change) -> + # TODO: i18n + return templateChangeDiff({ + name: "deleted custom attribute", + diff: change.name + }) + else + return _.map changes, (change) -> + customAttrsChanges = _.map change.changes, (values) -> + return templateChangeGeneric({ + name: change.name + from: formatChange(values[0]) + to: formatChange(values[1]) + }) + return _.flatten(customAttrsChanges).join("\n") + + return _.flatten(customAttributes).join("\n") + renderChangeEntry = (field, value) -> if field == "description" return templateChangeDiff({name: getHumanizedFieldName("description"), diff: value[1]}) @@ -182,6 +210,8 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> return templateChangePoints({points: value}) else if field == "attachments" return renderAttachmentEntry(value) + else if field == "custom_attributes" + return renderCustomAttributesEntry(value) else if field in ["tags", "watchers"] name = getHumanizedFieldName(field) removed = _.difference(value[0], value[1]) diff --git a/app/coffee/modules/issues/detail.coffee b/app/coffee/modules/issues/detail.coffee index eea923dc..2be4c7d7 100644 --- a/app/coffee/modules/issues/detail.coffee +++ b/app/coffee/modules/issues/detail.coffee @@ -85,6 +85,9 @@ class IssueDetailController extends mixOf(taiga.Controller, taiga.PageMixin) @rootscope.$broadcast("history:reload") @.loadIssue() + @scope.$on "custom-attributes-values:edit", => + @rootscope.$broadcast("history:reload") + initializeOnDeleteGoToUrl: -> ctx = {project: @scope.project.slug} if @scope.project.is_issues_activated diff --git a/app/coffee/modules/tasks/detail.coffee b/app/coffee/modules/tasks/detail.coffee index 1dd56d59..353fbaff 100644 --- a/app/coffee/modules/tasks/detail.coffee +++ b/app/coffee/modules/tasks/detail.coffee @@ -71,6 +71,8 @@ class TaskDetailController extends mixOf(taiga.Controller, taiga.PageMixin) @rootscope.$broadcast("history:reload") @scope.$on "attachment:delete", => @rootscope.$broadcast("history:reload") + @scope.$on "custom-attributes-values:edit", => + @rootscope.$broadcast("history:reload") initializeOnDeleteGoToUrl: -> ctx = {project: @scope.project.slug} diff --git a/app/coffee/modules/userstories/detail.coffee b/app/coffee/modules/userstories/detail.coffee index 6db4ccac..7347f72d 100644 --- a/app/coffee/modules/userstories/detail.coffee +++ b/app/coffee/modules/userstories/detail.coffee @@ -80,6 +80,9 @@ class UserStoryDetailController extends mixOf(taiga.Controller, taiga.PageMixin) @scope.$on "attachment:delete", => @rootscope.$broadcast("history:reload") + @scope.$on "custom-attributes-values:edit", => + @rootscope.$broadcast("history:reload") + initializeOnDeleteGoToUrl: -> ctx = {project: @scope.project.slug} @scope.onDeleteGoToUrl = @navUrls.resolve("project", ctx) From 53e814c9c0522522a37b8d1736841357ebfc9264 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Mar 2015 13:57:13 +0100 Subject: [PATCH 131/207] fix custom filters load --- app/coffee/modules/controllerMixins.coffee | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/controllerMixins.coffee b/app/coffee/modules/controllerMixins.coffee index 68cced92..34b5adb6 100644 --- a/app/coffee/modules/controllerMixins.coffee +++ b/app/coffee/modules/controllerMixins.coffee @@ -83,9 +83,8 @@ class FiltersMixin location.search(name, value) replaceAllFilters: (filters, load=false) -> - if !@location.isInCurrentRouteParams(name, value) - location = if load then @location else @location.noreload(@scope) - location.search(filters) + location = if load then @location else @location.noreload(@scope) + location.search(filters) unselectFilter: (name, value, load=false) -> params = @location.search() From 3b12b53aef4295289f96efc76c42604d61028561 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Mar 2015 15:09:35 +0100 Subject: [PATCH 132/207] fix 'add webhook' button style --- app/partials/admin/admin-third-parties-webhooks.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/admin/admin-third-parties-webhooks.jade b/app/partials/admin/admin-third-parties-webhooks.jade index 4262608c..b88fd939 100644 --- a/app/partials/admin/admin-third-parties-webhooks.jade +++ b/app/partials/admin/admin-third-parties-webhooks.jade @@ -14,7 +14,7 @@ block content p.admin-subtitle Webhooks notify external services about events in Taiga, like comments, user stories.... div.webhooks-options - a.utton-green.hidden.add-webhook(href="",title="Add a New Webhook") Add Webhook + a.button-green.hidden.add-webhook(href="",title="Add a New Webhook") Add Webhook section.webhooks-table.basic-table div.table-header From 9726992b84ddb4d1b3b9c2fe144d2ae8218c355f Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Mar 2015 15:28:18 +0100 Subject: [PATCH 133/207] fix long task names --- app/styles/modules/common/related-tasks.scss | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/app/styles/modules/common/related-tasks.scss b/app/styles/modules/common/related-tasks.scss index 13286580..aab7266b 100644 --- a/app/styles/modules/common/related-tasks.scss +++ b/app/styles/modules/common/related-tasks.scss @@ -49,15 +49,17 @@ border: 0; } .tasks { - flex-basis: 78%; - flex-grow: 10; + overflow: hidden; + width: 100%; } .status { - flex-basis: 100px; + flex-shrink: 0; + width: 100px; } .assigned-to { cursor: pointer; - flex-basis: 150px; + flex-shrink: 0; + width: 150px; } } .related-task-create-form { From 3d47ee44eb6d3bebbd7646fd13b03f1bce4652dc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Mon, 9 Mar 2015 16:35:51 +0100 Subject: [PATCH 134/207] Fixed bug #2370: Now showing correctly the payload of the request --- app/coffee/modules/admin/third-parties.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/third-parties.coffee b/app/coffee/modules/admin/third-parties.coffee index dd4055e0..640c0152 100644 --- a/app/coffee/modules/admin/third-parties.coffee +++ b/app/coffee/modules/admin/third-parties.coffee @@ -89,7 +89,7 @@ WebhookDirective = ($rs, $repo, $confirm, $loading) -> for log in webhooklogs log.validStatus = 200 <= log.status < 300 log.prettySentHeaders = _.map(_.pairs(log.request_headers), ([header, value]) -> "#{header}: #{value}").join("\n") - log.prettySentData = JSON.stringify(log.request_data.data, undefined, 2) + log.prettySentData = JSON.stringify(log.request_data) log.prettyDate = moment(log.created).format("DD MMM YYYY [at] hh:mm:ss") # TODO: i18n webhook.logs_counter = webhooklogs.length From 31cd4d4393748a9dc0d4c192d7b12912cc0954e0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Tue, 10 Feb 2015 09:31:06 +0100 Subject: [PATCH 135/207] US#1913: CSV Reports --- CHANGELOG.md | 2 + app/coffee/app.coffee | 28 +-- .../modules/admin/project-values.coffee | 177 ++++++++++++------ app/coffee/modules/base.coffee | 13 +- app/coffee/modules/resources.coffee | 5 + app/coffee/modules/resources/projects.coffee | 12 ++ .../admin-project-values-issue-extras.jade | 17 -- ...admin-project-values-issue-priorities.jade | 18 -- ...admin-project-values-issue-severities.jade | 18 -- .../admin-project-values-issue-status.jade | 18 -- .../admin-project-values-issue-types.jade | 18 -- .../admin/admin-project-values-issue.jade | 41 ++++ .../admin-project-values-task-extras.jade | 17 -- .../admin-project-values-task-status.jade | 18 -- .../admin/admin-project-values-task.jade | 26 +++ .../admin/admin-project-values-us-extras.jade | 17 -- .../admin/admin-project-values-us-points.jade | 24 --- .../admin/admin-project-values-us-status.jade | 18 -- .../admin/admin-project-values-us.jade | 31 +++ app/partials/includes/modules/admin-menu.jade | 10 +- .../modules/admin-submenu-project-values.jade | 55 +----- .../admin/admin-custom-attributes.jade | 5 + .../includes/modules/admin/project-csv.jade | 21 +++ .../modules/admin/project-points.jade | 6 + .../modules/admin/project-status.jade | 7 +- .../includes/modules/admin/project-types.jade | 6 + .../modules/admin/project-us-status.jade | 137 +++++++------- app/styles/components/buttons.scss | 3 +- app/styles/layout/admin-project-values.scss | 32 +++- app/styles/modules/admin/admin-common.scss | 2 +- app/styles/modules/admin/project-csv.scss | 41 ++++ app/styles/modules/common/colors-table.scss | 2 +- main-sass.js | 1 + 33 files changed, 447 insertions(+), 399 deletions(-) delete mode 100644 app/partials/admin/admin-project-values-issue-extras.jade delete mode 100644 app/partials/admin/admin-project-values-issue-priorities.jade delete mode 100644 app/partials/admin/admin-project-values-issue-severities.jade delete mode 100644 app/partials/admin/admin-project-values-issue-status.jade delete mode 100644 app/partials/admin/admin-project-values-issue-types.jade create mode 100644 app/partials/admin/admin-project-values-issue.jade delete mode 100644 app/partials/admin/admin-project-values-task-extras.jade delete mode 100644 app/partials/admin/admin-project-values-task-status.jade create mode 100644 app/partials/admin/admin-project-values-task.jade delete mode 100644 app/partials/admin/admin-project-values-us-extras.jade delete mode 100644 app/partials/admin/admin-project-values-us-points.jade delete mode 100644 app/partials/admin/admin-project-values-us-status.jade create mode 100644 app/partials/admin/admin-project-values-us.jade create mode 100644 app/partials/includes/modules/admin/project-csv.jade create mode 100644 app/styles/modules/admin/project-csv.scss diff --git a/CHANGELOG.md b/CHANGELOG.md index 7fb54d9f..f03bfa53 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,8 @@ ### Features - Added custom fields per project for user stories, tasks and issues. +- Add to the Admin Panel the export to CSV sections. +- Reorganized the Admin Panel. ### Misc - New contrib plugin for hipchat (by Δndrea Stagi) diff --git a/app/coffee/app.coffee b/app/coffee/app.coffee index 76e82774..2dec2bcc 100644 --- a/app/coffee/app.coffee +++ b/app/coffee/app.coffee @@ -89,28 +89,12 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-project-modules.html"}) $routeProvider.when("/project/:pslug/admin/project-profile/export", {templateUrl: "admin/admin-project-export.html"}) - # Admin Project Values - $routeProvider.when("/project/:pslug/admin/project-values/us-status", - {templateUrl: "admin/admin-project-values-us-status.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/us-points", - {templateUrl: "admin/admin-project-values-us-points.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/us-extras", - {templateUrl: "admin/admin-project-values-us-extras.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/task-status", - {templateUrl: "admin/admin-project-values-task-status.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/task-extras", - {templateUrl: "admin/admin-project-values-task-extras.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/issue-status", - {templateUrl: "admin/admin-project-values-issue-status.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/issue-types", - {templateUrl: "admin/admin-project-values-issue-types.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/issue-priorities", - {templateUrl: "admin/admin-project-values-issue-priorities.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/issue-severities", - {templateUrl: "admin/admin-project-values-issue-severities.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/issue-extras", - {templateUrl: "admin/admin-project-values-issue-extras.html"}) - # Admin - Memberships + $routeProvider.when("/project/:pslug/admin/project-values/us", + {templateUrl: "admin/admin-project-values-us.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/task", + {templateUrl: "admin/admin-project-values-task.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/issue", + {templateUrl: "admin/admin-project-values-issue.html"}) $routeProvider.when("/project/:pslug/admin/memberships", {templateUrl: "admin/admin-memberships.html"}) # Admin - Roles diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 48f52d63..217f5a5a 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -32,10 +32,10 @@ debounce = @.taiga.debounce module = angular.module("taigaAdmin") ############################################################################# -## Project values Controller +## Project values section Controller ############################################################################# -class ProjectValuesController extends mixOf(taiga.Controller, taiga.PageMixin) +class ProjectValuesSectionController extends mixOf(taiga.Controller, taiga.PageMixin) @.$inject = [ "$scope", "$rootScope", @@ -59,29 +59,44 @@ class ProjectValuesController extends mixOf(taiga.Controller, taiga.PageMixin) promise.then null, @.onInitialDataError.bind(@) - @scope.$on("admin:project-values:move", @.moveValue) - loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => @scope.project = project @scope.$emit('project:loaded', project) return project - loadValues: -> - return @rs[@scope.resource].listValues(@scope.projectId, @scope.type).then (values) => - @scope.values = values - @scope.maxValueOrder = _.max(values, "order").order - return values - loadInitialData: -> promise = @repo.resolve({pslug: @params.pslug}).then (data) => @scope.projectId = data.project return data - return promise.then( => @q.all([ - @.loadProject(), - @.loadValues(), - ])) + return promise.then => @.loadProject() + + +module.controller("ProjectValuesSectionController", ProjectValuesSectionController) + +############################################################################# +## Project values Controller +############################################################################# + +class ProjectValuesController extends taiga.Controller + @.$inject = [ + "$scope", + "$rootScope", + "$tgRepo", + "$tgConfirm", + "$tgResources", + ] + + constructor: (@scope, @rootscope, @repo, @confirm, @rs) -> + @scope.$on("admin:project-values:move", @.moveValue) + @rootscope.$on("project:loaded", @.loadValues) + + loadValues: => + return @rs[@scope.resource].listValues(@scope.projectId, @scope.type).then (values) => + @scope.values = values + @scope.maxValueOrder = _.max(values, "order").order + return values moveValue: (ctx, itemValue, itemIndex) => values = @scope.values @@ -147,7 +162,7 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> $(document.body).scrollTop(table.offset().top + table.height()) if focus - $(".new-value input").focus() + $el.find(".new-value input:visible").first().focus() saveValue = (target) -> form = target.parents("form").checksley() @@ -161,7 +176,25 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> row.siblings(".visualization").removeClass('hidden') promise.then null, (data) -> - $confirm.notify("error") + form.setErrors(data) + + saveNewValue = (target) -> + form = target.parents("form").checksley() + return if not form.validate() + + $scope.newValue.project = $scope.project.id + + $scope.newValue.order = if $scope.maxValueOrder then $scope.maxValueOrder + 1 else 1 + + promise = $repo.create(valueType, $scope.newValue) + promise.then (data) => + target.addClass("hidden") + + $scope.values.push(data) + $scope.maxValueOrder = data.order + initializeNewValue() + + promise.then null, (data) -> form.setErrors(data) cancel = (target) -> @@ -180,24 +213,8 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> $el.on "click", ".add-new", debounce 2000, (event) -> event.preventDefault() - form = $el.find(".new-value").parents("form").checksley() - return if not form.validate() - - $scope.newValue.project = $scope.project.id - - $scope.newValue.order = if $scope.maxValueOrder then $scope.maxValueOrder + 1 else 1 - - promise = $repo.create(valueType, $scope.newValue) - promise.then (data) => - $el.find(".new-value").addClass("hidden") - - $scope.values.push(data) - $scope.maxValueOrder = data.order - initializeNewValue() - - promise.then null, (data) -> - $confirm.notify("error") - form.setErrors(data) + target = $el.find(".new-value") + saveNewValue(target) $el.on "click", ".delete-new", (event) -> event.preventDefault() @@ -223,6 +240,14 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> target = angular.element(event.currentTarget) cancel(target) + $el.on "keyup", ".new-value input", (event) -> + if event.keyCode == 13 + target = $el.find(".new-value") + saveNewValue(target) + else if event.keyCode == 27 + $el.find(".new-value").addClass("hidden") + initializeNewValue() + $el.on "click", ".save", (event) -> event.preventDefault() target = angular.element(event.currentTarget) @@ -321,7 +346,6 @@ ColorSelectionDirective = () -> module.directive("tgColorSelection", ColorSelectionDirective) - ############################################################################# ## Custom Attributes Controller ############################################################################# @@ -342,33 +366,10 @@ class ProjectCustomAttributesController extends mixOf(taiga.Controller, taiga.Pa constructor: (@scope, @rootscope, @repo, @rs, @params, @q, @location, @navUrls, @appTitle) -> @scope.project = {} - promise = @.loadInitialData() - - promise.then () => + @rootscope.$on "project:loaded", => + @.loadCustomAttributes() @appTitle.set("Project Custom Attributes - " + @scope.sectionName + " - " + @scope.project.name) - promise.then null, @.onInitialDataError.bind(@) - - loadInitialData: => - promise = @repo.resolve({pslug: @params.pslug}).then (data) => - @scope.projectId = data.project - return data - - return promise.then( => @q.all([ - @.loadProject(), - @.loadCustomAttributes(), - ])) - - ######################### - # Project - ######################### - - loadProject: => - return @rs.projects.get(@scope.projectId).then (project) => - @scope.project = project - @scope.$emit('project:loaded', project) - return project - ######################### # Custom Attribute ######################### @@ -438,6 +439,7 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> showCreateForm = -> $el.find(".js-new-custom-field").removeClass("hidden") + $el.find(".js-new-custom-field input:visible").first().focus() hideCreateForm = -> $el.find(".js-new-custom-field").addClass("hidden") @@ -469,7 +471,6 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> onError = (data) => form.setErrors(data) - $confirm.notify("error") attr = $scope.newAttr attr.project = $scope.projectId @@ -525,6 +526,7 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> showEditForm = (formEl) -> formEl.find(".js-view-custom-field").addClass("hidden") formEl.find(".js-edit-custom-field").removeClass("hidden") + formEl.find(".js-edit-custom-field input:visible").first().focus().select() hideEditForm = (formEl) -> formEl.find(".js-edit-custom-field").addClass("hidden") @@ -545,7 +547,6 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> onError = (data) => form.setErrors(data) - $confirm.notify("error") attr = formEl.scope().attr $ctrl.saveCustomAttribute(attr).then(onSucces, onError) @@ -616,3 +617,55 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> return {link: link} module.directive("tgProjectCustomAttributes", ["$log", "$tgConfirm", "animationFrame", ProjectCustomAttributesDirective]) + +############################################################################# +## CSV Exporter directive +############################################################################# + +class CsvExporterController extends taiga.Controller + @.$inject = [ + "$scope", + "$rootScope", + "$tgUrls", + "$tgConfirm", + "$tgResources", + ] + + constructor: (@scope, @rootscope, @urls, @confirm, @rs) -> + @rootscope.$on("project:loaded", @.setCsvUuid) + @scope.$watch "csvUuid", (value) => + if value + @scope.csvUrl = @urls.resolve("#{@.type}-csv", value) + else + @scope.csvUrl = "" + + setCsvUuid: => + @scope.csvUuid = @scope.project["#{@.type}_csv_uuid"] + + regenerateUuid: -> + #TODO: i18n + @confirm.ask("Change URL", "You going to change the CSV data access url. The previous url will be disabled. Are you sure?").then (finish) => + promise = @rs.projects["regenerate_#{@.type}_csv_uuid"](@scope.projectId) + + promise.then (data) => + @scope.csvUuid = data.data?.uuid + + promise.then null, => + @confirm.notify("error") + + promise.finally -> + finish() + return promise + +class CsvExporterUserstoriesController extends CsvExporterController + type: "userstories" + +class CsvExporterTasksController extends CsvExporterController + type: "tasks" + +class CsvExporterIssuesController extends CsvExporterController + type: "issues" + +module.controller("CsvExporterUserstoriesController", CsvExporterUserstoriesController) +module.controller("CsvExporterTasksController", CsvExporterTasksController) +module.controller("CsvExporterIssuesController", CsvExporterIssuesController) diff --git a/app/coffee/modules/base.coffee b/app/coffee/modules/base.coffee index 2ae8983e..5f324796 100644 --- a/app/coffee/modules/base.coffee +++ b/app/coffee/modules/base.coffee @@ -84,16 +84,9 @@ urls = { "project-admin-project-profile-default-values": "/project/:project/admin/project-profile/default-values" "project-admin-project-profile-modules": "/project/:project/admin/project-profile/modules" "project-admin-project-profile-export": "/project/:project/admin/project-profile/export" - "project-admin-project-values-us-status": "/project/:project/admin/project-values/us-status" - "project-admin-project-values-us-points": "/project/:project/admin/project-values/us-points" - "project-admin-project-values-us-extras": "/project/:project/admin/project-values/us-extras" - "project-admin-project-values-task-status": "/project/:project/admin/project-values/task-status" - "project-admin-project-values-task-extras": "/project/:project/admin/project-values/task-extras" - "project-admin-project-values-issue-status": "/project/:project/admin/project-values/issue-status" - "project-admin-project-values-issue-types": "/project/:project/admin/project-values/issue-types" - "project-admin-project-values-issue-priorities": "/project/:project/admin/project-values/issue-priorities" - "project-admin-project-values-issue-severities": "/project/:project/admin/project-values/issue-severities" - "project-admin-project-values-issue-extras": "/project/:project/admin/project-values/issue-extras" + "project-admin-project-values-us": "/project/:project/admin/project-values/us" + "project-admin-project-values-task": "/project/:project/admin/project-values/task" + "project-admin-project-values-issue": "/project/:project/admin/project-values/issue" "project-admin-memberships": "/project/:project/admin/memberships" "project-admin-roles": "/project/:project/admin/roles" "project-admin-third-parties-webhooks": "/project/:project/admin/third-parties/webhooks" diff --git a/app/coffee/modules/resources.coffee b/app/coffee/modules/resources.coffee index 1761ae39..2364baa3 100644 --- a/app/coffee/modules/resources.coffee +++ b/app/coffee/modules/resources.coffee @@ -118,6 +118,11 @@ urls = { # Export/Import "exporter": "/exporter" "importer": "/importer/load_dump" + + # CSV + "userstories-csv": "/userstories/csv?uuid=%s" + "tasks-csv": "/tasks/csv?uuid=%s" + "issues-csv": "/issues/csv?uuid=%s" } # Initialize api urls service diff --git a/app/coffee/modules/resources/projects.coffee b/app/coffee/modules/resources/projects.coffee index d6a5a0ad..877b4763 100644 --- a/app/coffee/modules/resources/projects.coffee +++ b/app/coffee/modules/resources/projects.coffee @@ -50,6 +50,18 @@ resourceProvider = ($config, $repo, $http, $urls, $auth, $q, $rootScope) -> service.stats = (projectId) -> return $repo.queryOneRaw("projects", "#{projectId}/stats") + service.regenerate_userstories_csv_uuid = (projectId) -> + url = "#{$urls.resolve("projects")}/#{projectId}/regenerate_userstories_csv_uuid" + return $http.post(url) + + service.regenerate_issues_csv_uuid = (projectId) -> + url = "#{$urls.resolve("projects")}/#{projectId}/regenerate_issues_csv_uuid" + return $http.post(url) + + service.regenerate_tasks_csv_uuid = (projectId) -> + url = "#{$urls.resolve("projects")}/#{projectId}/regenerate_tasks_csv_uuid" + return $http.post(url) + service.leave = (projectId) -> url = "#{$urls.resolve("projects")}/#{projectId}/leave" return $http.post(url) diff --git a/app/partials/admin/admin-project-values-issue-extras.jade b/app/partials/admin/admin-project-values-issue-extras.jade deleted file mode 100644 index 9335bfa3..00000000 --- a/app/partials/admin/admin-project-values-issue-extras.jade +++ /dev/null @@ -1,17 +0,0 @@ -div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="section='admin'; type='issue'; sectionName='Issue extra'") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-issue-extras") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify here issue custom fields. The new field will appear on your issue detail. - - div.custom-field-options - a.button.button-green.js-add-custom-field-button(href="",title="Add a custom field in issues") - | Add custom field - - include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-issue-priorities.jade b/app/partials/admin/admin-project-values-issue-priorities.jade deleted file mode 100644 index be45b28d..00000000 --- a/app/partials/admin/admin-project-values-issue-priorities.jade +++ /dev/null @@ -1,18 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='priorities'; sectionName='Issue Priorities'", - type="priorities") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-priorities") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the priority levels users can assign to issues - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new priority - - include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-issue-severities.jade b/app/partials/admin/admin-project-values-issue-severities.jade deleted file mode 100644 index 25d17ced..00000000 --- a/app/partials/admin/admin-project-values-issue-severities.jade +++ /dev/null @@ -1,18 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='severities'; sectionName='Issue severities'", - type="severities") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-severities") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the severity level users can select to classify issues - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new severity - - include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-issue-status.jade b/app/partials/admin/admin-project-values-issue-status.jade deleted file mode 100644 index 629b7fdd..00000000 --- a/app/partials/admin/admin-project-values-issue-status.jade +++ /dev/null @@ -1,18 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='issue-statuses'; sectionName='Issue Statuses'", - type="issue-statuses") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-issue-status") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the column headers that you will use to classify Issues - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new status - - include ../includes/modules/admin/project-status diff --git a/app/partials/admin/admin-project-values-issue-types.jade b/app/partials/admin/admin-project-values-issue-types.jade deleted file mode 100644 index 4d702362..00000000 --- a/app/partials/admin/admin-project-values-issue-types.jade +++ /dev/null @@ -1,18 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='issue-types'; sectionName='Issue Types'", - type="issue-types") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-issue-types") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the categories users can select to classify issues - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new type - - include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-issue.jade b/app/partials/admin/admin-project-values-issue.jade new file mode 100644 index 00000000..4b414726 --- /dev/null +++ b/app/partials/admin/admin-project-values-issue.jade @@ -0,0 +1,41 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-issue") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the column headers that you will use to classify Issues + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='issue-statuses'; sectionName='Status'", + type="issue-statuses") + include ../includes/modules/admin/project-status + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='priorities'; sectionName='Priorities'; objName='priority'", + type="priorities") + include ../includes/modules/admin/project-types + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='severities'; sectionName='Severities'; objName='severity'", + type="severities") + include ../includes/modules/admin/project-types + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='issue-types'; sectionName='Types'; objName='type'", + type="issue-types") + include ../includes/modules/admin/project-types + + div.admin-attributes-section(tg-project-custom-attributes, + ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="type='issue';") + - var customFieldButtonTitle = "Add a custom field in tasks" + include ../includes/modules/admin/admin-custom-attributes + + - var csvType = "Issues"; + - var controller = "CsvExporterIssuesController"; + div.admin-attributes-section + include ../includes/modules/admin/project-csv diff --git a/app/partials/admin/admin-project-values-task-extras.jade b/app/partials/admin/admin-project-values-task-extras.jade deleted file mode 100644 index 95b50a1d..00000000 --- a/app/partials/admin/admin-project-values-task-extras.jade +++ /dev/null @@ -1,17 +0,0 @@ -div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="section='admin'; type='task'; sectionName='Task extra'") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-task-extras") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify here task custom fields. The new field will appear on your task detail. - - div.custom-field-options - a.button.button-green.js-add-custom-field-button(href="",title="Add a custom field in tasks") - | Add custom field - - include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-task-status.jade b/app/partials/admin/admin-project-values-task-status.jade deleted file mode 100644 index 5d6fa0ba..00000000 --- a/app/partials/admin/admin-project-values-task-status.jade +++ /dev/null @@ -1,18 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='tasks'; type='task-statuses'; sectionName='Task Statuses'", - type="task-statuses") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-task-status") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the column headers that you will use to classify Tasks related to each User Stories - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new status - - include ../includes/modules/admin/project-status diff --git a/app/partials/admin/admin-project-values-task.jade b/app/partials/admin/admin-project-values-task.jade new file mode 100644 index 00000000..62e1d191 --- /dev/null +++ b/app/partials/admin/admin-project-values-task.jade @@ -0,0 +1,26 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-task") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the column headers that you will use to classify Tasks related to each User Stories + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='tasks'; type='task-statuses'; sectionName='Task Statuses'", + type="task-statuses") + include ../includes/modules/admin/project-status + + div.admin-attributes-section(tg-project-custom-attributes, + ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="type='task';") + - var customFieldButtonTitle = "Add a custom field in tasks" + include ../includes/modules/admin/admin-custom-attributes + + - var csvType = "Task"; + - var controller = "CsvExporterTasksController"; + div.admin-attributes-section + include ../includes/modules/admin/project-csv diff --git a/app/partials/admin/admin-project-values-us-extras.jade b/app/partials/admin/admin-project-values-us-extras.jade deleted file mode 100644 index 40339494..00000000 --- a/app/partials/admin/admin-project-values-us-extras.jade +++ /dev/null @@ -1,17 +0,0 @@ -div.wrapper(tg-project-custom-attributes, ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="section='admin'; type='userstory'; sectionName='US extra'") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-us-extras") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify here user story custom fields. The new field will appear on your user story detail. - - div.custom-field-options - a.button.button-green.js-add-custom-field-button(href="",title="Add a custom field in user stories") - | Add custom field - - include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-us-points.jade b/app/partials/admin/admin-project-values-us-points.jade deleted file mode 100644 index 41b434ae..00000000 --- a/app/partials/admin/admin-project-values-us-points.jade +++ /dev/null @@ -1,24 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='userstories'; type='points'; sectionName='Us points'", - type="points") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-us-points") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the numerical system you will use to indicate the level of difficulty for each User Story - - - var helpLightboxId = "notion-admin-project-values-us-points" - include ../includes/components/help-notion-button - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new point - - include ../includes/modules/admin/project-points - -div.lightbox.lightbox-generic-notion.notion-admin-project-values-us-points(id="notion-admin-project-values-us-points", tg-lb-notion) - include ../includes/modules/help-notions/lightbox-notion-admin-project-values-us-points diff --git a/app/partials/admin/admin-project-values-us-status.jade b/app/partials/admin/admin-project-values-us-status.jade deleted file mode 100644 index c87811ce..00000000 --- a/app/partials/admin/admin-project-values-us-status.jade +++ /dev/null @@ -1,18 +0,0 @@ -div.wrapper(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='userstories'; type='userstory-statuses'; sectionName='Us Statuses'", - type="userstory-statuses") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-us-status") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common - include ../includes/components/mainTitle - p.admin-subtitle Specify the column headers that you will use to classify User Stories - - div.project-values-options - a.button-green.show-add-new(href="", title="Add New") - span Add new status - - include ../includes/modules/admin/project-us-status diff --git a/app/partials/admin/admin-project-values-us.jade b/app/partials/admin/admin-project-values-us.jade new file mode 100644 index 00000000..807d53fd --- /dev/null +++ b/app/partials/admin/admin-project-values-us.jade @@ -0,0 +1,31 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-us") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the column headers that you will use to classify User Stories + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='userstories'; type='userstory-statuses'; sectionName='Us Statuses'", + type="userstory-statuses") + include ../includes/modules/admin/project-us-status + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='userstories'; type='points'; sectionName='Us points'", + type="points") + include ../includes/modules/admin/project-points + + div.admin-attributes-section(tg-project-custom-attributes, + ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="type='userstory';") + - var customFieldButtonTitle = "Add a custom field in tasks" + include ../includes/modules/admin/admin-custom-attributes + + - var csvType = "US"; + - var controller = "CsvExporterUserstoriesController"; + div.admin-attributes-section + include ../includes/modules/admin/project-csv diff --git a/app/partials/includes/modules/admin-menu.jade b/app/partials/includes/modules/admin-menu.jade index 6f924633..858ec8a8 100644 --- a/app/partials/includes/modules/admin-menu.jade +++ b/app/partials/includes/modules/admin-menu.jade @@ -6,19 +6,19 @@ section.admin-menu ul li#adminmenu-project-profile a(href="", tg-nav="project-admin-project-profile-details:project=project.slug") - span.title Project profile + span.title Project span.icon.icon-arrow-right li#adminmenu-project-values - a(href="", tg-nav="project-admin-project-values-us-status:project=project.slug") - span.title Custom Attributes + a(href="", tg-nav="project-admin-project-values-us:project=project.slug") + span.title Attributes span.icon.icon-arrow-right li#adminmenu-memberships a(href="" tg-nav="project-admin-memberships:project=project.slug") - span.title Manage members + span.title Members span.icon.icon-arrow-right li#adminmenu-roles a(href="" tg-nav="project-admin-roles:project=project.slug") - span.title Roles & Permissions + span.title Permissions span.icon.icon-arrow-right li#adminmenu-third-parties a(href="" tg-nav="project-admin-third-parties-webhooks:project=project.slug") diff --git a/app/partials/includes/modules/admin-submenu-project-values.jade b/app/partials/includes/modules/admin-submenu-project-values.jade index 31d45ae9..1370e797 100644 --- a/app/partials/includes/modules/admin-submenu-project-values.jade +++ b/app/partials/includes/modules/admin-submenu-project-values.jade @@ -1,55 +1,20 @@ section.admin-submenu header - h1 Custom Attributes + h1 Attributes nav ul - li#adminmenu-values-us-status - a(href="", tg-nav="project-admin-project-values-us-status:project=project.slug") - span.title US statuses + li#adminmenu-values-us + a(href="", tg-nav="project-admin-project-values-us:project=project.slug") + span.title US span.icon.icon-arrow-right - li#adminmenu-values-us-points - a(href="", tg-nav="project-admin-project-values-us-points:project=project.slug") - span.title US points + li#adminmenu-values-task + a(href="", tg-nav="project-admin-project-values-task:project=project.slug") + span.title Task span.icon.icon-arrow-right - li#adminmenu-values-us-extras - a(href="", tg-nav="project-admin-project-values-us-extras:project=project.slug") - span.title US extras - span.icon.icon-arrow-right - - li#adminmenu-values-task-status - a(href="", tg-nav="project-admin-project-values-task-status:project=project.slug") - span.title Task statuses - span.icon.icon-arrow-right - - li#adminmenu-values-task-extras - a(href="", tg-nav="project-admin-project-values-task-extras:project=project.slug") - span.title Task extras - span.icon.icon-arrow-right - - li#adminmenu-values-issue-status - a(href="", tg-nav="project-admin-project-values-issue-status:project=project.slug") - span.title Issue statuses - span.icon.icon-arrow-right - - li#adminmenu-values-issue-types - a(href="", tg-nav="project-admin-project-values-issue-types:project=project.slug") - span.title Issue types - span.icon.icon-arrow-right - - li#adminmenu-values-priorities - a(href="", tg-nav="project-admin-project-values-issue-priorities:project=project.slug") - span.title Issue Priorities - span.icon.icon-arrow-right - - li#adminmenu-values-severities - a(href="", tg-nav="project-admin-project-values-issue-severities:project=project.slug") - span.title Issue Severities - span.icon.icon-arrow-right - - li#adminmenu-values-issue-extras - a(href="", tg-nav="project-admin-project-values-issue-extras:project=project.slug") - span.title Issue extras + li#adminmenu-values-issue + a(href="", tg-nav="project-admin-project-values-issue:project=project.slug") + span.title Issue span.icon.icon-arrow-right diff --git a/app/partials/includes/modules/admin/admin-custom-attributes.jade b/app/partials/includes/modules/admin/admin-custom-attributes.jade index 318a60be..cc9a3f35 100644 --- a/app/partials/includes/modules/admin/admin-custom-attributes.jade +++ b/app/partials/includes/modules/admin/admin-custom-attributes.jade @@ -1,4 +1,9 @@ section.custom-fields-table.basic-table + div.project-values-title + h2 Custom fields + a.button.button-gray.show-add-new.js-add-custom-field-button(href="", title="#{customFieldButtonTitle}") + span Add custom field + div.table-header div.row div.custom-name diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade new file mode 100644 index 00000000..1e68581a --- /dev/null +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -0,0 +1,21 @@ +section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text) + div.project-values-title + h2 Export #{csvType} Data + span (.csv format) + a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}") + span Download CSV + + p Get all information about your project #{csvType}. Save all your data to a .csv file and open it in your favourite text editor or spreadsheet. You will be able to visualize and analize all your data easily. + div.csv-regenerate-field + .field-with-options + input(type="text", placeholder="Please regenerate CSV url", readonly, ng-model="csvUrl") + .option-wrapper.select-input-content + .icon.icon-copy + a(href="", title="Regenerate CSV url", ng-click="ctrl.regenerateUuid()") + span.icon.icon-reload + span Regenerate + + a.help-button(href="", target="_blank") + span.icon.icon-help + span How to use this on my own spreadsheet? + diff --git a/app/partials/includes/modules/admin/project-points.jade b/app/partials/includes/modules/admin/project-points.jade index 02ad65f3..2e8eb8f0 100644 --- a/app/partials/includes/modules/admin/project-points.jade +++ b/app/partials/includes/modules/admin/project-points.jade @@ -1,4 +1,10 @@ section.project-values-table + + div.project-values-title + h2 Points + a.button.button-gray.show-add-new(href="", title="Add New") + span Add new point + div.project-values-header div.project-values-row div.project-values-name diff --git a/app/partials/includes/modules/admin/project-status.jade b/app/partials/includes/modules/admin/project-status.jade index d1c5a99a..00c0df30 100644 --- a/app/partials/includes/modules/admin/project-status.jade +++ b/app/partials/includes/modules/admin/project-status.jade @@ -1,4 +1,9 @@ -section.colors-table +section.colors-table.admin-status-table + div.project-values-title + h2 Status + a.button.button-gray.show-add-new(href="", title="Add New") + span Add new status + div.table-header div.row div.color-column Color diff --git a/app/partials/includes/modules/admin/project-types.jade b/app/partials/includes/modules/admin/project-types.jade index 4f504e38..df8843f2 100644 --- a/app/partials/includes/modules/admin/project-types.jade +++ b/app/partials/includes/modules/admin/project-types.jade @@ -1,4 +1,10 @@ section.colors-table + + div.project-values-title + h2 {{ sectionName }} + a.button.button-gray.show-add-new(href="", title="Add New") + span Add new {{ objName }} + div.table-header div.row div.color-column Color diff --git a/app/partials/includes/modules/admin/project-us-status.jade b/app/partials/includes/modules/admin/project-us-status.jade index a78f7607..8b443369 100644 --- a/app/partials/includes/modules/admin/project-us-status.jade +++ b/app/partials/includes/modules/admin/project-us-status.jade @@ -1,89 +1,96 @@ -section.colors-table - div.table-header - div.row - div.color-column Color - div.status-name Name - div.status-slug Slug - div.is-closed-column Is closed? - div.is-archived-column Is archived? - div.status-wip-limit WIP Limit - div.options-column +section.project-us-status - div.table-main - div.sortable - form(ng-repeat="value in values") - div.row.table-main.visualization - span.icon.icon-drag-v + div.project-values-title + h2 Status + a.button.button-gray.show-add-new(href="", title="Add New") + span Add new status - div.color-column - div.current-color(style="background: {{ value.color }}") + div.colors-table + div.table-header + div.row + div.color-column Color + div.status-name Name + div.status-slug Slug + div.is-closed-column Is closed? + div.is-archived-column Is archived? + div.status-wip-limit WIP Limit + div.options-column - div.status-name - span {{ value.name }} + div.table-main + div.sortable + form(ng-repeat="value in values") + div.row.table-main.visualization + span.icon.icon-drag-v - div.status-slug - span {{ value.slug }} + div.color-column + div.current-color(style="background: {{ value.color }}") - div.is-closed-column - div.icon.icon-check-square(ng-show="value.is_closed") + div.status-name + span {{ value.name }} - div.is-archived-column - div.icon.icon-check-square(ng-show="value.is_archived") + div.status-slug + span {{ value.slug }} - div.status-wip-limit - span {{ value.wip_limit }} + div.is-closed-column + div.icon.icon-check-square(ng-show="value.is_closed") - div.options-column - a.edit-value.icon.icon-edit(href="", title="Edit value") - a.delete-value.icon.icon-delete(href="", title="Delete value") + div.is-archived-column + div.icon.icon-check-square(ng-show="value.is_archived") - div.row.table-main.edition.hidden - div.color-column(tg-color-selection, ng-model="value") - div.current-color(style="background: {{ value.color }}") + div.status-wip-limit + span {{ value.wip_limit }} + + div.options-column + a.edit-value.icon.icon-edit(href="", title="Edit value") + a.delete-value.icon.icon-delete(href="", title="Delete value") + + div.row.table-main.edition.hidden + div.color-column(tg-color-selection, ng-model="value") + div.current-color(style="background: {{ value.color }}") + include ../../components/select-color + + div.status-name + input(name="name", type="text", placeholder="Write a name for the new status", + ng-model="value.name", data-required="true", data-maxlength="255") + + div.is-closed-column + select(name="is_closed", ng-model="value.is_closed", data-required="true", + ng-options="e.id as e.name for e in [{'id':true, 'name':'Yes'},{'id':false, 'name': 'No'}]") + + div.is-archived-column + select(name="is_archived", ng-model="value.is_archived", data-required="true", + ng-options="e.id as e.name for e in [{'id':true, 'name':'Yes'},{'id':false, 'name': 'No'}]") + + div.status-wip-limit + input(name="wip_limit", type="number", placeholder="WIP Limit", + ng-model="value.wip_limit", data-type="digits") + + div.options-column + a.save.icon.icon-floppy(href="", title="Save changes") + a.cancel.icon.icon-delete(href="", title="Cancel") + + form + div.row.table-main.new-value.hidden + div.color-column(tg-color-selection, ng-model="newValue") + div.current-color(style="background: {{ newValue.color }}") include ../../components/select-color div.status-name input(name="name", type="text", placeholder="Write a name for the new status", - ng-model="value.name", data-required="true", data-maxlength="255") + ng-model="newValue.name", data-required="true", data-maxlength="255") div.is-closed-column - select(name="is_closed", ng-model="value.is_closed", data-required="true", + select(name="is_closed", ng-model="newValue.is_closed", data-required="true", ng-options="e.id as e.name for e in [{'id':true, 'name':'Yes'},{'id':false, 'name': 'No'}]") div.is-archived-column - select(name="is_archived", ng-model="value.is_archived", data-required="true", + select(name="is_archived", ng-model="newValue.is_archived", data-required="true", ng-options="e.id as e.name for e in [{'id':true, 'name':'Yes'},{'id':false, 'name': 'No'}]") div.status-wip-limit input(name="wip_limit", type="number", placeholder="WIP Limit", - ng-model="value.wip_limit", data-type="digits") + ng-model="newValue.wip_limit", data-type="digits") div.options-column - a.save.icon.icon-floppy(href="", title="Save changes") - a.cancel.icon.icon-delete(href="", title="Cancel") - - form - div.row.table-main.new-value.hidden - div.color-column(tg-color-selection, ng-model="newValue") - div.current-color(style="background: {{ newValue.color }}") - include ../../components/select-color - - div.status-name - input(name="name", type="text", placeholder="Write a name for the new status", - ng-model="newValue.name", data-required="true", data-maxlength="255") - - div.is-closed-column - select(name="is_closed", ng-model="newValue.is_closed", data-required="true", - ng-options="e.id as e.name for e in [{'id':true, 'name':'Yes'},{'id':false, 'name': 'No'}]") - - div.is-archived-column - select(name="is_archived", ng-model="newValue.is_archived", data-required="true", - ng-options="e.id as e.name for e in [{'id':true, 'name':'Yes'},{'id':false, 'name': 'No'}]") - - div.status-wip-limit - input(name="wip_limit", type="number", placeholder="WIP Limit", - ng-model="newValue.wip_limit", data-type="digits") - - div.options-column - a.add-new.icon.icon-floppy(href="", title="Add") - a.delete-new.icon.icon-delete(href="", title="Cancel") + a.add-new.icon.icon-floppy(href="", title="Add") + a.delete-new.icon.icon-delete(href="", title="Cancel") diff --git a/app/styles/components/buttons.scss b/app/styles/components/buttons.scss index a7e371e5..e961ce8f 100755 --- a/app/styles/components/buttons.scss +++ b/app/styles/components/buttons.scss @@ -60,7 +60,8 @@ } } -.button-gray { +.button-gray, +a.button-gray { @extend %button; background: $gray; &:hover, diff --git a/app/styles/layout/admin-project-values.scss b/app/styles/layout/admin-project-values.scss index 904f3dd8..a7b44b10 100644 --- a/app/styles/layout/admin-project-values.scss +++ b/app/styles/layout/admin-project-values.scss @@ -1,3 +1,9 @@ +.admin-attributes { + .admin-attributes-section { + margin-bottom: 2rem; + } +} + .admin-roles { header { position: relative; @@ -12,7 +18,27 @@ } } -.project-values-options { - margin-bottom: 1rem; - text-align: right; +.project-values-title { + align-content: center; + align-items: center; + background: $whitish; + display: flex; + justify-content: space-between; + padding: .5rem 1rem; + text-transform: uppercase; + h2 { + margin: 0; + span { + margin-left: .5rem; + text-transform: none; + } + } + a { + display: inline-block; + } } + +//.project-values-options { +// margin-bottom: 1rem; +// text-align: right; +//} diff --git a/app/styles/modules/admin/admin-common.scss b/app/styles/modules/admin/admin-common.scss index dbedf557..0af84f5e 100644 --- a/app/styles/modules/admin/admin-common.scss +++ b/app/styles/modules/admin/admin-common.scss @@ -6,7 +6,7 @@ } .admin-subtitle { color: $gray-light; - margin: 0; + margin-bottom: 2rem; } .total { @extend %large; diff --git a/app/styles/modules/admin/project-csv.scss b/app/styles/modules/admin/project-csv.scss new file mode 100644 index 00000000..079fb53c --- /dev/null +++ b/app/styles/modules/admin/project-csv.scss @@ -0,0 +1,41 @@ +.project-csv { + .project-values-title { + margin-bottom: 1rem; + } + .csv-regenerate-field { + align-content: center; + align-items: center; + display: flex; + justify-content: space-between; + margin-bottom: 1rem; + a { + @extend %small; + } + span:first-child { + margin-right: .3rem; + } + } + .field-with-options { + display: flex; + margin-right: 1rem; + width: 100%; + input { + flex-grow: 1; + } + } + .option-wrapper { + align-items: center; + border: 1px solid $gray-light; + border-left: 0; + border-radius: 0 5px 5px 0; + cursor: pointer; + display: flex; + padding: 0 1rem; + } + .button { + padding: .5rem 1rem; + span { + margin: 0; + } + } +} diff --git a/app/styles/modules/common/colors-table.scss b/app/styles/modules/common/colors-table.scss index 630c3c0d..a3c6de34 100644 --- a/app/styles/modules/common/colors-table.scss +++ b/app/styles/modules/common/colors-table.scss @@ -87,7 +87,7 @@ } } .table-main { - border-bottom: 1px solid $gray-light; + border-bottom: 1px solid $whitish; .row { &:hover { background: lighten($green-taiga, 60%); diff --git a/main-sass.js b/main-sass.js index e8314453..d2d05578 100644 --- a/main-sass.js +++ b/main-sass.js @@ -131,6 +131,7 @@ exports.files = function () { 'modules/admin/third-parties', 'modules/admin/admin-third-parties-webhooks', 'modules/admin/contrib', + 'modules/admin/project-csv', //Modules user Settings 'modules/user-settings/user-profile', From 029d984e7cba33edade9cd5644afbbcb22fe7cb0 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 4 Mar 2015 13:20:38 +0100 Subject: [PATCH 136/207] configurable angular debug info --- app/coffee/app.coffee | 5 ++++- app/coffee/modules/backlog/main.coffee | 17 ++++++----------- app/coffee/modules/common/bind-scope.coffee | 13 +++++++++++++ app/partials/attachment/attachments.jade | 2 +- .../includes/components/backlog-row.jade | 2 +- .../modules/admin/admin-custom-attributes.jade | 2 +- .../includes/modules/admin/project-points.jade | 2 +- .../includes/modules/admin/project-status.jade | 2 +- .../includes/modules/admin/project-types.jade | 2 +- .../modules/admin/project-us-status.jade | 2 +- app/partials/includes/modules/kanban-table.jade | 5 +++-- .../includes/modules/search-result-table.jade | 9 ++++----- app/partials/includes/modules/sprint.jade | 2 +- .../includes/modules/taskboard-table.jade | 8 ++++---- conf/conf.example.json | 3 ++- 15 files changed, 44 insertions(+), 32 deletions(-) create mode 100644 app/coffee/modules/common/bind-scope.coffee diff --git a/app/coffee/app.coffee b/app/coffee/app.coffee index 2dec2bcc..2e6311fc 100644 --- a/app/coffee/app.coffee +++ b/app/coffee/app.coffee @@ -36,7 +36,7 @@ taiga.generateUniqueSessionIdentifier = -> taiga.sessionId = taiga.generateUniqueSessionIdentifier() -configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEventsProvider, tgLoaderProvider) -> +configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEventsProvider, tgLoaderProvider, $compileProvider) -> $routeProvider.when("/", {templateUrl: "project/projects.html", resolve: {loader: tgLoaderProvider.add()}}) @@ -224,6 +224,8 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven linewidth: "The subject must have a maximum size of %s" }) + $compileProvider.debugInfoEnabled(window.taigaConfig.debugInfo) + init = ($log, $i18n, $config, $rootscope, $auth, $events, $analytics) -> $i18n.initialize($config.get("defaultLanguage")) $log.debug("Initialize application") @@ -281,6 +283,7 @@ module.config([ "$provide", "$tgEventsProvider", "tgLoaderProvider", + "$compileProvider", configure ]) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index 681e1ddb..5904bce5 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -520,7 +520,6 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F module.controller("BacklogController", BacklogController) - ############################################################################# ## Backlog Directive ############################################################################# @@ -537,29 +536,25 @@ BacklogDirective = ($repo, $rootscope) -> if $scope.stats? removeDoomlineDom() - elements = getUsItems() stats = $scope.stats total_points = stats.total_points current_sum = stats.assigned_points - for element in elements - scope = element.scope() - - if not scope.us? - continue - - current_sum += scope.us.total_points + for us, i in $scope.visibleUserstories + current_sum += us.total_points if current_sum > total_points - addDoomLineDom(element) + domElement = $el.find('.backlog-table-body .us-item-row')[i] + addDoomLineDom(domElement) + break removeDoomlineDom = -> $el.find(".doom-line").remove() addDoomLineDom = (element) -> - element?.before(doomLineTemplate({})) + $(element).before(doomLineTemplate({})) getUsItems = -> rowElements = $el.find('.backlog-table-body .us-item-row') diff --git a/app/coffee/modules/common/bind-scope.coffee b/app/coffee/modules/common/bind-scope.coffee new file mode 100644 index 00000000..ed500d80 --- /dev/null +++ b/app/coffee/modules/common/bind-scope.coffee @@ -0,0 +1,13 @@ +module = angular.module("taigaCommon") + +BindScope = (config) -> + if !config.debugInfo + jQuery.fn.scope = () -> this.data('scope') + + link = ($scope, $el) -> + if !config.debugInfo + $el.data('scope', $scope) + + return {link: link} + +module.directive("tgBindScope", ["$tgConfig", BindScope]) diff --git a/app/partials/attachment/attachments.jade b/app/partials/attachment/attachments.jade index 363b71a8..bc025b6c 100644 --- a/app/partials/attachment/attachments.jade +++ b/app/partials/attachment/attachments.jade @@ -11,7 +11,7 @@ section.attachments input(id="add-attach", type="file", multiple="multiple") .attachment-body.sortable - .single-attachment(ng-repeat="attach in ctrl.attachments|filter:ctrl.filterAttachments track by attach.id" tg-attachment="attach") + .single-attachment(ng-repeat="attach in ctrl.attachments|filter:ctrl.filterAttachments track by attach.id" tg-attachment="attach", tg-bind-scope) .single-attachment(ng-repeat="file in ctrl.uploadingAttachments") .attachment-name diff --git a/app/partials/includes/components/backlog-row.jade b/app/partials/includes/components/backlog-row.jade index 7fbe7dbe..5a0dbf87 100644 --- a/app/partials/includes/components/backlog-row.jade +++ b/app/partials/includes/components/backlog-row.jade @@ -1,4 +1,4 @@ -div.row.us-item-row(ng-repeat="us in visibleUserstories track by us.id", tg-draggable, ng-class="{blocked: us.is_blocked}") +div.row.us-item-row(ng-repeat="us in visibleUserstories track by us.id", tg-bind-scope, ng-class="{blocked: us.is_blocked}") div.user-stories div.tags-block(tg-colorize-tags="us.tags", tg-colorize-tags-type="backlog") div.user-story-name diff --git a/app/partials/includes/modules/admin/admin-custom-attributes.jade b/app/partials/includes/modules/admin/admin-custom-attributes.jade index cc9a3f35..4b550b9b 100644 --- a/app/partials/includes/modules/admin/admin-custom-attributes.jade +++ b/app/partials/includes/modules/admin/admin-custom-attributes.jade @@ -14,7 +14,7 @@ section.custom-fields-table.basic-table div.table-body div.js-sortable - form.js-form(ng-repeat="attr in customAttributes track by attr.id") + form.js-form(ng-repeat="attr in customAttributes track by attr.id", tg-bind-scope) div.row.single-custom-field.js-view-custom-field span.icon.icon-drag-v div.custom-name diff --git a/app/partials/includes/modules/admin/project-points.jade b/app/partials/includes/modules/admin/project-points.jade index 2e8eb8f0..e23b531b 100644 --- a/app/partials/includes/modules/admin/project-points.jade +++ b/app/partials/includes/modules/admin/project-points.jade @@ -15,7 +15,7 @@ section.project-values-table div.project-values-body div.sortable - form(ng-repeat="value in values") + form(ng-repeat="value in values", tg-bind-scope) div.project-values-row.row.table-main.visualization span.icon.icon-drag-v diff --git a/app/partials/includes/modules/admin/project-status.jade b/app/partials/includes/modules/admin/project-status.jade index 00c0df30..ba9c2117 100644 --- a/app/partials/includes/modules/admin/project-status.jade +++ b/app/partials/includes/modules/admin/project-status.jade @@ -14,7 +14,7 @@ section.colors-table.admin-status-table div.table-main div.sortable - form(ng-repeat="value in values") + form(ng-repeat="value in values", tg-bind-scope) div.row.table-main.visualization span.icon.icon-drag-v div.color-column diff --git a/app/partials/includes/modules/admin/project-types.jade b/app/partials/includes/modules/admin/project-types.jade index df8843f2..6d02b520 100644 --- a/app/partials/includes/modules/admin/project-types.jade +++ b/app/partials/includes/modules/admin/project-types.jade @@ -13,7 +13,7 @@ section.colors-table div.table-main div.sortable - form(ng-repeat="value in values") + form(ng-repeat="value in values", tg-bind-scope) div.row.table-main.visualization span.icon.icon-drag-v diff --git a/app/partials/includes/modules/admin/project-us-status.jade b/app/partials/includes/modules/admin/project-us-status.jade index 8b443369..a0954c6b 100644 --- a/app/partials/includes/modules/admin/project-us-status.jade +++ b/app/partials/includes/modules/admin/project-us-status.jade @@ -18,7 +18,7 @@ section.project-us-status div.table-main div.sortable - form(ng-repeat="value in values") + form(ng-repeat="value in values", tg-bind-scope) div.row.table-main.visualization span.icon.icon-drag-v diff --git a/app/partials/includes/modules/kanban-table.jade b/app/partials/includes/modules/kanban-table.jade index 25f32625..4152d5f6 100644 --- a/app/partials/includes/modules/kanban-table.jade +++ b/app/partials/includes/modules/kanban-table.jade @@ -37,10 +37,11 @@ div.kanban-table(tg-kanban-squish-column) ng-repeat="s in usStatusList track by s.id", tg-kanban-sortable, tg-kanban-wip-limit="s.wip_limit", - tg-kanban-column-height-fixer) + tg-kanban-column-height-fixer, + tg-bind-scope) div.kanban-task(ng-repeat="us in usByStatus[s.id] track by us.id", - tg-kanban-userstory, ng-model="us", + tg-kanban-userstory, ng-model="us", tg-bind-scope, ng-class="ctrl.getCardClass(s.id)") div.kanban-column-intro(ng-if="s.is_archived", tg-kanban-archived-status-intro="s") diff --git a/app/partials/includes/modules/search-result-table.jade b/app/partials/includes/modules/search-result-table.jade index b259828c..c22f92a5 100644 --- a/app/partials/includes/modules/search-result-table.jade +++ b/app/partials/includes/modules/search-result-table.jade @@ -1,7 +1,7 @@ section.search-result-table script(type="text/ng-template", id="search-issues") - div.search-result-table-container(ng-class="{'hidden': !issues.length}") + div.search-result-table-container(ng-class="{'hidden': !issues.length}", tg-bind-scope) div.search-result-table-header div.row.title div.user-stories Issues @@ -23,7 +23,7 @@ script(type="text/ng-template", id="search-issues") script(type="text/ng-template", id="search-userstories") - div.search-result-table-container(ng-class="{'hidden': !userstories.length}") + div.search-result-table-container(ng-class="{'hidden': !userstories.length}", tg-bind-scope) div.search-result-table-header div.row.title div.user-stories User Stories @@ -44,7 +44,7 @@ script(type="text/ng-template", id="search-userstories") span Maybe try one of the tabs above or search again script(type="text/ng-template", id="search-tasks") - div.search-result-table-container(ng-class="{'hidden': !tasks.length}") + div.search-result-table-container(ng-class="{'hidden': !tasks.length}", tg-bind-scope) div.search-result-table-header div.row.title div.user-stories Task @@ -65,7 +65,7 @@ script(type="text/ng-template", id="search-tasks") span Maybe try one of the tabs above or search again script(type="text/ng-template", id="search-wikipages") - div.search-result-table-container(ng-class="{'hidden': !wikipages.length}") + div.search-result-table-container(ng-class="{'hidden': !wikipages.length}", tg-bind-scope) div.search-result-table-header div.row.title div.user-stories Wiki page @@ -80,4 +80,3 @@ script(type="text/ng-template", id="search-wikipages") span.icon.icon-issues span.title It looks like nothing was found with your search criteria. span Maybe try one of the tabs above or search again - diff --git a/app/partials/includes/modules/sprint.jade b/app/partials/includes/modules/sprint.jade index 6ceb219f..80b1e024 100644 --- a/app/partials/includes/modules/sprint.jade +++ b/app/partials/includes/modules/sprint.jade @@ -3,7 +3,7 @@ header(tg-backlog-sprint-header, ng-model="sprint") div.sprint-progress-bar(tg-progress-bar="100 * sprint.closed_points / sprint.total_points") div.sprint-table - div.row.milestone-us-item-row(ng-repeat="us in sprint.user_stories track by us.id") + div.row.milestone-us-item-row(ng-repeat="us in sprint.user_stories track by us.id", tg-bind-scope) div.column-us a.us-name.clickable(tg-nav="project-userstories-detail:project=project.slug,ref=us.ref", tg-bo-title="'#' + us.ref + ' ' + us.subject", diff --git a/app/partials/includes/modules/taskboard-table.jade b/app/partials/includes/modules/taskboard-table.jade index 9621b44e..17478b62 100644 --- a/app/partials/includes/modules/taskboard-table.jade +++ b/app/partials/includes/modules/taskboard-table.jade @@ -22,9 +22,9 @@ div.taskboard-table(tg-taskboard-squish-column) span(ng-bind="us.total_points") span points include ../components/addnewtask - div.taskboard-tasks-box.task-column(ng-repeat="st in taskStatusList track by st.id", tg-taskboard-sortable, class="squish-status-{{st.id}}", ng-class="{'column-fold':statusesFolded[st.id]}") + div.taskboard-tasks-box.task-column(ng-repeat="st in taskStatusList track by st.id", tg-taskboard-sortable, class="squish-status-{{st.id}}", ng-class="{'column-fold':statusesFolded[st.id]}", tg-bind-scope) div.taskboard-task(ng-repeat="task in usTasks[us.id][st.id] track by task.id", - tg-taskboard-task) + tg-taskboard-task, tg-bind-scope) include ../components/taskboard-task div.task-row(ng-init="us = null", ng-class="{'row-fold':usFolded[null]}") @@ -34,7 +34,7 @@ div.taskboard-table(tg-taskboard-squish-column) h3.us-title span Unassigned tasks include ../components/addnewtask.jade - div.taskboard-tasks-box.task-column(ng-repeat="st in taskStatusList track by st.id", tg-taskboard-sortable, class="squish-status-{{st.id}}", ng-class="{'column-fold':statusesFolded[st.id]}") + div.taskboard-tasks-box.task-column(ng-repeat="st in taskStatusList track by st.id", tg-taskboard-sortable, class="squish-status-{{st.id}}", ng-class="{'column-fold':statusesFolded[st.id]}", tg-bind-scope) div.taskboard-task(ng-repeat="task in usTasks[null][st.id] track by task.id", - tg-taskboard-task) + tg-taskboard-task, tg-bind-scope) include ../components/taskboard-task diff --git a/conf/conf.example.json b/conf/conf.example.json index bd6340a9..ec7a8285 100644 --- a/conf/conf.example.json +++ b/conf/conf.example.json @@ -8,5 +8,6 @@ "termsOfServiceUrl": null, "maxUploadFileSize": null, "gitHubClientId": null, - "contribPlugins": [] + "contribPlugins": [], + "debugInfo": false } From 09e050098792d34fda5672ed3a40560b1de5d8c0 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 13:02:02 +0100 Subject: [PATCH 137/207] fix webhooks enter submit --- app/coffee/modules/admin/third-parties.coffee | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/admin/third-parties.coffee b/app/coffee/modules/admin/third-parties.coffee index 640c0152..a78fdc1d 100644 --- a/app/coffee/modules/admin/third-parties.coffee +++ b/app/coffee/modules/admin/third-parties.coffee @@ -152,7 +152,7 @@ WebhookDirective = ($rs, $repo, $confirm, $loading) -> $el.on "keyup", ".edition-mode input", (event) -> if event.keyCode == 13 target = angular.element(event.currentTarget) - saveWebhook(target) + save(target) else if event.keyCode == 27 target = angular.element(event.currentTarget) cancel(target) @@ -231,8 +231,7 @@ NewWebhookDirective = ($rs, $repo, $confirm, $loading) -> formDOMNode.addClass("hidden") addWebhookDOMNode.removeClass("hidden") - formDOMNode.on "click", ".add-new", debounce 2000, (event) -> - event.preventDefault() + save = debounce 2000, () -> form = formDOMNode.checksley() return if not form.validate() @@ -246,6 +245,14 @@ NewWebhookDirective = ($rs, $repo, $confirm, $loading) -> $confirm.notify("error") form.setErrors(data) + formDOMNode.on "click", ".add-new", (event) -> + event.preventDefault() + save() + + formDOMNode.on "keyup", "input", (event) -> + if event.keyCode == 13 + save() + formDOMNode.on "click", ".cancel-new", (event) -> $scope.$apply -> initializeNewValue() From f7057179053983da27561fcb191083d3b91f6f43 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 13:07:01 +0100 Subject: [PATCH 138/207] add help csv-report link --- app/partials/includes/modules/admin/project-csv.jade | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade index 1e68581a..fe321bfb 100644 --- a/app/partials/includes/modules/admin/project-csv.jade +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -15,7 +15,6 @@ section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text span.icon.icon-reload span Regenerate - a.help-button(href="", target="_blank") + a.help-button(href="https://taiga.io/support/csv-reports/", target="_blank") span.icon.icon-help span How to use this on my own spreadsheet? - From 9dde7323d1649b253e2b156385ef264855302fc9 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 13:16:06 +0100 Subject: [PATCH 139/207] fix drag icon hover in colors table --- app/styles/modules/common/colors-table.scss | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/app/styles/modules/common/colors-table.scss b/app/styles/modules/common/colors-table.scss index a3c6de34..1da52861 100644 --- a/app/styles/modules/common/colors-table.scss +++ b/app/styles/modules/common/colors-table.scss @@ -88,11 +88,13 @@ } .table-main { border-bottom: 1px solid $whitish; - .row { - &:hover { - background: lighten($green-taiga, 60%); - cursor: move; - transition: background .2s ease-in; + .row:hover { + background: lighten($green-taiga, 60%); + cursor: move; + transition: background .2s ease-in; + .icon { + opacity: 1; + transition: opacity .2s ease-in; } } } @@ -106,8 +108,10 @@ @extend %large; color: $gray-light; margin-right: 1rem; + opacity: 0; &:hover { color: $green-taiga; + transition: all .2s ease-in; } } .icon-delete { From 3e24fa77a30115fcc075b36a3b61ee07e8a90ef6 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Mon, 9 Feb 2015 09:11:17 +0100 Subject: [PATCH 140/207] Remove user secction in main menu --- app/coffee/modules/team/main.coffee | 6 +++--- app/partials/project/project-menu.jade | 2 ++ 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/team/main.coffee b/app/coffee/modules/team/main.coffee index 69830a2f..9bc9b57a 100644 --- a/app/coffee/modules/team/main.coffee +++ b/app/coffee/modules/team/main.coffee @@ -69,18 +69,18 @@ class TeamController extends mixOf(taiga.Controller, taiga.PageMixin) loadMembers: -> return @rs.memberships.list(@scope.projectId, {}, false).then (data) => currentUser = @auth.getUser() - if not currentUser.photo? + if currentUser? and not currentUser.photo? currentUser.photo = "/images/unnamed.png" @scope.currentUser = _.find data, (membership) => - return membership.user == currentUser.id + return currentUser? and membership.user == currentUser.id @scope.totals = {} _.forEach data, (membership) => @scope.totals[membership.user] = 0 @scope.memberships = _.filter data, (membership) => - if membership.user && membership.user != currentUser.id && membership.is_user_active + if membership.user && (not currentUser? or membership.user != currentUser.id) && membership.is_user_active return membership for membership in @scope.memberships diff --git a/app/partials/project/project-menu.jade b/app/partials/project/project-menu.jade index 9b70ae09..ea56ff56 100644 --- a/app/partials/project/project-menu.jade +++ b/app/partials/project/project-menu.jade @@ -44,6 +44,7 @@ div(class="menu-container") span(class="icon icon-settings") span(class="item") Admin <% } %> + <% if (user) { %> div(class="user") div(class="user-settings") ul(class="popover") @@ -61,3 +62,4 @@ div(class="menu-container") a(href="" title="Logout" class="logout") Logout a(href="" title="User preferences" class="avatar" id="nav-user-settings") img(src="{{ user.photo }}" alt="{{ user.full_name_display }}") + <% } %> From cb782dd2b967d5885401e8cfecae7a9968f8baf2 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 26 Feb 2015 10:11:49 +0100 Subject: [PATCH 141/207] prevent dragging for anonymous user on taskboard --- app/coffee/modules/taskboard/sortable.coffee | 71 +++++++++++--------- 1 file changed, 38 insertions(+), 33 deletions(-) diff --git a/app/coffee/modules/taskboard/sortable.coffee b/app/coffee/modules/taskboard/sortable.coffee index 16aa5020..57f99711 100644 --- a/app/coffee/modules/taskboard/sortable.coffee +++ b/app/coffee/modules/taskboard/sortable.coffee @@ -36,47 +36,52 @@ module = angular.module("taigaBacklog") TaskboardSortableDirective = ($repo, $rs, $rootscope) -> link = ($scope, $el, $attrs) -> - oldParentScope = null - newParentScope = null - itemEl = null - tdom = $el + bindOnce $scope, "project", (project) -> + # If the user has not enough permissions we don't enable the sortable + if not (project.my_permissions.indexOf("modify_us") > -1) + return - deleteElement = (itemEl) -> - # Completelly remove item and its scope from dom - itemEl.scope().$destroy() - itemEl.off() - itemEl.remove() + oldParentScope = null + newParentScope = null + itemEl = null + tdom = $el - tdom.sortable({ - handle: ".taskboard-task-inner", - dropOnEmpty: true - connectWith: ".taskboard-tasks-box" - revert: 400 - }) + deleteElement = (itemEl) -> + # Completelly remove item and its scope from dom + itemEl.scope().$destroy() + itemEl.off() + itemEl.remove() - tdom.on "sortstop", (event, ui) -> - parentEl = ui.item.parent() - itemEl = ui.item - itemTask = itemEl.scope().task - itemIndex = itemEl.index() - newParentScope = parentEl.scope() + tdom.sortable({ + handle: ".taskboard-task-inner", + dropOnEmpty: true + connectWith: ".taskboard-tasks-box" + revert: 400 + }) - oldUsId = if oldParentScope.us then oldParentScope.us.id else null - oldStatusId = oldParentScope.st.id - newUsId = if newParentScope.us then newParentScope.us.id else null - newStatusId = newParentScope.st.id + tdom.on "sortstop", (event, ui) -> + parentEl = ui.item.parent() + itemEl = ui.item + itemTask = itemEl.scope().task + itemIndex = itemEl.index() + newParentScope = parentEl.scope() - if newStatusId != oldStatusId or newUsId != oldUsId - deleteElement(itemEl) + oldUsId = if oldParentScope.us then oldParentScope.us.id else null + oldStatusId = oldParentScope.st.id + newUsId = if newParentScope.us then newParentScope.us.id else null + newStatusId = newParentScope.st.id - $scope.$apply -> - $rootscope.$broadcast("taskboard:task:move", itemTask, newUsId, newStatusId, itemIndex) + if newStatusId != oldStatusId or newUsId != oldUsId + deleteElement(itemEl) - ui.item.find('a').removeClass('noclick') + $scope.$apply -> + $rootscope.$broadcast("taskboard:task:move", itemTask, newUsId, newStatusId, itemIndex) - tdom.on "sortstart", (event, ui) -> - oldParentScope = ui.item.parent().scope() - ui.item.find('a').addClass('noclick') + ui.item.find('a').removeClass('noclick') + + tdom.on "sortstart", (event, ui) -> + oldParentScope = ui.item.parent().scope() + ui.item.find('a').addClass('noclick') $scope.$on "$destroy", -> $el.off() From b5c0b36e007374fef0b1330ae036d7fac8638f83 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 26 Feb 2015 10:22:28 +0100 Subject: [PATCH 142/207] hide current user if not exists --- app/partials/includes/modules/team/team-table.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/includes/modules/team/team-table.jade b/app/partials/includes/modules/team/team-table.jade index 9ee2279c..f4e0c739 100644 --- a/app/partials/includes/modules/team/team-table.jade +++ b/app/partials/includes/modules/team/team-table.jade @@ -27,7 +27,7 @@ section.table-team.basic-table div.popover.attribute-explanation span Total Points - div.hero(tg-team-current-user, stats="stats", currentuser="currentUser", projectid="projectId", issuesEnabled="issuesEnabled", tasksenabled="tasksEnabled", wikienabled="wikiEnabled") + div.hero(tg-team-current-user, stats="stats", currentuser="currentUser", projectid="projectId", issuesEnabled="issuesEnabled", tasksenabled="tasksEnabled", wikienabled="wikiEnabled", ng-if="::currentUser") h2(ng-show="memberships.length") span Team > From 8fd60856f967bdba077be46e09cd99604620ac6a Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 26 Feb 2015 11:52:45 +0100 Subject: [PATCH 143/207] fix comment list for annonymous users --- app/coffee/modules/common/history.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/common/history.coffee b/app/coffee/modules/common/history.coffee index fcd1d961..c7ab11d5 100644 --- a/app/coffee/modules/common/history.coffee +++ b/app/coffee/modules/common/history.coffee @@ -258,7 +258,7 @@ HistoryDirective = ($log, $loading, $qqueue, $template, $confirm) -> deleteCommentDate: moment(comment.delete_comment_date).format("DD MMM YYYY HH:mm") if comment.delete_comment_date deleteCommentUser: comment.delete_comment_user.name if comment.delete_comment_user?.name activityId: comment.id - canDeleteComment: comment.user.pk == $scope.user.id or $scope.project.my_permissions.indexOf("modify_project") > -1 + canDeleteComment: comment.user.pk == $scope.user?.id or $scope.project.my_permissions.indexOf("modify_project") > -1 }) renderChange = (change) -> From 69c9f03b90c11d95b3db04abe037803fef22ffa4 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 26 Feb 2015 12:02:15 +0100 Subject: [PATCH 144/207] fix errors for anonymous users in the wiki --- app/coffee/modules/wiki/main.coffee | 1 + app/styles/layout/wiki.scss | 12 ++++++++---- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/app/coffee/modules/wiki/main.coffee b/app/coffee/modules/wiki/main.coffee index 381c4848..8aad38e7 100644 --- a/app/coffee/modules/wiki/main.coffee +++ b/app/coffee/modules/wiki/main.coffee @@ -238,6 +238,7 @@ EditableWikiContentDirective = ($window, $document, $repo, $confirm, $loading, $ $el.on "mouseup", ".view-wiki-content", (event) -> target = angular.element(event.target) return if getSelectedText() + return if not isEditable() return if target.is('a') return if target.is('pre') diff --git a/app/styles/layout/wiki.scss b/app/styles/layout/wiki.scss index 9bb55308..48cb40ab 100644 --- a/app/styles/layout/wiki.scss +++ b/app/styles/layout/wiki.scss @@ -24,10 +24,6 @@ position: relative; .view-wiki-content { &:hover { - .wysiwyg { - background: $whitish; - cursor: pointer; - } .edit { opacity: 1; top: -1.5rem; @@ -67,4 +63,12 @@ top: .4rem; } } + &.editable { + &:hover { + .wysiwyg { + background: $whitish; + cursor: pointer; + } + } + } } From fe40b0bcd65a854061c784664cc812f24093b2f9 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 08:43:27 +0100 Subject: [PATCH 145/207] external user permissions --- app/coffee/modules/admin/roles.coffee | 59 +++++++++++++++++++---- app/partials/admin/admin-roles.jade | 4 +- app/styles/modules/admin/admin-roles.scss | 6 +++ 3 files changed, 58 insertions(+), 11 deletions(-) diff --git a/app/coffee/modules/admin/roles.coffee b/app/coffee/modules/admin/roles.coffee index b14effb2..693ae80c 100644 --- a/app/coffee/modules/admin/roles.coffee +++ b/app/coffee/modules/admin/roles.coffee @@ -64,16 +64,36 @@ class RolesController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fil loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => @scope.project = project + @scope.$emit('project:loaded', project) @scope.anyComputableRole = _.some(_.map(project.roles, (point) -> point.computable)) return project + loadExternalUserRole: (roles) -> + roles = roles.map (role) -> + role.external_user = false + + return role + + public_permission = { + "name": "External User", + "permissions": @scope.project.public_permissions, + "external_user": true + } + + roles.push(public_permission) + + return roles + loadRoles: -> - return @rs.roles.list(@scope.projectId).then (data) => - @scope.roles = data - @scope.role = @scope.roles[0] - return data + return @rs.roles.list(@scope.projectId) + .then @loadExternalUserRole + .then (roles) => + @scope.roles = roles + @scope.role = @scope.roles[0] + + return roles loadInitialData: -> promise = @repo.resolve({pslug: @params.pslug}).then (data) => @@ -256,7 +276,7 @@ RolePermissionsDirective = ($rootscope, $repo, $confirm) ->
<%- permission.description %>
- checked="checked"<% } %>/> + disabled="disabled"<% } %> <% if(permission.active) { %>checked="checked"<% } %>/>
Yes No @@ -279,10 +299,23 @@ RolePermissionsDirective = ($rootscope, $repo, $confirm) -> setActivePermissions = (permissions) -> return _.map(permissions, (x) -> _.extend({}, x, {active: x["key"] in role.permissions})) + isPermissionEditable = (permission, role, project) -> + if role.external_user && + !project.is_private && + permission.key.indexOf("view_") == 0 + return false + else + return true + setActivePermissionsPerCategory = (category) -> - return _.map(category, (x) -> - _.extend({}, x, { - activePermissions: _.filter(x["permissions"], "active").length + return _.map(category, (cat) -> + cat.permissions = cat.permissions.map (permission) -> + permission.editable = isPermissionEditable(permission, role, $scope.project) + + return permission + + _.extend({}, cat, { + activePermissions: _.filter(cat["permissions"], "active").length }) ) @@ -366,6 +399,7 @@ RolePermissionsDirective = ($rootscope, $repo, $confirm) -> return activePermissions target = angular.element(event.currentTarget) + $scope.role.permissions = getActivePermissions() onSuccess = (role) -> @@ -381,7 +415,14 @@ RolePermissionsDirective = ($rootscope, $repo, $confirm) -> target.prop "checked", !target.prop("checked") $scope.role.permissions = getActivePermissions() - $repo.save($scope.role).then onSuccess, onError + if $scope.role.external_user + $scope.project.public_permissions = $scope.role.permissions + $scope.project.anon_permissions = $scope.role.permissions.filter (permission) -> + return permission.indexOf("view_") == 0 + + $repo.save($scope.project) + else + $repo.save($scope.role).then onSuccess, onError $scope.$on "$destroy", -> $el.off() diff --git a/app/partials/admin/admin-roles.jade b/app/partials/admin/admin-roles.jade index 52dc954f..94982f98 100644 --- a/app/partials/admin/admin-roles.jade +++ b/app/partials/admin/admin-roles.jade @@ -8,7 +8,7 @@ div.wrapper.roles(ng-controller="RolesController as ctrl", section.main.admin-roles.admin-common .header-with-actions include ../includes/components/mainTitle - .action-buttons + .action-buttons(ng-if="!role.external_user") a.button-red.delete-role(href="", title="Delete", ng-click="ctrl.delete()") span Delete @@ -24,7 +24,7 @@ div.wrapper.roles(ng-controller="RolesController as ctrl", div.any-computable-role(ng-hide="anyComputableRole") Be careful, no role in your project will be able to estimate the point value for user stories - div.general-category + div.general-category(ng-if="!role.external_user") | When enabled, members assigned to this role will be able to estimate the point value for user stories div.check input(type="checkbox", ng-model="role.computable", ng-change="ctrl.setComputable()") diff --git a/app/styles/modules/admin/admin-roles.scss b/app/styles/modules/admin/admin-roles.scss index 58203d80..daa55c21 100644 --- a/app/styles/modules/admin/admin-roles.scss +++ b/app/styles/modules/admin/admin-roles.scss @@ -101,5 +101,11 @@ opacity: 0; } } + input:disabled { + cursor: auto; + + div { + background-color: #ccc; + } + } } } From 64481effbcd60b315433ec771d1bc82c48e9e910 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 09:11:01 +0100 Subject: [PATCH 146/207] prevent edit external user role name --- app/partials/admin/admin-roles.jade | 37 ++++++++++++++++------------- 1 file changed, 21 insertions(+), 16 deletions(-) diff --git a/app/partials/admin/admin-roles.jade b/app/partials/admin/admin-roles.jade index 94982f98..2899d960 100644 --- a/app/partials/admin/admin-roles.jade +++ b/app/partials/admin/admin-roles.jade @@ -13,23 +13,28 @@ div.wrapper.roles(ng-controller="RolesController as ctrl", span Delete - div(tg-edit-role) - .edit-role - input(type="text", value="{{ role.name }}") - a.save.icon.icon-floppy(href="", title="Save") + div(ng-if="!role.external_user") + div(tg-edit-role) + .edit-role + input(type="text", value="{{ role.name }}") + a.save.icon.icon-floppy(href="", title="Save") + p.total + span.role-name(title="{{ role.members_count }} members with this role") {{ role.name }} + a.edit-value.icon.icon-edit + + div.any-computable-role(ng-hide="anyComputableRole") Be careful, no role in your project will be able to estimate the point value for user stories + + div.general-category + | When enabled, members assigned to this role will be able to estimate the point value for user stories + div.check + input(type="checkbox", ng-model="role.computable", ng-change="ctrl.setComputable()") + div + span.check-text.check-yes Yes + span.check-text.check-no No + + div(ng-if="role.external_user") p.total - span.role-name(title="{{ role.members_count }} members with this role") {{ role.name }} - a.edit-value.icon.icon-edit - - div.any-computable-role(ng-hide="anyComputableRole") Be careful, no role in your project will be able to estimate the point value for user stories - - div.general-category(ng-if="!role.external_user") - | When enabled, members assigned to this role will be able to estimate the point value for user stories - div.check - input(type="checkbox", ng-model="role.computable", ng-change="ctrl.setComputable()") - div - span.check-text.check-yes Yes - span.check-text.check-no No + span.role-name {{ role.name }} div(tg-role-permissions, ng-model="role") From e778e8b1003da0f17bb50677fafdb24a870f6f37 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 09:15:13 +0100 Subject: [PATCH 147/207] update external user category summary --- app/coffee/modules/admin/roles.coffee | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/admin/roles.coffee b/app/coffee/modules/admin/roles.coffee index 693ae80c..cbd45d1a 100644 --- a/app/coffee/modules/admin/roles.coffee +++ b/app/coffee/modules/admin/roles.coffee @@ -402,8 +402,8 @@ RolePermissionsDirective = ($rootscope, $repo, $confirm) -> $scope.role.permissions = getActivePermissions() - onSuccess = (role) -> - categories = generateCategoriesFromRole(role) + onSuccess = () -> + categories = generateCategoriesFromRole($scope.role) categoryId = target.parents(".category-config").data("id") renderResume(target.parents(".category-config"), categories[categoryId]) $rootscope.$broadcast("projects:reload") @@ -420,7 +420,7 @@ RolePermissionsDirective = ($rootscope, $repo, $confirm) -> $scope.project.anon_permissions = $scope.role.permissions.filter (permission) -> return permission.indexOf("view_") == 0 - $repo.save($scope.project) + $repo.save($scope.project).then onSuccess, onError else $repo.save($scope.role).then onSuccess, onError From cd237d832a9d752b8d280fde9e1edf3cbee2ae1f Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 09:46:18 +0100 Subject: [PATCH 148/207] change project privacy --- app/partials/admin/admin-project-profile.jade | 4 ++-- .../modules/admin/admin-project-profile.scss | 23 +++++++++++++------ 2 files changed, 18 insertions(+), 9 deletions(-) diff --git a/app/partials/admin/admin-project-profile.jade b/app/partials/admin/admin-project-profile.jade index 6ee7c272..90a21b09 100644 --- a/app/partials/admin/admin-project-profile.jade +++ b/app/partials/admin/admin-project-profile.jade @@ -40,11 +40,11 @@ div.wrapper(tg-project-profile, ng-controller="ProjectProfileController as ctrl" tg-privacy-settings-inputs div.privacy-settings div - input.hidden(type="radio", disabled="disabled") + input.privacy-project(type="radio", name="private-project", ng-model="project.is_private", ng-value="false") label.trans-button(for="public-project") span Public Project div - input.hidden(type="radio", checked="checked", disabled="disabled") + input.privacy-project(type="radio", name="private-project", ng-model="project.is_private", ng-value="true") label.trans-button(for="private-project") span Private Project diff --git a/app/styles/modules/admin/admin-project-profile.scss b/app/styles/modules/admin/admin-project-profile.scss index 0339fc66..cefec654 100644 --- a/app/styles/modules/admin/admin-project-profile.scss +++ b/app/styles/modules/admin/admin-project-profile.scss @@ -21,14 +21,15 @@ .privacy-settings { display: flex; margin-bottom: 2rem; - div { + > div { flex-basis: 0; flex-grow: 1; + overflow: hidden; + position: relative; &:first-child { margin-right: .5rem; } } - // TODO: This should change when public projects available label { @extend %title; border: 1px solid $gray-light; @@ -39,14 +40,22 @@ span { color: $gray-light; } - // &:hover { - // border: 1px solid $fresh-taiga; - // } } - input:checked+label { + } + .privacy-project { + cursor: pointer; + height: 500px; + left: -10px; + opacity: 0; + position: absolute; + top: -10px; + width: 500px; + z-index: 999; + } + .privacy-project:checked { + + label { background: $fresh-taiga; border: 1px solid $fresh-taiga; - cursor: default; span { color: $white; } From d84bc9ff4f8b65e93f74974dd00973838cd55f4e Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Tue, 10 Mar 2015 14:11:54 +0100 Subject: [PATCH 149/207] Removing unnecesary text --- app/partials/admin/admin-project-profile.jade | 2 -- 1 file changed, 2 deletions(-) diff --git a/app/partials/admin/admin-project-profile.jade b/app/partials/admin/admin-project-profile.jade index 90a21b09..b504ceb9 100644 --- a/app/partials/admin/admin-project-profile.jade +++ b/app/partials/admin/admin-project-profile.jade @@ -48,8 +48,6 @@ div.wrapper(tg-project-profile, ng-controller="ProjectProfileController as ctrl" label.trans-button(for="private-project") span Private Project - p All projects are private during Taiga's beta period. - button.button-green.submit-button(type="submit", title="Save") Save a.delete-project(href="", title="Delete this project", ng-click="ctrl.openDeleteLightbox()") Delete this project From d435d92443869ae4d474a42e5af5aa1b95c96ebd Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 14:55:09 +0100 Subject: [PATCH 150/207] fix-taiga-front-extras plugins load --- app/plugins/humanshtml/humanshtml.coffee | 2 +- app/plugins/terms/terms.coffee | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/app/plugins/humanshtml/humanshtml.coffee b/app/plugins/humanshtml/humanshtml.coffee index 0cf8312d..59130f8a 100644 --- a/app/plugins/humanshtml/humanshtml.coffee +++ b/app/plugins/humanshtml/humanshtml.coffee @@ -23,7 +23,7 @@ # and add additional template. taiga = @.taiga -module = angular.module("taigaPlugins", ["ngRoute"]) +module = angular.module("taigaPlugins") configure = ($routeProvider) -> $routeProvider.when("/humans.html", {"templateUrl": "/plugins/humanshtml/templates/humans.html"}) diff --git a/app/plugins/terms/terms.coffee b/app/plugins/terms/terms.coffee index 512445ad..ef4fa4d2 100644 --- a/app/plugins/terms/terms.coffee +++ b/app/plugins/terms/terms.coffee @@ -21,7 +21,7 @@ taiga = @.taiga -module = angular.module("taigaPlugins", ["ngRoute"]) +module = angular.module("taigaPlugins") template = _.template("""

From c1dd7e52d05c5a110d270247c9b5b2f304b77aab Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 10 Mar 2015 14:57:57 +0100 Subject: [PATCH 151/207] remove unnecessary directive --- app/partials/admin/admin-project-profile.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/admin/admin-project-profile.jade b/app/partials/admin/admin-project-profile.jade index b504ceb9..cb90def2 100644 --- a/app/partials/admin/admin-project-profile.jade +++ b/app/partials/admin/admin-project-profile.jade @@ -37,7 +37,7 @@ div.wrapper(tg-project-profile, ng-controller="ProjectProfileController as ctrl" textarea(name="description", placeholder="Description", id="project-description", ng-model="project.description", data-required="true") - tg-privacy-settings-inputs + div div.privacy-settings div input.privacy-project(type="radio", name="private-project", ng-model="project.is_private", ng-value="false") From c59782caefe31290fab3a0a08af92cac8983e2bd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Tue, 10 Mar 2015 17:07:36 +0100 Subject: [PATCH 152/207] Fix how the update of user data is done when update email is requiered --- app/coffee/modules/user-settings/main.coffee | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/user-settings/main.coffee b/app/coffee/modules/user-settings/main.coffee index 3b221008..90fa56b2 100644 --- a/app/coffee/modules/user-settings/main.coffee +++ b/app/coffee/modules/user-settings/main.coffee @@ -91,7 +91,8 @@ UserProfileDirective = ($confirm, $auth, $repo) -> changeEmail = $scope.user.isAttributeModified("email") onSuccess = (data) => - $auth.setUser($scope.user) + user = $model.make_model("users", data) + $auth.setUser(user) if changeEmail $confirm.success("Check your inbox!
We have sent a mail to your account
From 7a1f4c64a1ec051ded5aefa4179036167e1c004c Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Mar 2015 08:38:45 +0100 Subject: [PATCH 153/207] fix #2394 - move us to current sprint --- app/coffee/modules/backlog/main.coffee | 3 ++- app/coffee/modules/common/bind-scope.coffee | 4 +++- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index 5904bce5..93c84ba7 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -605,7 +605,8 @@ BacklogDirective = ($repo, $rootscope) -> ussDom = $el.find(".backlog-table-body .user-stories input:checkbox:checked") ussToMove = _.map ussDom, (item) -> - itemScope = angular.element(item).scope() + item = $(item).closest('.tg-scope') + itemScope = item.scope() itemScope.us.milestone = $scope.sprints[0].id return itemScope.us diff --git a/app/coffee/modules/common/bind-scope.coffee b/app/coffee/modules/common/bind-scope.coffee index ed500d80..2278e4b2 100644 --- a/app/coffee/modules/common/bind-scope.coffee +++ b/app/coffee/modules/common/bind-scope.coffee @@ -6,7 +6,9 @@ BindScope = (config) -> link = ($scope, $el) -> if !config.debugInfo - $el.data('scope', $scope) + $el + .data('scope', $scope) + .addClass('tg-scope') return {link: link} From 4d2ffcbe51c3ebcea59344c3da2d82ba72ec64b9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Mar 2015 08:43:09 +0100 Subject: [PATCH 154/207] Fix history broken width. TG-2396 #STATUS-ready-for-test --- app/styles/modules/common/history.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/modules/common/history.scss b/app/styles/modules/common/history.scss index ad14a78f..6fad337a 100644 --- a/app/styles/modules/common/history.scss +++ b/app/styles/modules/common/history.scss @@ -227,7 +227,7 @@ } .activity-content { flex-shrink: 0; - max-width: calc(100% - 80px); + width: calc(100% - 80px); } .changes { background: $whitish; From 8aa88cf28d0624acac3f9ce0017c73c9d56c03ae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Mar 2015 09:00:49 +0100 Subject: [PATCH 155/207] Remove all Help notion code --- app/coffee/modules/common/lightboxes.coffee | 38 ------------------- .../components/help-notion-button.jade | 12 ------ .../help-notions/lightbox-generic-notion.jade | 12 ------ ...notion-admin-project-values-us-points.jade | 12 ------ app/styles/components/help-notion-button.scss | 11 ------ main-sass.js | 1 - scsslint.yml | 1 - 7 files changed, 87 deletions(-) delete mode 100644 app/partials/includes/components/help-notion-button.jade delete mode 100644 app/partials/includes/modules/help-notions/lightbox-generic-notion.jade delete mode 100644 app/partials/includes/modules/help-notions/lightbox-notion-admin-project-values-us-points.jade delete mode 100644 app/styles/components/help-notion-button.scss diff --git a/app/coffee/modules/common/lightboxes.coffee b/app/coffee/modules/common/lightboxes.coffee index b13ffff9..a11b6048 100644 --- a/app/coffee/modules/common/lightboxes.coffee +++ b/app/coffee/modules/common/lightboxes.coffee @@ -602,41 +602,3 @@ WatchersLightboxDirective = ($repo, lightboxService, lightboxKeyboardNavigationS } module.directive("tgLbWatchers", ["$tgRepo", "lightboxService", "lightboxKeyboardNavigationService", "$tgTemplate", WatchersLightboxDirective]) - -############################################################################# -## Notion Lightbox Directive -############################################################################# - -# Lightbox -NotionLightboxDirective = (lightboxService) -> - link = ($scope, $el, $attrs, $model) -> - $scope.$on "notion:open", (event, lightboxId) -> - if $el.attr("id") == lightboxId - lightboxService.open($el) - - $el.on "click", ".button-green", (event) -> - lightboxService.close($el) - - $scope.$on "$destroy", -> - $el.off() - - return {link:link} - -module.directive("tgLbNotion", ["lightboxService", NotionLightboxDirective]) - - -# Button -NotionButtonDirective = ($log, $rootScope) -> - link = ($scope, $el, $attrs, $model) -> - if not $attrs.tgLbNotionButton? - return $log.error "NotionButtonDirective: the directive need the id of the notion lightbox" - - $el.on "click", -> - $rootScope.$broadcast("notion:open", $attrs.tgLbNotionButton) - - $scope.$on "$destroy", -> - $el.off() - - return {link:link} - -module.directive("tgLbNotionButton", ["$log", "$rootScope", NotionButtonDirective]) diff --git a/app/partials/includes/components/help-notion-button.jade b/app/partials/includes/components/help-notion-button.jade deleted file mode 100644 index 510a7fbd..00000000 --- a/app/partials/includes/components/help-notion-button.jade +++ /dev/null @@ -1,12 +0,0 @@ -//- NOTE: - Add a lightbox-notion at the end of parent template. Ex: -//- -//- div.hide.lightbox.lightbox-generic-notion(id="notion-admin-project-values-us-points", -//- tg-lb-notion) -//- include views/modules/help-notions/lightbox-notion-admin-project-values-us-points -//- -//- - Defined variable 'helpLightboxId' in parent template. Ex: -//- -//- - var helpLightboxId = "admin-project-values-us-points" -//- include views/components/help - -a.icon.icon-idea.help(href="", title="You need some help?", tg-lb-notion-button=helpLightboxId) diff --git a/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade b/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade deleted file mode 100644 index 1c312656..00000000 --- a/app/partials/includes/modules/help-notions/lightbox-generic-notion.jade +++ /dev/null @@ -1,12 +0,0 @@ -a.close(href="", title="close") - span.icon.icon-delete - -section - h2.title - block title - - block content - - div.options - a.button-green(href="", title="Accept") - span Accept diff --git a/app/partials/includes/modules/help-notions/lightbox-notion-admin-project-values-us-points.jade b/app/partials/includes/modules/help-notions/lightbox-notion-admin-project-values-us-points.jade deleted file mode 100644 index e8e70206..00000000 --- a/app/partials/includes/modules/help-notions/lightbox-notion-admin-project-values-us-points.jade +++ /dev/null @@ -1,12 +0,0 @@ -extends lightbox-generic-notion - -block title - About User Story (US) Points: - -block content - p - | Most people start off with 1 point = 1 man day of effort. If you're new to scrum & agile start there. - p - | After the first week if you and your team expected to accomplish 25 points (i.e. 5 people 5 full days) - | and only got half done, learn from your findings, and adjust expectations for the following week. - | By doing so you'll learn your teams true 'velocity.' diff --git a/app/styles/components/help-notion-button.scss b/app/styles/components/help-notion-button.scss deleted file mode 100644 index 528c8f63..00000000 --- a/app/styles/components/help-notion-button.scss +++ /dev/null @@ -1,11 +0,0 @@ -a.help { - color: $gray-light; - position: absolute; - right: 1rem; - top: 1rem; - transition: color .2s linear; - &:hover { - color: $green-taiga; - transition: color .2s linear; - } -} diff --git a/main-sass.js b/main-sass.js index d2d05578..5ebdb49f 100644 --- a/main-sass.js +++ b/main-sass.js @@ -52,7 +52,6 @@ exports.files = function () { 'components/select-color', 'components/loader', 'components/loading-bar', - 'components/help-notion-button', 'components/beta', 'components/markitup', 'components/markdown-help', diff --git a/scsslint.yml b/scsslint.yml index 42a06f1c..3aacec8f 100644 --- a/scsslint.yml +++ b/scsslint.yml @@ -83,7 +83,6 @@ linters: exclude: - 'app/styles/components/buttons.scss' - 'app/styles/layout/forms.scss' - - 'app/styles/components/help-notion-button.scss' - 'app/styles/components/markdown-help.scss' SelectorDepth: From 3adf0cd3dbfd6568992b5ffb8ce669e38b5b752e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 11 Mar 2015 10:09:34 +0100 Subject: [PATCH 156/207] Bug#2389 Not show csv download icon if the url doesn't exists --- app/partials/includes/modules/admin/project-csv.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade index fe321bfb..16948073 100644 --- a/app/partials/includes/modules/admin/project-csv.jade +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -2,7 +2,7 @@ section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text div.project-values-title h2 Export #{csvType} Data span (.csv format) - a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}") + a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}", ng-show="csvUrl") span Download CSV p Get all information about your project #{csvType}. Save all your data to a .csv file and open it in your favourite text editor or spreadsheet. You will be able to visualize and analize all your data easily. From a93fb7006a41cc9f0e91d9629e38b8835301f92c Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Mar 2015 11:05:31 +0100 Subject: [PATCH 157/207] fix 2393 - fix if I filter by status and tag the status filter disappear - filter by status - check if the tags doesn't have an US with this status are disappear --- app/coffee/modules/backlog/filters.coffee | 2 - app/coffee/modules/backlog/main.coffee | 80 +++++++++++------------ 2 files changed, 40 insertions(+), 42 deletions(-) diff --git a/app/coffee/modules/backlog/filters.coffee b/app/coffee/modules/backlog/filters.coffee index 56199e3e..8185fdf2 100644 --- a/app/coffee/modules/backlog/filters.coffee +++ b/app/coffee/modules/backlog/filters.coffee @@ -89,12 +89,10 @@ BacklogFiltersDirective = ($log, $location, $templates) -> selectedFilters.push(filter) $scope.$apply -> $ctrl.selectFilter(type, id) - $ctrl.filterVisibleUserstories() else selectedFilters = _.reject(selectedFilters, filter) $scope.$apply -> $ctrl.unselectFilter(type, id) - $ctrl.filterVisibleUserstories() renderSelectedFilters(selectedFilters) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index 93c84ba7..518042f2 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -204,8 +204,9 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F # NOTE: Fix order of USs because the filter orderBy does not work propertly in the partials files @scope.userstories = _.sortBy(userstories, "backlog_order") - @.generateFilters() + @.setSearchDataFilters() @.filterVisibleUserstories() + @.generateFilters() @rootscope.$broadcast("filters:loaded", @scope.filters) # The broadcast must be executed when the DOM has been fully reloaded. @@ -246,32 +247,16 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F @scope.visibleUserstories = [] # Filter by tags - selectedTags = _.filter(@scope.filters.tags, "selected") - selectedTags = _.map(selectedTags, "name") - - if selectedTags.length == 0 - @scope.visibleUserstories = _.clone(@scope.userstories, false) - else - @scope.visibleUserstories = _.reject @scope.userstories, (us) => - if _.intersection(selectedTags, us.tags).length == 0 - return true - return false + @scope.visibleUserstories = _.reject @scope.userstories, (us) => + return _.some us.tags, (tag) => + return @isFilterSelected("tag", tag) # Filter by status - selectedStatuses = _.filter(@scope.filters.statuses, "selected") - selectedStatuses = _.map(selectedStatuses, "id") + @scope.visibleUserstories = _.filter @scope.visibleUserstories, (us) => + if @searchdata["statuses"] && Object.keys(@searchdata["statuses"]).length + return @isFilterSelected("statuses", taiga.toString(us.status)) - if selectedStatuses.length > 0 - @scope.visibleUserstories = _.reject @scope.visibleUserstories, (us) => - res = _.find(selectedStatuses, (x) -> x == taiga.toString(us.status)) - return not res - - @rs.userstories.storeQueryParams(@scope.projectId, { - "status": selectedStatuses, - "tags": selectedTags, - "project": @scope.projectId - "milestone": null - }) + return true prepareBulkUpdateData: (uses, field="backlog_order") -> return _.map(uses, (x) -> {"us_id": x.id, "order": x[field]}) @@ -428,31 +413,33 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F return promise - getUrlFilters: -> - return _.pick(@location.search(), "statuses", "tags", "q") + isFilterSelected: (type, id) -> + if @searchdata[type]? and @searchdata[type][id] + return true + return false - generateFilters: -> + setSearchDataFilters: () -> urlfilters = @.getUrlFilters() if urlfilters.q @scope.filtersQ = @scope.filtersQ or urlfilters.q - searchdata = {} + @searchdata = {} for name, value of urlfilters - if not searchdata[name]? - searchdata[name] = {} + if not @searchdata[name]? + @searchdata[name] = {} for val in taiga.toString(value).split(",") - searchdata[name][val] = true + @searchdata[name][val] = true - isSelected = (type, id) -> - if searchdata[type]? and searchdata[type][id] - return true - return false + getUrlFilters: -> + return _.pick(@location.search(), "statuses", "tags", "q") + generateFilters: -> @scope.filters = {} - plainTags = _.flatten(_.filter(_.map(@scope.userstories, "tags"))) + #tags + plainTags = _.flatten(_.filter(_.map(@scope.visibleUserstories, "tags"))) plainTags.sort() @scope.filters.tags = _.map _.countBy(plainTags), (v, k) => @@ -463,10 +450,14 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F color: @scope.project.tags_colors[k], count: v } - obj.selected = true if isSelected("tags", obj.id) + obj.selected = true if @isFilterSelected("tags", obj.id) return obj - plainStatuses = _.map(@scope.userstories, "status") + selectedTags = _.filter(@scope.filters.tags, "selected") + selectedTags = _.map(selectedTags, "name") + + #status + plainStatuses = _.map(@scope.visibleUserstories, "status") plainStatuses = _.filter plainStatuses, (status) => if status @@ -480,11 +471,20 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F color: @scope.usStatusById[k].color, count:v } - obj.selected = true if isSelected("statuses", obj.id) + obj.selected = true if @isFilterSelected("statuses", obj.id) return obj - return @scope.filters + selectedStatuses = _.filter(@scope.filters.statuses, "selected") + selectedStatuses = _.map(selectedStatuses, "id") + + #store query params + @rs.userstories.storeQueryParams(@scope.projectId, { + "status": selectedStatuses, + "tags": selectedTags, + "project": @scope.projectId + "milestone": null + }) ## Template actions From 31e087a754b97a760ae31581d11fb7563864d7a4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Wed, 11 Mar 2015 11:36:29 +0100 Subject: [PATCH 158/207] Fix ##2399: Errors CRUD over admin > attributes items --- app/coffee/modules/admin/project-values.coffee | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 217f5a5a..9ab4d917 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -165,10 +165,11 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> $el.find(".new-value input:visible").first().focus() saveValue = (target) -> - form = target.parents("form").checksley() + formEl = target.parents("form") + form = formEl.checksley() return if not form.validate() - value = target.scope().value + value = formEl.scope().value promise = $repo.save(value) promise.then => row = target.parents(".row.table-main") @@ -179,7 +180,8 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> form.setErrors(data) saveNewValue = (target) -> - form = target.parents("form").checksley() + formEl = target.parents("form") + form = formEl.checksley() return if not form.validate() $scope.newValue.project = $scope.project.id @@ -199,7 +201,8 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> cancel = (target) -> row = target.parents(".row.table-main") - value = target.scope().value + formEl = target.parents("form") + value = formEl.scope().value $scope.$apply -> row.addClass("hidden") value.revert() @@ -261,7 +264,9 @@ ProjectValuesDirective = ($log, $repo, $confirm, $location, animationFrame) -> $el.on "click", ".delete-value", (event) -> event.preventDefault() target = angular.element(event.currentTarget) - value = target.scope().value + formEl = target.parents("form") + value = formEl.scope().value + choices = {} _.each $scope.values, (option) -> if value.id != option.id From b215b04d8f5e822c0164992f3239572198f68b00 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Wed, 11 Mar 2015 11:52:03 +0100 Subject: [PATCH 159/207] Fix legibility of errors in fields. #TG-2262 #STATUS-ready-for-test --- app/styles/layout/forms.scss | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/app/styles/layout/forms.scss b/app/styles/layout/forms.scss index ad69d0f2..efc8d085 100644 --- a/app/styles/layout/forms.scss +++ b/app/styles/layout/forms.scss @@ -28,6 +28,10 @@ textarea { @include placeholder { color: darken($gray-light, 10%); } + &.checksley-error { + border: 1px solid $red; + transition: border .3s linear; + } } textarea { @@ -35,9 +39,12 @@ textarea { resize: vertical; } + .checksley-error-list { @extend %small; + background: rgba($whitish, .8); margin-bottom: 0; + padding: 0 .5rem; position: absolute; right: 2rem; top: 10px; From 8c2dc657239623e1e725c3922024e0d88ae494d9 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Mar 2015 11:53:12 +0100 Subject: [PATCH 160/207] fix firefox open popup blink --- app/coffee/modules/common/lightboxes.coffee | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/coffee/modules/common/lightboxes.coffee b/app/coffee/modules/common/lightboxes.coffee index a11b6048..f270837d 100644 --- a/app/coffee/modules/common/lightboxes.coffee +++ b/app/coffee/modules/common/lightboxes.coffee @@ -45,6 +45,8 @@ class LightboxService extends taiga.Service @animationFrame.add => $el.addClass("open") + + @animationFrame.add => lightboxContent.show() defered.resolve() From 0191868d82471402ddd3a487c006c65523795bf6 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Mar 2015 12:04:22 +0100 Subject: [PATCH 161/207] fix change avatar --- app/coffee/modules/user-settings/main.coffee | 2 +- app/partials/user/user-profile.jade | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/user-settings/main.coffee b/app/coffee/modules/user-settings/main.coffee index 90fa56b2..203b978d 100644 --- a/app/coffee/modules/user-settings/main.coffee +++ b/app/coffee/modules/user-settings/main.coffee @@ -139,7 +139,7 @@ UserAvatarDirective = ($auth, $model, $rs, $confirm) -> $confirm.notify('error', response.data._error_message) # Change photo - $el.on "click", ".button.change", -> + $el.on "click", ".js-change-avatar", -> $el.find("#avatar-field").click() $el.on "change", "#avatar-field", (event) -> diff --git a/app/partials/user/user-profile.jade b/app/partials/user/user-profile.jade index 9f3dd154..6c39fb79 100644 --- a/app/partials/user/user-profile.jade +++ b/app/partials/user/user-profile.jade @@ -20,7 +20,7 @@ div.wrapper(tg-user-profile, ng-controller="UserSettingsController as ctrl", tg-avatar-model="avatarAttachment") p The image will be cropped to 80x80px.
span.size-info.hidden(tg-bo-html="maxFileSizeMsg") - a.button-green.change(tg-bo-title="'Change photo. ' + maxFileSizeMsg") Change + a.button-green.change.js-change-avatar(tg-bo-title="'Change photo. ' + maxFileSizeMsg") Change a.use-gravatar Use gravatar image div.data From c638951368d085cbcbc987c7a536210eb9176b45 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Wed, 11 Mar 2015 13:19:48 +0100 Subject: [PATCH 162/207] Remove gitHubClientId because it's part of a contrib plugin --- app-loader/app-loader.coffee | 1 - conf/conf.example.json | 1 - 2 files changed, 2 deletions(-) diff --git a/app-loader/app-loader.coffee b/app-loader/app-loader.coffee index d17794e9..e216a9f0 100644 --- a/app-loader/app-loader.coffee +++ b/app-loader/app-loader.coffee @@ -8,7 +8,6 @@ window.taigaConfig = { "privacyPolicyUrl": null, "termsOfServiceUrl": null, "maxUploadFileSize": null, - "gitHubClientId": null, "contribPlugins": [] } diff --git a/conf/conf.example.json b/conf/conf.example.json index ec7a8285..f378107e 100644 --- a/conf/conf.example.json +++ b/conf/conf.example.json @@ -7,7 +7,6 @@ "privacyPolicyUrl": null, "termsOfServiceUrl": null, "maxUploadFileSize": null, - "gitHubClientId": null, "contribPlugins": [], "debugInfo": false } From 89e7811f8196a37953f522d6674790c6bb1f3d77 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 11 Mar 2015 11:38:23 +0100 Subject: [PATCH 163/207] BUG#2404 Check permissions for click the username label on kanban and taskboard --- app/coffee/modules/kanban/main.coffee | 20 ++++++++++++-------- app/coffee/modules/taskboard/main.coffee | 16 ++++++++++------ 2 files changed, 22 insertions(+), 14 deletions(-) diff --git a/app/coffee/modules/kanban/main.coffee b/app/coffee/modules/kanban/main.coffee index 7b559a58..2beef957 100644 --- a/app/coffee/modules/kanban/main.coffee +++ b/app/coffee/modules/kanban/main.coffee @@ -504,6 +504,9 @@ KanbanUserDirective = ($log) -> clickable = false link = ($scope, $el, $attrs, $model) -> + username_label = $el.parent().find("a.task-assigned") + username_label.addClass("not-clickable") + if not $attrs.tgKanbanUserAvatar return $log.error "KanbanUserDirective: no attr is defined" @@ -523,15 +526,7 @@ KanbanUserDirective = ($log) -> html = template(ctx) $el.html(html) - username_label = $el.parent().find("a.task-assigned") username_label.text(ctx.name) - username_label.on "click", (event) -> - if $el.find("a").hasClass("noclick") - return - - us = $model.$modelValue - $ctrl = $el.controller() - $ctrl.changeUsAssignedTo(us) bindOnce $scope, "project", (project) -> if project.my_permissions.indexOf("modify_us") > -1 @@ -544,6 +539,15 @@ KanbanUserDirective = ($log) -> $ctrl = $el.controller() $ctrl.changeUsAssignedTo(us) + username_label.removeClass("not-clickable") + username_label.on "click", (event) -> + if $el.find("a").hasClass("noclick") + return + + us = $model.$modelValue + $ctrl = $el.controller() + $ctrl.changeUsAssignedTo(us) + $scope.$on "$destroy", -> $el.off() diff --git a/app/coffee/modules/taskboard/main.coffee b/app/coffee/modules/taskboard/main.coffee index 2bc15a7d..5499cdec 100644 --- a/app/coffee/modules/taskboard/main.coffee +++ b/app/coffee/modules/taskboard/main.coffee @@ -397,12 +397,7 @@ TaskboardUserDirective = ($log) -> link = ($scope, $el, $attrs) -> username_label = $el.parent().find("a.task-assigned") - username_label.on "click", (event) -> - if $el.find('a').hasClass('noclick') - return - - $ctrl = $el.controller() - $ctrl.editTaskAssignedTo($scope.task) + username_label.addClass("not-clickable") $scope.$watch 'task.assigned_to', (assigned_to) -> user = $scope.usersById[assigned_to] @@ -425,6 +420,15 @@ TaskboardUserDirective = ($log) -> $ctrl = $el.controller() $ctrl.editTaskAssignedTo($scope.task) + username_label.removeClass("not-clickable") + username_label.on "click", (event) -> + if $el.find('a').hasClass('noclick') + return + + $ctrl = $el.controller() + $ctrl.editTaskAssignedTo($scope.task) + + return { link: link, templateUrl: "taskboard/taskboard-user.html", From 4c89984dfaf84b893a26c596cf3a3d40d6ac815c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Wed, 11 Mar 2015 14:15:50 +0100 Subject: [PATCH 164/207] Fix bug #2392: Accept invitations with auth plugins --- app/partials/includes/modules/invitation-login-form.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/includes/modules/invitation-login-form.jade b/app/partials/includes/modules/invitation-login-form.jade index f298fa5a..ebdd4bbc 100644 --- a/app/partials/includes/modules/invitation-login-form.jade +++ b/app/partials/includes/modules/invitation-login-form.jade @@ -10,4 +10,4 @@ form.login-form fieldset button.button-login.button-gray.submit-button(type="submit", title="Enter") Enter - fieldset(tg-github-login-button) + fieldset(ng-repeat="plugin in contribPlugins|filter:{type: 'auth'}", ng-include="plugin.template") From 8ccf004d12f0a304dbb935af444d37f53c93f5a1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 11 Mar 2015 12:38:11 +0100 Subject: [PATCH 165/207] Bug#2403 Force to only show edit template if the custom-field is editable by the user --- app/coffee/modules/common/custom-field-values.coffee | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/common/custom-field-values.coffee b/app/coffee/modules/common/custom-field-values.coffee index dd3e661b..c827afb8 100644 --- a/app/coffee/modules/common/custom-field-values.coffee +++ b/app/coffee/modules/common/custom-field-values.coffee @@ -128,15 +128,16 @@ CustomAttributeValueDirective = ($template, $selectedText) -> link = ($scope, $el, $attrs, $ctrl) -> render = (attributeValue, edit=false) -> value = attributeValue.value + editable = isEditable() ctx = { id: attributeValue.id name: attributeValue.name description: attributeValue.description value: value - isEditable: isEditable() + isEditable: editable } - if edit or not value + if editable and (edit or not value) html = templateEdit(ctx) else html = template(ctx) From 3108df45530f4d52b9ef7a70f0865f79b62226dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 11 Mar 2015 12:28:45 +0100 Subject: [PATCH 166/207] Bug#2409 CSV regenerate popup only showed when you are overwriting the previous url --- .../modules/admin/project-values.coffee | 29 +++++++++++-------- 1 file changed, 17 insertions(+), 12 deletions(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 9ab4d917..09b23d58 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -647,20 +647,25 @@ class CsvExporterController extends taiga.Controller setCsvUuid: => @scope.csvUuid = @scope.project["#{@.type}_csv_uuid"] + _generateUuid: (finish) => + promise = @rs.projects["regenerate_#{@.type}_csv_uuid"](@scope.projectId) + + promise.then (data) => + @scope.csvUuid = data.data?.uuid + + promise.then null, => + @confirm.notify("error") + + promise.finally -> + finish() + return promise + regenerateUuid: -> #TODO: i18n - @confirm.ask("Change URL", "You going to change the CSV data access url. The previous url will be disabled. Are you sure?").then (finish) => - promise = @rs.projects["regenerate_#{@.type}_csv_uuid"](@scope.projectId) - - promise.then (data) => - @scope.csvUuid = data.data?.uuid - - promise.then null, => - @confirm.notify("error") - - promise.finally -> - finish() - return promise + if @scope.csvUuid + @confirm.ask("Change URL", "You going to change the CSV data access url. The previous url will be disabled. Are you sure?").then @._generateUuid + else + @._generateUuid(_.identity) class CsvExporterUserstoriesController extends CsvExporterController type: "userstories" From 3fc6dcf4ca535974f72606c5bf2b2b8d3d6aca38 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 11 Mar 2015 16:46:12 +0100 Subject: [PATCH 167/207] Bug#2402 Add resolveAbsolute method and used in csv export url building --- app/coffee/modules/admin/project-values.coffee | 2 +- app/coffee/modules/base/urls.coffee | 8 ++++++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 09b23d58..0a1bcd99 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -640,7 +640,7 @@ class CsvExporterController extends taiga.Controller @rootscope.$on("project:loaded", @.setCsvUuid) @scope.$watch "csvUuid", (value) => if value - @scope.csvUrl = @urls.resolve("#{@.type}-csv", value) + @scope.csvUrl = @urls.resolveAbsolute("#{@.type}-csv", value) else @scope.csvUrl = "" diff --git a/app/coffee/modules/base/urls.coffee b/app/coffee/modules/base/urls.coffee index c542476a..46339b68 100644 --- a/app/coffee/modules/base/urls.coffee +++ b/app/coffee/modules/base/urls.coffee @@ -49,6 +49,14 @@ class UrlsService extends taiga.Service _.str.ltrim(url, "/") ]) + resolveAbsolute: -> + url = @.resolve.apply(@, arguments) + if (/^https?:\/\//i).test(url) + return url + if (/^\//).test(url) + return "#{window.location.protocol}//#{window.location.host}#{url}" + return "#{window.location.protocol}//#{window.location.host}/#{url}" + module = angular.module("taigaBase") module.service('$tgUrls', UrlsService) From cb0f3b6564c65e69fb804f2678210d708463cbc7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Wed, 11 Mar 2015 17:10:14 +0100 Subject: [PATCH 168/207] Bug#2390 Only list my projects on home page and projects menu --- app/coffee/modules/nav.coffee | 2 +- app/coffee/modules/projects/main.coffee | 2 +- app/coffee/modules/resources/projects.coffee | 4 ++++ 3 files changed, 6 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/nav.coffee b/app/coffee/modules/nav.coffee index ffe765c6..e42b0069 100644 --- a/app/coffee/modules/nav.coffee +++ b/app/coffee/modules/nav.coffee @@ -49,7 +49,7 @@ class ProjectsNavigationController extends taiga.Controller @.loadInitialData() loadInitialData: -> - return @rs.projects.list().then (projects) => + return @rs.projects.listByMember(@rootscope.user.id).then (projects) => for project in projects project.url = @projectUrl.get(project) @scope.projects = projects diff --git a/app/coffee/modules/projects/main.coffee b/app/coffee/modules/projects/main.coffee index 97d68d77..3fda7aef 100644 --- a/app/coffee/modules/projects/main.coffee +++ b/app/coffee/modules/projects/main.coffee @@ -58,7 +58,7 @@ class ProjectsController extends taiga.Controller promise.finally tgLoader.pageLoaded loadInitialData: -> - return @rs.projects.list().then (projects) => + return @rs.projects.listByMember(@rootscope.user.id).then (projects) => @.projects = {'recents': projects.slice(0, 8), 'all': projects} for project in projects project.url = @projectUrl.get(project) diff --git a/app/coffee/modules/resources/projects.coffee b/app/coffee/modules/resources/projects.coffee index 877b4763..88393f48 100644 --- a/app/coffee/modules/resources/projects.coffee +++ b/app/coffee/modules/resources/projects.coffee @@ -36,6 +36,10 @@ resourceProvider = ($config, $repo, $http, $urls, $auth, $q, $rootScope) -> service.list = -> return $repo.queryMany("projects") + service.listByMember = (memberId) -> + params = {"member": memberId} + return $repo.queryMany("projects", params) + service.templates = -> return $repo.queryMany("project-templates") From bfde3193fe1f3b1f01dd7ff435cf45304bdce489 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Wed, 11 Mar 2015 12:45:39 +0100 Subject: [PATCH 169/207] fix markitup image generation --- gulpfile.js | 17 +++++++---------- 1 file changed, 7 insertions(+), 10 deletions(-) diff --git a/gulpfile.js b/gulpfile.js index 0d9ae11c..dbef97e0 100644 --- a/gulpfile.js +++ b/gulpfile.js @@ -1,4 +1,5 @@ var gulp = require("gulp"), + imagemin = require("gulp-imagemin"), jade = require("gulp-jade"), coffee = require("gulp-coffee"), concat = require("gulp-concat"), @@ -337,16 +338,12 @@ gulp.task("copy-fonts", function() { }); gulp.task("copy-images", function() { - var imageMin = gulp.src(paths.app + "/images/**/*"); - - if (isDeploy) { - //require imagemin is very slow - var imagemin = require("gulp-imagemin"); - imageMin.pipe(imagemin({progressive: true})) - } - - imageMin.pipe(gulp.dest(paths.dist + "/images/")) + return gulp.src(paths.app + "/images/**/*") + .pipe(imagemin({progressive: true})) + .pipe(gulp.dest(paths.dist + "/images/")); +}); +gulp.task("copy-images-plugins", function() { return gulp.src(paths.app + "/plugins/**/images/*") .pipe(flatten()) .pipe(gulp.dest(paths.dist + "/images/")); @@ -362,7 +359,7 @@ gulp.task("copy-extras", function() { .pipe(gulp.dest(paths.dist + "/")); }); -gulp.task("copy", ["copy-fonts", "copy-images", "copy-plugin-templates", "copy-svg", "copy-extras"]); +gulp.task("copy", ["copy-fonts", "copy-images", "copy-images-plugins", "copy-plugin-templates", "copy-svg", "copy-extras"]); gulp.task("express", function() { var express = require("express"); From 736eea00d01aa40f16f7e51a1b159d67d5111bba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Thu, 12 Mar 2015 08:47:59 +0100 Subject: [PATCH 170/207] Fixed problem with not logged users --- app/coffee/modules/nav.coffee | 2 +- app/coffee/modules/projects/main.coffee | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/nav.coffee b/app/coffee/modules/nav.coffee index e42b0069..578890e0 100644 --- a/app/coffee/modules/nav.coffee +++ b/app/coffee/modules/nav.coffee @@ -49,7 +49,7 @@ class ProjectsNavigationController extends taiga.Controller @.loadInitialData() loadInitialData: -> - return @rs.projects.listByMember(@rootscope.user.id).then (projects) => + return @rs.projects.listByMember(@rootscope.user?.id).then (projects) => for project in projects project.url = @projectUrl.get(project) @scope.projects = projects diff --git a/app/coffee/modules/projects/main.coffee b/app/coffee/modules/projects/main.coffee index 3fda7aef..0642ab3b 100644 --- a/app/coffee/modules/projects/main.coffee +++ b/app/coffee/modules/projects/main.coffee @@ -58,7 +58,7 @@ class ProjectsController extends taiga.Controller promise.finally tgLoader.pageLoaded loadInitialData: -> - return @rs.projects.listByMember(@rootscope.user.id).then (projects) => + return @rs.projects.listByMember(@rootscope.user?.id).then (projects) => @.projects = {'recents': projects.slice(0, 8), 'all': projects} for project in projects project.url = @projectUrl.get(project) From 19d84359cb78df2833c48650a2bf032e32c219da Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 12 Mar 2015 10:07:04 +0100 Subject: [PATCH 171/207] fill taskboard scope user with the project users --- app/coffee/modules/taskboard/main.coffee | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/taskboard/main.coffee b/app/coffee/modules/taskboard/main.coffee index 5499cdec..430f770c 100644 --- a/app/coffee/modules/taskboard/main.coffee +++ b/app/coffee/modules/taskboard/main.coffee @@ -116,6 +116,8 @@ class TaskboardController extends mixOf(taiga.Controller, taiga.PageMixin) @scope.$emit('project:loaded', project) + @.fillUsersAndRoles(project.users, project.roles) + return project loadSprintStats: -> @@ -185,7 +187,6 @@ class TaskboardController extends mixOf(taiga.Controller, taiga.PageMixin) return data return promise.then(=> @.loadProject()) - .then(=> @.loadUsersAndRoles()) .then(=> @.loadTaskboard()) refreshTasksOrder: (tasks) -> From 5a8d203f7581f0169ad332a3f597cd926f85d4dd Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Thu, 12 Mar 2015 11:24:34 +0100 Subject: [PATCH 172/207] Redirecting the user when trying to access to a section not enabled --- app/coffee/modules/admin/memberships.coffee | 3 +++ app/coffee/modules/admin/project-profile.coffee | 3 +++ app/coffee/modules/admin/project-values.coffee | 3 +++ app/coffee/modules/admin/roles.coffee | 3 +++ app/coffee/modules/admin/third-parties.coffee | 7 ++++++- app/coffee/modules/backlog/main.coffee | 3 +++ app/coffee/modules/issues/list.coffee | 3 +++ app/coffee/modules/kanban/main.coffee | 3 +++ app/coffee/modules/taskboard/main.coffee | 3 +++ app/coffee/modules/wiki/main.coffee | 3 +++ 10 files changed, 33 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/admin/memberships.coffee b/app/coffee/modules/admin/memberships.coffee index 14d481d6..574e38de 100644 --- a/app/coffee/modules/admin/memberships.coffee +++ b/app/coffee/modules/admin/memberships.coffee @@ -67,6 +67,9 @@ class MembershipsController extends mixOf(taiga.Controller, taiga.PageMixin, tai loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => + if not project.i_am_owner + @location.path(@navUrls.resolve("permission-denied")) + @scope.project = project @scope.$emit('project:loaded', project) return project diff --git a/app/coffee/modules/admin/project-profile.coffee b/app/coffee/modules/admin/project-profile.coffee index a8da32e6..03f4415b 100644 --- a/app/coffee/modules/admin/project-profile.coffee +++ b/app/coffee/modules/admin/project-profile.coffee @@ -65,6 +65,9 @@ class ProjectProfileController extends mixOf(taiga.Controller, taiga.PageMixin) loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => + if not project.i_am_owner + @location.path(@navUrls.resolve("permission-denied")) + @scope.project = project @scope.pointsList = _.sortBy(project.points, "order") @scope.usStatusList = _.sortBy(project.us_statuses, "order") diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 0a1bcd99..87f0de3b 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -61,6 +61,9 @@ class ProjectValuesSectionController extends mixOf(taiga.Controller, taiga.PageM loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => + if not project.i_am_owner + @location.path(@navUrls.resolve("permission-denied")) + @scope.project = project @scope.$emit('project:loaded', project) return project diff --git a/app/coffee/modules/admin/roles.coffee b/app/coffee/modules/admin/roles.coffee index cbd45d1a..ff47fca8 100644 --- a/app/coffee/modules/admin/roles.coffee +++ b/app/coffee/modules/admin/roles.coffee @@ -63,6 +63,9 @@ class RolesController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fil loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => + if not project.i_am_owner + @location.path(@navUrls.resolve("permission-denied")) + @scope.project = project @scope.$emit('project:loaded', project) diff --git a/app/coffee/modules/admin/third-parties.coffee b/app/coffee/modules/admin/third-parties.coffee index a78fdc1d..5ba18666 100644 --- a/app/coffee/modules/admin/third-parties.coffee +++ b/app/coffee/modules/admin/third-parties.coffee @@ -38,10 +38,12 @@ class WebhooksController extends mixOf(taiga.Controller, taiga.PageMixin, taiga. "$tgRepo", "$tgResources", "$routeParams", + "$tgLocation", + "$tgNavUrls", "$appTitle" ] - constructor: (@scope, @repo, @rs, @params, @appTitle) -> + constructor: (@scope, @repo, @rs, @params, @location, @navUrls, @appTitle) -> bindMethods(@) @scope.sectionName = "Webhooks" #i18n @@ -62,6 +64,9 @@ class WebhooksController extends mixOf(taiga.Controller, taiga.PageMixin, taiga. loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => + if not project.i_am_owner + @location.path(@navUrls.resolve("permission-denied")) + @scope.project = project @scope.$emit('project:loaded', project) return project diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index 518042f2..d2333baa 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -225,6 +225,9 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F loadProject: -> return @rs.projects.getBySlug(@params.pslug).then (project) => + if not project.is_backlog_activated + @location.path(@navUrls.resolve("permission-denied")) + @scope.projectId = project.id @scope.project = project @scope.totalClosedMilestones = project.total_closed_milestones diff --git a/app/coffee/modules/issues/list.coffee b/app/coffee/modules/issues/list.coffee index f29c0848..7d2e1234 100644 --- a/app/coffee/modules/issues/list.coffee +++ b/app/coffee/modules/issues/list.coffee @@ -94,6 +94,9 @@ class IssuesController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fi loadProject: -> return @rs.projects.getBySlug(@params.pslug).then (project) => + if not project.is_issues_activated + @location.path(@navUrls.resolve("permission-denied")) + @scope.projectId = project.id @scope.project = project @scope.$emit('project:loaded', project) diff --git a/app/coffee/modules/kanban/main.coffee b/app/coffee/modules/kanban/main.coffee index 2beef957..b56a46a7 100644 --- a/app/coffee/modules/kanban/main.coffee +++ b/app/coffee/modules/kanban/main.coffee @@ -183,6 +183,9 @@ class KanbanController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.Fi loadProject: -> return @rs.projects.getBySlug(@params.pslug).then (project) => + if not project.is_kanban_activated + @location.path(@navUrls.resolve("permission-denied")) + @scope.projectId = project.id @scope.project = project @scope.projectId = project.id diff --git a/app/coffee/modules/taskboard/main.coffee b/app/coffee/modules/taskboard/main.coffee index 430f770c..8a922148 100644 --- a/app/coffee/modules/taskboard/main.coffee +++ b/app/coffee/modules/taskboard/main.coffee @@ -104,6 +104,9 @@ class TaskboardController extends mixOf(taiga.Controller, taiga.PageMixin) loadProject: -> return @rs.projects.get(@scope.projectId).then (project) => + if not project.is_backlog_activated + @location.path(@navUrls.resolve("permission-denied")) + @scope.project = project # Not used at this momment @scope.pointsList = _.sortBy(project.points, "order") diff --git a/app/coffee/modules/wiki/main.coffee b/app/coffee/modules/wiki/main.coffee index 8aad38e7..9596212b 100644 --- a/app/coffee/modules/wiki/main.coffee +++ b/app/coffee/modules/wiki/main.coffee @@ -70,6 +70,9 @@ class WikiDetailController extends mixOf(taiga.Controller, taiga.PageMixin) loadProject: -> return @rs.projects.getBySlug(@params.pslug).then (project) => + if not project.is_wiki_activated + @location.path(@navUrls.resolve("permission-denied")) + @scope.projectId = project.id @scope.project = project @scope.$emit('project:loaded', project) From 646137c0c68a0b08ecaa8ecf38f25b0ebe04dea2 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 12 Mar 2015 12:00:24 +0100 Subject: [PATCH 173/207] bind estimationProcess to a dom element --- app/coffee/modules/common/estimation.coffee | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/common/estimation.coffee b/app/coffee/modules/common/estimation.coffee index f8666078..3ca34f5f 100644 --- a/app/coffee/modules/common/estimation.coffee +++ b/app/coffee/modules/common/estimation.coffee @@ -224,7 +224,12 @@ EstimationsService = ($template, $qqueue, $repo, $confirm, $q) -> @$el.find(".pop-points-open").show() create = ($el, us, project) -> - estimationProcess = new EstimationProcess($el, us, project) + estimationProcess = $el.data("estimationProcess") + + if !estimationProcess + estimationProcess = new EstimationProcess($el, us, project) + $el.data("estimationProcess", estimationProcess) + if estimationProcess.isEditable estimationProcess.bindClickEvents() else From 545513a96cc60fef1274403de210caec210cdc9b Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Wed, 11 Mar 2015 12:00:14 +0100 Subject: [PATCH 174/207] Refactoring menu structure --- app/coffee/app.coffee | 22 +++++++--- app/coffee/modules/base.coffee | 12 ++++-- app/partials/admin/admin-project-reports.jade | 27 ++++++++++++ .../admin-project-values-custom-fields.jade | 31 ++++++++++++++ .../admin/admin-project-values-issue.jade | 41 ------------------- .../admin/admin-project-values-points.jade | 15 +++++++ .../admin-project-values-priorities.jade | 15 +++++++ .../admin-project-values-severities.jade | 15 +++++++ .../admin/admin-project-values-status.jade | 25 +++++++++++ .../admin/admin-project-values-task.jade | 26 ------------ .../admin/admin-project-values-types.jade | 15 +++++++ .../admin/admin-project-values-us.jade | 31 -------------- app/partials/includes/modules/admin-menu.jade | 2 +- .../admin-submenu-project-profile.jade | 4 ++ .../modules/admin-submenu-project-values.jade | 33 +++++++++++---- .../admin/admin-custom-attributes.jade | 2 +- .../modules/admin/project-points.jade | 2 +- .../modules/admin/project-status.jade | 2 +- .../modules/admin/project-us-status.jade | 2 +- 19 files changed, 201 insertions(+), 121 deletions(-) create mode 100644 app/partials/admin/admin-project-reports.jade create mode 100644 app/partials/admin/admin-project-values-custom-fields.jade delete mode 100644 app/partials/admin/admin-project-values-issue.jade create mode 100644 app/partials/admin/admin-project-values-points.jade create mode 100644 app/partials/admin/admin-project-values-priorities.jade create mode 100644 app/partials/admin/admin-project-values-severities.jade create mode 100644 app/partials/admin/admin-project-values-status.jade delete mode 100644 app/partials/admin/admin-project-values-task.jade create mode 100644 app/partials/admin/admin-project-values-types.jade delete mode 100644 app/partials/admin/admin-project-values-us.jade diff --git a/app/coffee/app.coffee b/app/coffee/app.coffee index 2e6311fc..0f099adc 100644 --- a/app/coffee/app.coffee +++ b/app/coffee/app.coffee @@ -89,12 +89,22 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven {templateUrl: "admin/admin-project-modules.html"}) $routeProvider.when("/project/:pslug/admin/project-profile/export", {templateUrl: "admin/admin-project-export.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/us", - {templateUrl: "admin/admin-project-values-us.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/task", - {templateUrl: "admin/admin-project-values-task.html"}) - $routeProvider.when("/project/:pslug/admin/project-values/issue", - {templateUrl: "admin/admin-project-values-issue.html"}) + $routeProvider.when("/project/:pslug/admin/project-profile/reports", + {templateUrl: "admin/admin-project-reports.html"}) + + $routeProvider.when("/project/:pslug/admin/project-values/status", + {templateUrl: "admin/admin-project-values-status.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/points", + {templateUrl: "admin/admin-project-values-points.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/priorities", + {templateUrl: "admin/admin-project-values-priorities.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/severities", + {templateUrl: "admin/admin-project-values-severities.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/types", + {templateUrl: "admin/admin-project-values-types.html"}) + $routeProvider.when("/project/:pslug/admin/project-values/custom-fields", + {templateUrl: "admin/admin-project-values-custom-fields.html"}) + $routeProvider.when("/project/:pslug/admin/memberships", {templateUrl: "admin/admin-memberships.html"}) # Admin - Roles diff --git a/app/coffee/modules/base.coffee b/app/coffee/modules/base.coffee index 5f324796..8c762e77 100644 --- a/app/coffee/modules/base.coffee +++ b/app/coffee/modules/base.coffee @@ -84,9 +84,15 @@ urls = { "project-admin-project-profile-default-values": "/project/:project/admin/project-profile/default-values" "project-admin-project-profile-modules": "/project/:project/admin/project-profile/modules" "project-admin-project-profile-export": "/project/:project/admin/project-profile/export" - "project-admin-project-values-us": "/project/:project/admin/project-values/us" - "project-admin-project-values-task": "/project/:project/admin/project-values/task" - "project-admin-project-values-issue": "/project/:project/admin/project-values/issue" + "project-admin-project-profile-reports": "/project/:project/admin/project-profile/reports" + + "project-admin-project-values-status": "/project/:project/admin/project-values/status" + "project-admin-project-values-points": "/project/:project/admin/project-values/points" + "project-admin-project-values-priorities": "/project/:project/admin/project-values/priorities" + "project-admin-project-values-severities": "/project/:project/admin/project-values/severities" + "project-admin-project-values-types": "/project/:project/admin/project-values/types" + "project-admin-project-values-custom-fields": "/project/:project/admin/project-values/custom-fields" + "project-admin-memberships": "/project/:project/admin/memberships" "project-admin-roles": "/project/:project/admin/roles" "project-admin-third-parties-webhooks": "/project/:project/admin/third-parties/webhooks" diff --git a/app/partials/admin/admin-project-reports.jade b/app/partials/admin/admin-project-reports.jade new file mode 100644 index 00000000..09d45a54 --- /dev/null +++ b/app/partials/admin/admin-project-reports.jade @@ -0,0 +1,27 @@ +div.wrapper(ng-controller="ProjectProfileController as ctrl", + ng-init="section='admin'; sectionName='Export'") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-profile") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="reports") + include ../includes/modules/admin-submenu-project-profile + + section.main.admin-common(tg-project-export) + header + include ../includes/components/mainTitle + p.admin-subtitle Export your project data in CSV format. + + - var csvType = "US"; + - var controller = "CsvExporterUserstoriesController"; + div.admin-attributes-section + include ../includes/modules/admin/project-csv + + - var csvType = "Task"; + - var controller = "CsvExporterTasksController"; + div.admin-attributes-section + include ../includes/modules/admin/project-csv + + - var csvType = "Issues"; + - var controller = "CsvExporterIssuesController"; + div.admin-attributes-section + include ../includes/modules/admin/project-csv diff --git a/app/partials/admin/admin-project-values-custom-fields.jade b/app/partials/admin/admin-project-values-custom-fields.jade new file mode 100644 index 00000000..ddc03dfc --- /dev/null +++ b/app/partials/admin/admin-project-values-custom-fields.jade @@ -0,0 +1,31 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-custom-fields") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the custom fields for your user stories, tasks and issues + + div.admin-attributes-section(tg-project-custom-attributes, + ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="type='userstory';") + - var customFieldSectionTitle = "User stories custom fields" + - var customFieldButtonTitle = "Add a custom field in user stories" + include ../includes/modules/admin/admin-custom-attributes + + div.admin-attributes-section(tg-project-custom-attributes, + ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="type='task';") + - var customFieldSectionTitle = "Tasks custom fields" + - var customFieldButtonTitle = "Add a custom field in tasks" + include ../includes/modules/admin/admin-custom-attributes + + div.admin-attributes-section(tg-project-custom-attributes, + ng-controller="ProjectCustomAttributesController as ctrl", + ng-init="type='issue';") + - var customFieldSectionTitle = "Issues custom fields" + - var customFieldButtonTitle = "Add a custom field in issues" + include ../includes/modules/admin/admin-custom-attributes diff --git a/app/partials/admin/admin-project-values-issue.jade b/app/partials/admin/admin-project-values-issue.jade deleted file mode 100644 index 4b414726..00000000 --- a/app/partials/admin/admin-project-values-issue.jade +++ /dev/null @@ -1,41 +0,0 @@ -div.wrapper(ng-controller="ProjectValuesSectionController") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-issue") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common.admin-attributes - include ../includes/components/mainTitle - p.admin-subtitle Specify the column headers that you will use to classify Issues - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='issue-statuses'; sectionName='Status'", - type="issue-statuses") - include ../includes/modules/admin/project-status - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='priorities'; sectionName='Priorities'; objName='priority'", - type="priorities") - include ../includes/modules/admin/project-types - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='severities'; sectionName='Severities'; objName='severity'", - type="severities") - include ../includes/modules/admin/project-types - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='issues'; type='issue-types'; sectionName='Types'; objName='type'", - type="issue-types") - include ../includes/modules/admin/project-types - - div.admin-attributes-section(tg-project-custom-attributes, - ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="type='issue';") - - var customFieldButtonTitle = "Add a custom field in tasks" - include ../includes/modules/admin/admin-custom-attributes - - - var csvType = "Issues"; - - var controller = "CsvExporterIssuesController"; - div.admin-attributes-section - include ../includes/modules/admin/project-csv diff --git a/app/partials/admin/admin-project-values-points.jade b/app/partials/admin/admin-project-values-points.jade new file mode 100644 index 00000000..64ef3fb1 --- /dev/null +++ b/app/partials/admin/admin-project-values-points.jade @@ -0,0 +1,15 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-points") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the points your user stories could be estimated to + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='userstories'; type='points'; sectionName='Us points'", + type="points") + include ../includes/modules/admin/project-points diff --git a/app/partials/admin/admin-project-values-priorities.jade b/app/partials/admin/admin-project-values-priorities.jade new file mode 100644 index 00000000..4e0c5098 --- /dev/null +++ b/app/partials/admin/admin-project-values-priorities.jade @@ -0,0 +1,15 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-priorities") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the priorities your issues will have + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='priorities'; sectionName='Issue priorities'; objName='priority'", + type="priorities") + include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-severities.jade b/app/partials/admin/admin-project-values-severities.jade new file mode 100644 index 00000000..507ff930 --- /dev/null +++ b/app/partials/admin/admin-project-values-severities.jade @@ -0,0 +1,15 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-severities") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the severities your issues will have + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='severities'; sectionName='Issue severities'; objName='severity'", + type="severities") + include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-status.jade b/app/partials/admin/admin-project-values-status.jade new file mode 100644 index 00000000..5f6e8876 --- /dev/null +++ b/app/partials/admin/admin-project-values-status.jade @@ -0,0 +1,25 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-status") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the statuses your user stories, tasks and issues will go through + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='userstories'; type='userstory-statuses'; sectionName='Us Statuses'", + type="userstory-statuses") + include ../includes/modules/admin/project-us-status + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='tasks'; type='task-statuses'; sectionName='Task Statuses'", + type="task-statuses") + include ../includes/modules/admin/project-status + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='issue-statuses'; sectionName='Issue Statuses'", + type="issue-statuses") + include ../includes/modules/admin/project-status diff --git a/app/partials/admin/admin-project-values-task.jade b/app/partials/admin/admin-project-values-task.jade deleted file mode 100644 index 62e1d191..00000000 --- a/app/partials/admin/admin-project-values-task.jade +++ /dev/null @@ -1,26 +0,0 @@ -div.wrapper(ng-controller="ProjectValuesSectionController") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-task") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common.admin-attributes - include ../includes/components/mainTitle - p.admin-subtitle Specify the column headers that you will use to classify Tasks related to each User Stories - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='tasks'; type='task-statuses'; sectionName='Task Statuses'", - type="task-statuses") - include ../includes/modules/admin/project-status - - div.admin-attributes-section(tg-project-custom-attributes, - ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="type='task';") - - var customFieldButtonTitle = "Add a custom field in tasks" - include ../includes/modules/admin/admin-custom-attributes - - - var csvType = "Task"; - - var controller = "CsvExporterTasksController"; - div.admin-attributes-section - include ../includes/modules/admin/project-csv diff --git a/app/partials/admin/admin-project-values-types.jade b/app/partials/admin/admin-project-values-types.jade new file mode 100644 index 00000000..2f033b29 --- /dev/null +++ b/app/partials/admin/admin-project-values-types.jade @@ -0,0 +1,15 @@ +div.wrapper(ng-controller="ProjectValuesSectionController") + sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") + include ../includes/modules/admin-menu + + sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-types") + include ../includes/modules/admin-submenu-project-values + + section.main.admin-common.admin-attributes + include ../includes/components/mainTitle + p.admin-subtitle Specify the types your user stories could be estimated to + + div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", + ng-init="section='admin'; resource='issues'; type='issue-types'; sectionName='Issue types'; objName='type'", + type="issue-types") + include ../includes/modules/admin/project-types diff --git a/app/partials/admin/admin-project-values-us.jade b/app/partials/admin/admin-project-values-us.jade deleted file mode 100644 index 807d53fd..00000000 --- a/app/partials/admin/admin-project-values-us.jade +++ /dev/null @@ -1,31 +0,0 @@ -div.wrapper(ng-controller="ProjectValuesSectionController") - sidebar.menu-secondary.sidebar(tg-admin-navigation="project-values") - include ../includes/modules/admin-menu - - sidebar.menu-tertiary.sidebar(tg-admin-navigation="values-us") - include ../includes/modules/admin-submenu-project-values - - section.main.admin-common.admin-attributes - include ../includes/components/mainTitle - p.admin-subtitle Specify the column headers that you will use to classify User Stories - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='userstories'; type='userstory-statuses'; sectionName='Us Statuses'", - type="userstory-statuses") - include ../includes/modules/admin/project-us-status - - div.admin-attributes-section(tg-project-values, ng-controller="ProjectValuesController as ctrl", - ng-init="section='admin'; resource='userstories'; type='points'; sectionName='Us points'", - type="points") - include ../includes/modules/admin/project-points - - div.admin-attributes-section(tg-project-custom-attributes, - ng-controller="ProjectCustomAttributesController as ctrl", - ng-init="type='userstory';") - - var customFieldButtonTitle = "Add a custom field in tasks" - include ../includes/modules/admin/admin-custom-attributes - - - var csvType = "US"; - - var controller = "CsvExporterUserstoriesController"; - div.admin-attributes-section - include ../includes/modules/admin/project-csv diff --git a/app/partials/includes/modules/admin-menu.jade b/app/partials/includes/modules/admin-menu.jade index 858ec8a8..0a4cb08e 100644 --- a/app/partials/includes/modules/admin-menu.jade +++ b/app/partials/includes/modules/admin-menu.jade @@ -9,7 +9,7 @@ section.admin-menu span.title Project span.icon.icon-arrow-right li#adminmenu-project-values - a(href="", tg-nav="project-admin-project-values-us:project=project.slug") + a(href="", tg-nav="project-admin-project-values-status:project=project.slug") span.title Attributes span.icon.icon-arrow-right li#adminmenu-memberships diff --git a/app/partials/includes/modules/admin-submenu-project-profile.jade b/app/partials/includes/modules/admin-submenu-project-profile.jade index e9522a86..30be41da 100644 --- a/app/partials/includes/modules/admin-submenu-project-profile.jade +++ b/app/partials/includes/modules/admin-submenu-project-profile.jade @@ -20,3 +20,7 @@ section.admin-submenu a(href="", tg-nav="project-admin-project-profile-export:project=project.slug") span.title Export span.icon.icon-arrow-right + li#adminmenu-reports + a(href="", tg-nav="project-admin-project-profile-reports:project=project.slug") + span.title Reports + span.icon.icon-arrow-right diff --git a/app/partials/includes/modules/admin-submenu-project-values.jade b/app/partials/includes/modules/admin-submenu-project-values.jade index 1370e797..57df5300 100644 --- a/app/partials/includes/modules/admin-submenu-project-values.jade +++ b/app/partials/includes/modules/admin-submenu-project-values.jade @@ -4,17 +4,32 @@ section.admin-submenu nav ul - li#adminmenu-values-us - a(href="", tg-nav="project-admin-project-values-us:project=project.slug") - span.title US + li#adminmenu-values-status + a(href="", tg-nav="project-admin-project-values-status:project=project.slug") + span.title Status span.icon.icon-arrow-right - li#adminmenu-values-task - a(href="", tg-nav="project-admin-project-values-task:project=project.slug") - span.title Task + li#adminmenu-values-points + a(href="", tg-nav="project-admin-project-values-points:project=project.slug") + span.title Points span.icon.icon-arrow-right - li#adminmenu-values-issue - a(href="", tg-nav="project-admin-project-values-issue:project=project.slug") - span.title Issue + li#adminmenu-values-priorities + a(href="", tg-nav="project-admin-project-values-priorities:project=project.slug") + span.title Priorities + span.icon.icon-arrow-right + + li#adminmenu-values-severities + a(href="", tg-nav="project-admin-project-values-severities:project=project.slug") + span.title Severities + span.icon.icon-arrow-right + + li#adminmenu-values-types + a(href="", tg-nav="project-admin-project-values-types:project=project.slug") + span.title Types + span.icon.icon-arrow-right + + li#adminmenu-values-custom-fields + a(href="", tg-nav="project-admin-project-values-custom-fields:project=project.slug") + span.title Custom fields span.icon.icon-arrow-right diff --git a/app/partials/includes/modules/admin/admin-custom-attributes.jade b/app/partials/includes/modules/admin/admin-custom-attributes.jade index 4b550b9b..09186600 100644 --- a/app/partials/includes/modules/admin/admin-custom-attributes.jade +++ b/app/partials/includes/modules/admin/admin-custom-attributes.jade @@ -1,6 +1,6 @@ section.custom-fields-table.basic-table div.project-values-title - h2 Custom fields + h2 #{customFieldSectionTitle} a.button.button-gray.show-add-new.js-add-custom-field-button(href="", title="#{customFieldButtonTitle}") span Add custom field diff --git a/app/partials/includes/modules/admin/project-points.jade b/app/partials/includes/modules/admin/project-points.jade index e23b531b..70ecb29c 100644 --- a/app/partials/includes/modules/admin/project-points.jade +++ b/app/partials/includes/modules/admin/project-points.jade @@ -1,7 +1,7 @@ section.project-values-table div.project-values-title - h2 Points + h2(ng-bind="sectionName") a.button.button-gray.show-add-new(href="", title="Add New") span Add new point diff --git a/app/partials/includes/modules/admin/project-status.jade b/app/partials/includes/modules/admin/project-status.jade index ba9c2117..4e90d97d 100644 --- a/app/partials/includes/modules/admin/project-status.jade +++ b/app/partials/includes/modules/admin/project-status.jade @@ -1,6 +1,6 @@ section.colors-table.admin-status-table div.project-values-title - h2 Status + h2(ng-bind="sectionName") a.button.button-gray.show-add-new(href="", title="Add New") span Add new status diff --git a/app/partials/includes/modules/admin/project-us-status.jade b/app/partials/includes/modules/admin/project-us-status.jade index a0954c6b..f9f2a8ba 100644 --- a/app/partials/includes/modules/admin/project-us-status.jade +++ b/app/partials/includes/modules/admin/project-us-status.jade @@ -1,7 +1,7 @@ section.project-us-status div.project-values-title - h2 Status + h2(ng-bind="sectionName") a.button.button-gray.show-add-new(href="", title="Add New") span Add new status From 07e12e27b0c538daa41a6b1a8ddfedb9dfb00f93 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 08:50:37 +0100 Subject: [PATCH 175/207] Style refactor for admin reorganization --- app/styles/layout/admin-project-values.scss | 2 +- .../admin/admin-custom-attributes.scss | 12 ++++-- app/styles/modules/admin/project-values.scss | 9 +++- app/styles/modules/common/colors-table.scss | 43 +++++++++++-------- 4 files changed, 43 insertions(+), 23 deletions(-) diff --git a/app/styles/layout/admin-project-values.scss b/app/styles/layout/admin-project-values.scss index a7b44b10..749d7178 100644 --- a/app/styles/layout/admin-project-values.scss +++ b/app/styles/layout/admin-project-values.scss @@ -24,7 +24,7 @@ background: $whitish; display: flex; justify-content: space-between; - padding: .5rem 1rem; + padding: .8em 1rem; text-transform: uppercase; h2 { margin: 0; diff --git a/app/styles/modules/admin/admin-custom-attributes.scss b/app/styles/modules/admin/admin-custom-attributes.scss index d110cf23..a6ba34fa 100644 --- a/app/styles/modules/admin/admin-custom-attributes.scss +++ b/app/styles/modules/admin/admin-custom-attributes.scss @@ -4,26 +4,31 @@ } .custom-fields-table { + margin-bottom: 2em; .row { border-bottom: 0; padding: .5rem 0; - } .table-header { @extend %bold; - border-bottom: 1px solid $gray-light; + border-bottom: 3px solid $whitish; .custom-name span, .custom-description span { padding-left: 1.1rem; } } .table-body { + form:last-child { + .row { + border: 0; + } + } .row:hover { background: rgba($fresh-taiga, .05); cursor: move; transition: background .2s linear; .icon-drag-v, - .custom-options-wrapper { + .custom-options { opacity: 1; transition: opacity .2s linear; } @@ -72,6 +77,7 @@ flex-basis: 100px; flex-grow: 0; flex-shrink: 0; + opacity: 0; text-align: center; a { color: $gray-light; diff --git a/app/styles/modules/admin/project-values.scss b/app/styles/modules/admin/project-values.scss index 9f96b6ee..e8920a8f 100644 --- a/app/styles/modules/admin/project-values.scss +++ b/app/styles/modules/admin/project-values.scss @@ -21,9 +21,16 @@ .project-values-header { @extend %bold; - border-bottom: 2px solid $gray-light; + border-bottom: 3px solid $whitish; } .project-values-body { + form { + &:last-child { + .project-values-row { + border: 0; + } + } + } .project-values-row { &:hover { background: lighten($green-taiga, 60%); diff --git a/app/styles/modules/common/colors-table.scss b/app/styles/modules/common/colors-table.scss index 1da52861..f84a0d6e 100644 --- a/app/styles/modules/common/colors-table.scss +++ b/app/styles/modules/common/colors-table.scss @@ -2,7 +2,7 @@ .table-header { @extend %medium; @extend %bold; - border-bottom: 2px solid $gray-light; + border-bottom: 3px solid $whitish; &:hover { background: transparent; } @@ -10,17 +10,40 @@ padding-left: 50px; } } + form { + &:last-child { + .row { + border: 0; + } + } + } .row { align-items: center; + border-bottom: 1px solid $whitish; display: flex; justify-content: center; padding: 1rem; &:hover { + background: lighten($green-taiga, 60%); + cursor: move; + transition: background .2s ease-in; + .icon { + opacity: 1; + transition: opacity .2s ease-in; + } .options-column { opacity: 1; transition: opacity .3s linear; } } + &:last-child { + border: 0; + } + &.edition { + .current-color { + cursor: pointer; + } + } &.edition, &.new-value { padding-left: 50px; @@ -28,11 +51,6 @@ &.hidden { display: none; } - &.edition { - .current-color { - cursor: pointer; - } - } .color-column { flex-basis: 60px; flex-grow: 1; @@ -86,18 +104,7 @@ opacity: 1; } } - .table-main { - border-bottom: 1px solid $whitish; - .row:hover { - background: lighten($green-taiga, 60%); - cursor: move; - transition: background .2s ease-in; - .icon { - opacity: 1; - transition: opacity .2s ease-in; - } - } - } + .current-color { background-color: $gray-light; border-radius: 2px; From 361299119260c69fab93f6155d45edf991171aa1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 10:07:57 +0100 Subject: [PATCH 176/207] Reports page styles --- app/partials/admin/admin-project-reports.jade | 7 +++++-- .../includes/modules/admin/project-csv.jade | 14 ++++++-------- app/styles/modules/admin/project-csv.scss | 4 +++- 3 files changed, 14 insertions(+), 11 deletions(-) diff --git a/app/partials/admin/admin-project-reports.jade b/app/partials/admin/admin-project-reports.jade index 09d45a54..3bf447e8 100644 --- a/app/partials/admin/admin-project-reports.jade +++ b/app/partials/admin/admin-project-reports.jade @@ -1,5 +1,5 @@ div.wrapper(ng-controller="ProjectProfileController as ctrl", - ng-init="section='admin'; sectionName='Export'") + ng-init="section='admin'; sectionName='Reports'") sidebar.menu-secondary.sidebar(tg-admin-navigation="project-profile") include ../includes/modules/admin-menu @@ -9,7 +9,7 @@ div.wrapper(ng-controller="ProjectProfileController as ctrl", section.main.admin-common(tg-project-export) header include ../includes/components/mainTitle - p.admin-subtitle Export your project data in CSV format. + p.admin-subtitle Export your project data in CSV format and make your own reports - var csvType = "US"; - var controller = "CsvExporterUserstoriesController"; @@ -25,3 +25,6 @@ div.wrapper(ng-controller="ProjectProfileController as ctrl", - var controller = "CsvExporterIssuesController"; div.admin-attributes-section include ../includes/modules/admin/project-csv + a.help-button(href="https://taiga.io/support/csv-reports/", target="_blank") + span.icon.icon-help + span How to use this on my own spreadsheet? diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade index 16948073..57b644c5 100644 --- a/app/partials/includes/modules/admin/project-csv.jade +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -1,20 +1,18 @@ section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text) div.project-values-title - h2 Export #{csvType} Data - span (.csv format) + h2 #{csvType} reports a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}", ng-show="csvUrl") span Download CSV p Get all information about your project #{csvType}. Save all your data to a .csv file and open it in your favourite text editor or spreadsheet. You will be able to visualize and analize all your data easily. + div.csv-regenerate-field .field-with-options input(type="text", placeholder="Please regenerate CSV url", readonly, ng-model="csvUrl") .option-wrapper.select-input-content .icon.icon-copy a(href="", title="Regenerate CSV url", ng-click="ctrl.regenerateUuid()") - span.icon.icon-reload - span Regenerate - - a.help-button(href="https://taiga.io/support/csv-reports/", target="_blank") - span.icon.icon-help - span How to use this on my own spreadsheet? + span.icon.icon-plus(ng-hide="csvUrl") + span(ng-hide="csvUrl") Generate URL + span.icon.icon-reload(ng-Show="csvUrl") + span(ng-Show="csvUrl") Regenerate diff --git a/app/styles/modules/admin/project-csv.scss b/app/styles/modules/admin/project-csv.scss index 079fb53c..e6f16a08 100644 --- a/app/styles/modules/admin/project-csv.scss +++ b/app/styles/modules/admin/project-csv.scss @@ -1,4 +1,5 @@ .project-csv { + margin-bottom: 2.5rem; .project-values-title { margin-bottom: 1rem; } @@ -10,8 +11,9 @@ margin-bottom: 1rem; a { @extend %small; + min-width: 110px; } - span:first-child { + .icon { margin-right: .3rem; } } From 506210c29216334cc213302e8cc6c145b153f7cb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 11:52:07 +0100 Subject: [PATCH 177/207] Project reports text organization --- app/partials/admin/admin-project-reports.jade | 4 +++- app/partials/includes/modules/admin/project-csv.jade | 2 -- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/app/partials/admin/admin-project-reports.jade b/app/partials/admin/admin-project-reports.jade index 3bf447e8..a066b767 100644 --- a/app/partials/admin/admin-project-reports.jade +++ b/app/partials/admin/admin-project-reports.jade @@ -9,7 +9,9 @@ div.wrapper(ng-controller="ProjectProfileController as ctrl", section.main.admin-common(tg-project-export) header include ../includes/components/mainTitle - p.admin-subtitle Export your project data in CSV format and make your own reports + p.admin-subtitle Export your project data in CSV format and make your own reports. + + p Download a CSV file or copy the generated URL and open it in your favourite text editor or spreadsheet to make your own project data reports. You will be able to visualize and analize all your data easily. - var csvType = "US"; - var controller = "CsvExporterUserstoriesController"; diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade index 57b644c5..b3f89b4e 100644 --- a/app/partials/includes/modules/admin/project-csv.jade +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -4,8 +4,6 @@ section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}", ng-show="csvUrl") span Download CSV - p Get all information about your project #{csvType}. Save all your data to a .csv file and open it in your favourite text editor or spreadsheet. You will be able to visualize and analize all your data easily. - div.csv-regenerate-field .field-with-options input(type="text", placeholder="Please regenerate CSV url", readonly, ng-model="csvUrl") From 1906abaa1c7da0041497d6c107c16aede18b139e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 12:35:35 +0100 Subject: [PATCH 178/207] Added same margin when editing and preview. --- app/styles/layout/us-detail.scss | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index ae06ec79..efda5f53 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -226,6 +226,9 @@ top: .4rem; transition: all .2s linear; } + .preview { + padding-top: 1.5rem; + } } } From c6e8b70d4b752dd47519fb80cc271816a2f64cd9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Thu, 12 Mar 2015 12:56:59 +0100 Subject: [PATCH 179/207] Fix #2423: Javascript error when the doomline is rendered --- app/coffee/modules/backlog/main.coffee | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index d2333baa..ac1185bb 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -544,6 +544,8 @@ BacklogDirective = ($repo, $rootscope) -> total_points = stats.total_points current_sum = stats.assigned_points + return if not $scope.visibleUserstories + for us, i in $scope.visibleUserstories current_sum += us.total_points From 44080a63ef3a520ffa8685051f45c67624dec2a9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 13:02:59 +0100 Subject: [PATCH 180/207] Fix flexbox in home page --- app/partials/project/project.jade | 25 ++++++++++++------------- app/styles/modules/home-project.scss | 15 +++++---------- 2 files changed, 17 insertions(+), 23 deletions(-) diff --git a/app/partials/project/project.jade b/app/partials/project/project.jade index 77a571ec..56fb4f81 100644 --- a/app/partials/project/project.jade +++ b/app/partials/project/project.jade @@ -3,19 +3,18 @@ div.wrapper(ng-controller="ProjectController as ctrl") h1 span.green(tg-bo-bind="project.name", class="project-name") div.summary - ul.home-project-info-list - li - span.info-num(tg-bo-bind="stats.total_points") - span.info-text project
points - li - span.info-num(tg-bo-bind="stats.defined_points") - span.info-text defined
points - li - span.info-num(tg-bo-bind="stats.assigned_points") - span.info-text assigned
points - li - span.info-num(tg-bo-bind="stats.closed_points") - span.info-text closed
points + div.summary-stats + span.info-num(tg-bo-bind="stats.total_points") + span.info-text project
points + div.summary-stats + span.info-num(tg-bo-bind="stats.defined_points") + span.info-text defined
points + div.summary-stats + span.info-num(tg-bo-bind="stats.assigned_points") + span.info-text assigned
points + div.summary-stats + span.info-num(tg-bo-bind="stats.closed_points") + span.info-text closed
points div.project-data-container p.description(tg-bo-bind="project.description") ul diff --git a/app/styles/modules/home-project.scss b/app/styles/modules/home-project.scss index a106546f..b093b945 100644 --- a/app/styles/modules/home-project.scss +++ b/app/styles/modules/home-project.scss @@ -1,10 +1,6 @@ -.home-project-info-list { +.summary-stats { + align-items: flex-start; display: flex; - li { - flex-basis: 0; - flex-grow: 1; - margin-right: 1rem; - } .info-num { @extend %xlarge; @extend %bold; @@ -22,11 +18,10 @@ .project-data-container { display: flex; - p { - flex-grow: 3; - } + justify-content: space-between; ul { - flex-grow: 1; + flex-grow: 0; + max-width: 33%; } li { display: inline-block; From 9f4292782ad0b4333de12569331177f1be03836e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 13:22:12 +0100 Subject: [PATCH 181/207] Fix inheritance code and buttons --- .../project/project-navigation-base.jade | 26 +++++++++---------- app/partials/project/projects.jade | 4 +-- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/app/partials/project/project-navigation-base.jade b/app/partials/project/project-navigation-base.jade index f9c7cc15..030087b6 100644 --- a/app/partials/project/project-navigation-base.jade +++ b/app/partials/project/project-navigation-base.jade @@ -1,20 +1,20 @@ h1 Your projects form fieldset - input(type="text", placeholder="Search in...", class="search-project") - a(class="icon icon-search") + input.search-project(type="text", placeholder="Search in...") + a.icon.icon-search -div(class="create-project-button-wrapper") - a(class="button button-green create-project-button" href="" title="Create new project"). - Create project +div.create-project-button-wrapper + a.button-green.create-project-button(href="" title="Create new project") + span Create project div(tg-import-project-button) - a(class="button button-blackish import-project-button" href="" title="Import project") - span(class="icon icon-upload") - input(class="import-file hidden" type="file") + a.button-blackish.import-project-button(href="" title="Import project") + span.icon.icon-upload + input.import-file.hidden(type="file") -div(class="projects-pagination" tg-projects-pagination) - a(class="v-pagination-previous icon icon-arrow-up", href="") - div(class="v-pagination-list") - ul(class="projects-list") - a(class="v-pagination-next icon icon-arrow-bottom" href="") +div.projects-pagination(tg-projects-pagination) + a.v-pagination-previous.icon.icon-arrow-up(href="", title="Show previous projects") + div.v-pagination-list + ul.projects-list + a.v-pagination-next.icon.icon-arrow-bottom(href="", title="Show next projects") diff --git a/app/partials/project/projects.jade b/app/partials/project/projects.jade index f51708fa..94a16268 100644 --- a/app/partials/project/projects.jade +++ b/app/partials/project/projects.jade @@ -25,8 +25,8 @@ div.home-projects-list(ng-controller="ProjectsController as ctrl") div(tg-projects-list) .create-project-button-wrapper - a.button-green.create-project-button(href="", ng-click="ctrl.newProject()", - title="Create new project") Create project + a.button-green.create-project-button(href="", ng-click="ctrl.newProject()", title="Create new project") + span Create project div(tg-import-project-button) a.button-blackish.import-project-button(href="", title="Import project") span.icon.icon-upload From e3290adf290136720aedb78ac5c72c874597ca45 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Thu, 12 Mar 2015 13:22:30 +0100 Subject: [PATCH 182/207] fix edit user settings --- app/coffee/modules/user-settings/main.coffee | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/user-settings/main.coffee b/app/coffee/modules/user-settings/main.coffee index 203b978d..656decd4 100644 --- a/app/coffee/modules/user-settings/main.coffee +++ b/app/coffee/modules/user-settings/main.coffee @@ -91,8 +91,8 @@ UserProfileDirective = ($confirm, $auth, $repo) -> changeEmail = $scope.user.isAttributeModified("email") onSuccess = (data) => - user = $model.make_model("users", data) - $auth.setUser(user) + $auth.setUser(data) + if changeEmail $confirm.success("Check your inbox!
We have sent a mail to your account
@@ -113,7 +113,7 @@ UserProfileDirective = ($confirm, $auth, $repo) -> return {link:link} -module.directive("tgUserProfile", ["$tgConfirm", "$tgAuth", "$tgRepo", UserProfileDirective]) +module.directive("tgUserProfile", ["$tgConfirm", "$tgAuth", "$tgRepo", UserProfileDirective]) ############################################################################# From a30c4731e3ab79e4b218a9d8e389934fc80e7c7d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 13:47:52 +0100 Subject: [PATCH 183/207] Fix kanban height when empty. #TG-2417 #ready-for-test --- app/styles/layout/kanban.scss | 1 + app/styles/modules/kanban/kanban-table.scss | 2 ++ 2 files changed, 3 insertions(+) diff --git a/app/styles/layout/kanban.scss b/app/styles/layout/kanban.scss index 8421f1bd..236ee1a0 100644 --- a/app/styles/layout/kanban.scss +++ b/app/styles/layout/kanban.scss @@ -1,6 +1,7 @@ .kanban { display: flex; flex-direction: column; + height: 100vh; max-height: 100vh; header { min-height: 70px; diff --git a/app/styles/modules/kanban/kanban-table.scss b/app/styles/modules/kanban/kanban-table.scss index f498637a..16620a05 100644 --- a/app/styles/modules/kanban/kanban-table.scss +++ b/app/styles/modules/kanban/kanban-table.scss @@ -9,6 +9,7 @@ $column-margin: 0 10px 0 0; .kanban-table { display: flex; flex-direction: column; + height: 100%; overflow: hidden; width: 100%; .vfold { @@ -97,6 +98,7 @@ $column-margin: 0 10px 0 0; .kanban-table-body { @extend %medium; display: flex; + height: 100%; overflow: hidden; overflow-x: auto; width: 100%; From 27dccac790c7a1ae1cd9245e36ffd2bce07864cd Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Thu, 12 Mar 2015 12:41:03 +0100 Subject: [PATCH 184/207] Reseting form for clearing errors --- app/coffee/modules/backlog/lightboxes.coffee | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/coffee/modules/backlog/lightboxes.coffee b/app/coffee/modules/backlog/lightboxes.coffee index 0965fa7e..d77ac2ee 100644 --- a/app/coffee/modules/backlog/lightboxes.coffee +++ b/app/coffee/modules/backlog/lightboxes.coffee @@ -103,6 +103,9 @@ CreateEditSprint = ($repo, $confirm, $rs, $rootscope, lightboxService, $loading) $repo.remove($scope.sprint).then(onSuccess, onError) $scope.$on "sprintform:create", (event, projectId) -> + form = $el.find("form").checksley() + form.reset() + createSprint = true $scope.sprint.project = projectId $scope.sprint.name = null From 70641bc3425fd9be8f3c9bf0ffaf5336b50311e5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Thu, 12 Mar 2015 15:11:40 +0100 Subject: [PATCH 185/207] Add scrollbars only when needed --- app/styles/modules/backlog/taskboard-table.scss | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/app/styles/modules/backlog/taskboard-table.scss b/app/styles/modules/backlog/taskboard-table.scss index 23900067..6863e530 100644 --- a/app/styles/modules/backlog/taskboard-table.scss +++ b/app/styles/modules/backlog/taskboard-table.scss @@ -110,8 +110,7 @@ $column-margin: 0 10px 0 0; .taskboard-table-body { height: 700px; - overflow-x: scroll; - overflow-y: scroll; + overflow: auto; width: 100%; .task-column { flex-basis: $column-width; From 6fddf57c93eaac96860c2a6d82531c8ebdc2b7e0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Thu, 12 Mar 2015 15:43:22 +0100 Subject: [PATCH 186/207] Revert "Add scrollbars only when needed" --- app/styles/modules/backlog/taskboard-table.scss | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/styles/modules/backlog/taskboard-table.scss b/app/styles/modules/backlog/taskboard-table.scss index 6863e530..23900067 100644 --- a/app/styles/modules/backlog/taskboard-table.scss +++ b/app/styles/modules/backlog/taskboard-table.scss @@ -110,7 +110,8 @@ $column-margin: 0 10px 0 0; .taskboard-table-body { height: 700px; - overflow: auto; + overflow-x: scroll; + overflow-y: scroll; width: 100%; .task-column { flex-basis: $column-width; From 7f78de39d19fec17c3ac37bca4951190d42e3f4c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Thu, 12 Mar 2015 15:48:25 +0100 Subject: [PATCH 187/207] Revert "Revert "Add scrollbars only when needed"" This reverts commit 6fddf57c93eaac96860c2a6d82531c8ebdc2b7e0. --- app/styles/modules/backlog/taskboard-table.scss | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/app/styles/modules/backlog/taskboard-table.scss b/app/styles/modules/backlog/taskboard-table.scss index 23900067..6863e530 100644 --- a/app/styles/modules/backlog/taskboard-table.scss +++ b/app/styles/modules/backlog/taskboard-table.scss @@ -110,8 +110,7 @@ $column-margin: 0 10px 0 0; .taskboard-table-body { height: 700px; - overflow-x: scroll; - overflow-y: scroll; + overflow: auto; width: 100%; .task-column { flex-basis: $column-width; From 30c4a3f71608e2d163148c3075b97a8923b50cc2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Thu, 12 Mar 2015 19:57:49 +0100 Subject: [PATCH 188/207] Move CSVController from project-attributes to project-profile --- .../modules/admin/project-profile.coffee | 64 +++++++++++++++++++ .../modules/admin/project-values.coffee | 60 +---------------- .../includes/modules/admin/project-csv.jade | 2 +- 3 files changed, 67 insertions(+), 59 deletions(-) diff --git a/app/coffee/modules/admin/project-profile.coffee b/app/coffee/modules/admin/project-profile.coffee index 03f4415b..8e109cd6 100644 --- a/app/coffee/modules/admin/project-profile.coffee +++ b/app/coffee/modules/admin/project-profile.coffee @@ -297,3 +297,67 @@ ProjectExportDirective = ($window, $rs, $confirm) -> return {link:link} module.directive("tgProjectExport", ["$window", "$tgResources", "$tgConfirm", ProjectExportDirective]) + + +############################################################################# +## CSV Export Controllers +############################################################################# + +class CsvExporterController extends taiga.Controller + @.$inject = [ + "$scope", + "$rootScope", + "$tgUrls", + "$tgConfirm", + "$tgResources", + ] + + constructor: (@scope, @rootscope, @urls, @confirm, @rs) -> + @rootscope.$on("project:loaded", @.setCsvUuid) + @scope.$watch "csvUuid", (value) => + if value + @scope.csvUrl = @urls.resolveAbsolute("#{@.type}-csv", value) + else + @scope.csvUrl = "" + + setCsvUuid: => + @scope.csvUuid = @scope.project["#{@.type}_csv_uuid"] + + _generateUuid: (finish) => + promise = @rs.projects["regenerate_#{@.type}_csv_uuid"](@scope.projectId) + + promise.then (data) => + @scope.csvUuid = data.data?.uuid + + promise.then null, => + @confirm.notify("error") + + promise.finally -> + finish() + return promise + + regenerateUuid: -> + #TODO: i18n + if @scope.csvUuid + title = "Change URL" + subtitle = "You going to change the CSV data access url. The previous url will be disabled. Are you sure?" + @confirm.ask(title, subtitle).then @._generateUuid + else + @._generateUuid(_.identity) + + +class CsvExporterUserstoriesController extends CsvExporterController + type: "userstories" + + +class CsvExporterTasksController extends CsvExporterController + type: "tasks" + + +class CsvExporterIssuesController extends CsvExporterController + type: "issues" + + +module.controller("CsvExporterUserstoriesController", CsvExporterUserstoriesController) +module.controller("CsvExporterTasksController", CsvExporterTasksController) +module.controller("CsvExporterIssuesController", CsvExporterIssuesController) diff --git a/app/coffee/modules/admin/project-values.coffee b/app/coffee/modules/admin/project-values.coffee index 87f0de3b..35390de9 100644 --- a/app/coffee/modules/admin/project-values.coffee +++ b/app/coffee/modules/admin/project-values.coffee @@ -63,7 +63,7 @@ class ProjectValuesSectionController extends mixOf(taiga.Controller, taiga.PageM return @rs.projects.get(@scope.projectId).then (project) => if not project.i_am_owner @location.path(@navUrls.resolve("permission-denied")) - + @scope.project = project @scope.$emit('project:loaded', project) return project @@ -354,6 +354,7 @@ ColorSelectionDirective = () -> module.directive("tgColorSelection", ColorSelectionDirective) + ############################################################################# ## Custom Attributes Controller ############################################################################# @@ -625,60 +626,3 @@ ProjectCustomAttributesDirective = ($log, $confirm, animationFrame) -> return {link: link} module.directive("tgProjectCustomAttributes", ["$log", "$tgConfirm", "animationFrame", ProjectCustomAttributesDirective]) - -############################################################################# -## CSV Exporter directive -############################################################################# - -class CsvExporterController extends taiga.Controller - @.$inject = [ - "$scope", - "$rootScope", - "$tgUrls", - "$tgConfirm", - "$tgResources", - ] - - constructor: (@scope, @rootscope, @urls, @confirm, @rs) -> - @rootscope.$on("project:loaded", @.setCsvUuid) - @scope.$watch "csvUuid", (value) => - if value - @scope.csvUrl = @urls.resolveAbsolute("#{@.type}-csv", value) - else - @scope.csvUrl = "" - - setCsvUuid: => - @scope.csvUuid = @scope.project["#{@.type}_csv_uuid"] - - _generateUuid: (finish) => - promise = @rs.projects["regenerate_#{@.type}_csv_uuid"](@scope.projectId) - - promise.then (data) => - @scope.csvUuid = data.data?.uuid - - promise.then null, => - @confirm.notify("error") - - promise.finally -> - finish() - return promise - - regenerateUuid: -> - #TODO: i18n - if @scope.csvUuid - @confirm.ask("Change URL", "You going to change the CSV data access url. The previous url will be disabled. Are you sure?").then @._generateUuid - else - @._generateUuid(_.identity) - -class CsvExporterUserstoriesController extends CsvExporterController - type: "userstories" - -class CsvExporterTasksController extends CsvExporterController - type: "tasks" - -class CsvExporterIssuesController extends CsvExporterController - type: "issues" - -module.controller("CsvExporterUserstoriesController", CsvExporterUserstoriesController) -module.controller("CsvExporterTasksController", CsvExporterTasksController) -module.controller("CsvExporterIssuesController", CsvExporterIssuesController) diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade index b3f89b4e..e87d728c 100644 --- a/app/partials/includes/modules/admin/project-csv.jade +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -1,4 +1,4 @@ -section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text) +section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text) div.project-values-title h2 #{csvType} reports a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}", ng-show="csvUrl") From 72c3eb596014f2e8a1b4500d163b4ca08ef4109a Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 13 Mar 2015 07:54:23 +0100 Subject: [PATCH 189/207] Fixing Bug 2440 - The download CSV buttons doesn't work --- app/partials/includes/modules/admin/project-csv.jade | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/partials/includes/modules/admin/project-csv.jade b/app/partials/includes/modules/admin/project-csv.jade index e87d728c..07254021 100644 --- a/app/partials/includes/modules/admin/project-csv.jade +++ b/app/partials/includes/modules/admin/project-csv.jade @@ -1,7 +1,7 @@ section.project-csv(ng-controller='#{controller} as ctrl', tg-select-input-text) div.project-values-title h2 #{csvType} reports - a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}", ng-show="csvUrl") + a.button.button-gray(title="Download #{csvType} CSV", ng-href="{{csvUrl}}", ng-show="csvUrl", target="_blank") span Download CSV div.csv-regenerate-field From d4a0f4cda5004540517058e3b119f42e68824b5e Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 13 Mar 2015 08:08:17 +0100 Subject: [PATCH 190/207] Bug 2439 - Webooks created can't be edited without refreshing --- app/coffee/modules/admin/third-parties.coffee | 2 -- 1 file changed, 2 deletions(-) diff --git a/app/coffee/modules/admin/third-parties.coffee b/app/coffee/modules/admin/third-parties.coffee index 5ba18666..ceeaaf2f 100644 --- a/app/coffee/modules/admin/third-parties.coffee +++ b/app/coffee/modules/admin/third-parties.coffee @@ -128,8 +128,6 @@ WebhookDirective = ($rs, $repo, $confirm, $loading) -> save = debounce 2000, (target) -> form = target.parents("form").checksley() return if not form.validate() - - value = target.scope().value promise = $repo.save(webhook) promise.then => showVisualizationMode() From e0aa554153b93591bca992a5c612d636e3067bba Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 13 Mar 2015 08:23:01 +0100 Subject: [PATCH 191/207] BUG 2437 - The taskboard edit lightbox have the button (CREATE in place of SAVE) --- app/coffee/modules/taskboard/lightboxes.coffee | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/taskboard/lightboxes.coffee b/app/coffee/modules/taskboard/lightboxes.coffee index fbdfa1c4..367aba17 100644 --- a/app/coffee/modules/taskboard/lightboxes.coffee +++ b/app/coffee/modules/taskboard/lightboxes.coffee @@ -40,7 +40,7 @@ CreateEditTaskDirective = ($repo, $model, $rs, $rootscope, $loading, lightboxSer $scope.isNew = true # Update texts for creation - $el.find(".button-green span").html("Create") #TODO: i18n + $el.find(".button-green").html("Create") #TODO: i18n $el.find(".title").html("New task ") #TODO: i18n $el.find(".tag-input").val("") @@ -51,7 +51,7 @@ CreateEditTaskDirective = ($repo, $model, $rs, $rootscope, $loading, lightboxSer $scope.isNew = false # Update texts for edition - $el.find(".button-green span").html("Save") #TODO: i18n + $el.find(".button-green").html("Save") #TODO: i18n $el.find(".title").html("Edit task ") #TODO: i18n $el.find(".tag-input").val("") From 360ee898bfe44405b66060548d3c02d7721bf0fe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Mar 2015 08:30:27 +0100 Subject: [PATCH 192/207] Move preview in Wiki to fit in edition position. #TG-2442 #ready-for-test --- app/styles/layout/wiki.scss | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/app/styles/layout/wiki.scss b/app/styles/layout/wiki.scss index 48cb40ab..62fb3b23 100644 --- a/app/styles/layout/wiki.scss +++ b/app/styles/layout/wiki.scss @@ -22,6 +22,14 @@ .wiki-content { margin-bottom: 2rem; position: relative; + &.editable { + &:hover { + .wysiwyg { + background: $whitish; + cursor: pointer; + } + } + } .view-wiki-content { &:hover { .edit { @@ -63,12 +71,7 @@ top: .4rem; } } - &.editable { - &:hover { - .wysiwyg { - background: $whitish; - cursor: pointer; - } - } + .preview { + padding-top: 1.8rem; } } From dfbfe4210b62e3eb3aab477c358ac2d147a7dc3f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Mar 2015 08:48:30 +0100 Subject: [PATCH 193/207] Fix long text breaks on history. TG-2433 #ready-for-test --- app/styles/modules/common/history.scss | 1 + 1 file changed, 1 insertion(+) diff --git a/app/styles/modules/common/history.scss b/app/styles/modules/common/history.scss index 6fad337a..688bcb9e 100644 --- a/app/styles/modules/common/history.scss +++ b/app/styles/modules/common/history.scss @@ -35,6 +35,7 @@ } .activity-fromto { @extend %small; + word-wrap: break-word; } } .history-tabs { From 83487b631362b19923fc2c4192643bbb999181ce Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 13 Mar 2015 08:57:45 +0100 Subject: [PATCH 194/207] Bug 2441 - there is a visual glitch in the issue title, when I promote it to us --- app/styles/layout/us-detail.scss | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/app/styles/layout/us-detail.scss b/app/styles/layout/us-detail.scss index efda5f53..90107884 100644 --- a/app/styles/layout/us-detail.scss +++ b/app/styles/layout/us-detail.scss @@ -100,8 +100,7 @@ margin-top: .5rem; a { border-left: 1px solid $gray-light; - padding: 0 .2rem; - transition: color .3s linear; + padding: 0 .2rem; } a:hover { color: $green-taiga; From 5edc4d76f397bf8a4f0971373e35acc204f4bfc8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Xavier=20Juli=C3=A1n?= Date: Fri, 13 Mar 2015 09:07:53 +0100 Subject: [PATCH 195/207] Fix button width regarless of text in lightbox --- app/styles/modules/common/lightbox.scss | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/styles/modules/common/lightbox.scss b/app/styles/modules/common/lightbox.scss index 7a9f4adb..bdfdd09c 100644 --- a/app/styles/modules/common/lightbox.scss +++ b/app/styles/modules/common/lightbox.scss @@ -247,9 +247,9 @@ .options { display: flex; a { - flex-grow: 1; padding: 8px 0; text-align: center; + width: 100%; &:first-child { margin-right: .5rem; } From d7579b052bd8f75d1594da1bdc85b15fb9685dfc Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 13 Mar 2015 08:42:08 +0100 Subject: [PATCH 196/207] tgCheckPermission directive tg-class-permission="{'xx': 'modify_us'}" the directive add 'xx' if the user has the modify_us permisssion --- app/coffee/modules/common.coffee | 36 ++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/app/coffee/modules/common.coffee b/app/coffee/modules/common.coffee index bb11a405..15514453 100644 --- a/app/coffee/modules/common.coffee +++ b/app/coffee/modules/common.coffee @@ -60,6 +60,42 @@ CheckPermissionDirective = -> module.directive("tgCheckPermission", CheckPermissionDirective) +############################################################################# +## Add class based on permissions +############################################################################# + +ClassPermissionDirective = -> + name = "tgClassPermission" + + link = ($scope, $el, $attrs) -> + checkPermissions = (project, className, permission) -> + negation = permission[0] == "!" + + permission = permission.slice(1) if negation + + if negation && project.my_permissions.indexOf(permission) == -1 + $el.addClass(className) + else if project.my_permissions.indexOf(permission) != -1 + $el.addClass(className) + else + $el.removeClass(className) + + tgClassPermissionWatchAction = (project) -> + if project + unbindWatcher() + + classes = $scope.$eval($attrs[name]) + + for className, permission of classes + checkPermissions(project, className, permission) + + + unbindWatcher = $scope.$watch "project", tgClassPermissionWatchAction + + return {link:link} + +module.directive("tgClassPermission", ClassPermissionDirective) + ############################################################################# ## Animation frame service, apply css changes in the next render frame ############################################################################# From 7ced58da24a5ec7696dcc38d7d77dccea1bb7790 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Fri, 13 Mar 2015 08:54:36 +0100 Subject: [PATCH 197/207] fix #2432 - backlog table points near the border with anonymous users --- app/partials/includes/components/backlog-row.jade | 2 +- app/styles/modules/backlog/backlog-table.scss | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/app/partials/includes/components/backlog-row.jade b/app/partials/includes/components/backlog-row.jade index 5a0dbf87..7b10d154 100644 --- a/app/partials/includes/components/backlog-row.jade +++ b/app/partials/includes/components/backlog-row.jade @@ -1,4 +1,4 @@ -div.row.us-item-row(ng-repeat="us in visibleUserstories track by us.id", tg-bind-scope, ng-class="{blocked: us.is_blocked}") +div.row.us-item-row(ng-repeat="us in visibleUserstories track by us.id", tg-bind-scope, ng-class="{blocked: us.is_blocked}", tg-class-permission="{'readonly': '!modify_us'}") div.user-stories div.tags-block(tg-colorize-tags="us.tags", tg-colorize-tags-type="backlog") div.user-story-name diff --git a/app/styles/modules/backlog/backlog-table.scss b/app/styles/modules/backlog/backlog-table.scss index c9dd613a..c92e6333 100644 --- a/app/styles/modules/backlog/backlog-table.scss +++ b/app/styles/modules/backlog/backlog-table.scss @@ -237,4 +237,8 @@ opacity: 0; padding: .1rem .5rem 0 0; } + .readonly { + cursor: auto; + padding-right: 45px; + } } From 23005a28c32769235db32946b9bf3a48cb6b06a3 Mon Sep 17 00:00:00 2001 From: Andrea Stagi Date: Fri, 13 Mar 2015 10:48:35 +0100 Subject: [PATCH 198/207] Add url formatting to the markdown wysiwyg editor --- app/coffee/modules/common/wisiwyg.coffee | 47 +++++++++++++++++++++++- 1 file changed, 45 insertions(+), 2 deletions(-) diff --git a/app/coffee/modules/common/wisiwyg.coffee b/app/coffee/modules/common/wisiwyg.coffee index 96ffcf77..5b2cf079 100644 --- a/app/coffee/modules/common/wisiwyg.coffee +++ b/app/coffee/modules/common/wisiwyg.coffee @@ -214,14 +214,18 @@ tgMarkitupDirective = ($rootscope, $rs, $tr, $selectedText, $template) -> { name: $tr.t("markdown-editor.picture") key: "P" - replaceWith: '![[![Alternative text]!]]([![Url:!:http://]!] "[![Title]!]")' + replaceWith: '![[![Alternative text]!]](<<<[![Url:!:http://]!]>>> "[![Title]!]")' + beforeInsert:(markItUp) -> prepareUrlFormatting(markItUp) + afterInsert:(markItUp) -> urlFormatting(markItUp) }, { name: $tr.t("markdown-editor.link") key: "L" openWith: "[" - closeWith: ']([![Url:!:http://]!] "[![Title]!]")' + closeWith: '](<<<[![Url:!:http://]!]>>> "[![Title]!]")' placeHolder: $tr.t("markdown-editor.link-placeholder") + beforeInsert:(markItUp) -> prepareUrlFormatting(markItUp) + afterInsert:(markItUp) -> urlFormatting(markItUp) }, { separator: "---------------" @@ -256,6 +260,45 @@ tgMarkitupDirective = ($rootscope, $rs, $tr, $selectedText, $template) -> target = angular.element(event.textarea) $model.$setViewValue(target.val()) + prepareUrlFormatting = (markItUp) -> + console.log(markItUp) + regex = /(<<<|>>>)/gi + result = 0 + indices = [] + (indices.push(result.index)) while ( (result = regex.exec(markItUp.textarea.value)) ) + markItUp.donotparse = indices + console.log(indices) + + urlFormatting = (markItUp) -> + console.log(markItUp.donotparse) + regex = /<<>>/gi + endIndex = 0 + loop + result = regex.exec(markItUp.textarea.value) + break if !result + if result.index not in markItUp.donotparse + endIndex = result.index + break + + value = markItUp.textarea.value + url = value.substring(startIndex, endIndex).replace('<<<', '').replace('>>>', '') + url = url.replace('(', '%28').replace(')', '%29') + url = url.replace('[', '%5B').replace(']', '%5D') + value = value.substring(0, startIndex) + url + value.substring(endIndex+3, value.length) + markItUp.textarea.value = value + markItUp.donotparse = undefined + markdownTitle = (markItUp, char) -> heading = "" n = $.trim(markItUp.selection or markItUp.placeHolder).length From d33591ebc4f2bcc2f73cbaa9834b50be03a47971 Mon Sep 17 00:00:00 2001 From: Alejandro Alonso Date: Fri, 13 Mar 2015 11:14:30 +0100 Subject: [PATCH 199/207] Bug 2374 - The projects cache isn't cleared properly when a user logs out in tree.taiga.io --- app/coffee/modules/projects/main.coffee | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/coffee/modules/projects/main.coffee b/app/coffee/modules/projects/main.coffee index 0642ab3b..8fda3a20 100644 --- a/app/coffee/modules/projects/main.coffee +++ b/app/coffee/modules/projects/main.coffee @@ -50,7 +50,7 @@ class ProjectsController extends taiga.Controller promise = @.loadInitialData() promise.then () => - @scope.$emit("projects:loaded") + @scope.$emit("projects:loaded", @.projects) promise.then null, @.onInitialDataError.bind(@) @@ -257,8 +257,8 @@ ProjectsListDirective = ($compile, $template) -> $el.html($compile(template({projects: projects}))($scope)) $scope.$emit("regenerate:project-pagination") - $scope.$watch "projects", (projects) -> - render(projects) if projects? + $scope.$on "projects:loaded", (ctx, projects) -> + render(projects.all) if projects.all? return { link: link From 1eb657ff7e661f801b300edf43833e223b47056c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?David=20Barrag=C3=A1n=20Merino?= Date: Sun, 15 Mar 2015 11:22:24 +0100 Subject: [PATCH 200/207] Update CHANGELOG --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f03bfa53..99a3ff88 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,7 @@ # Changelog # -## 1.6.0 ??? (Unreleased) +## 1.6.0 Abies Bifolia (Unreleased) ### Features - Added custom fields per project for user stories, tasks and issues. From cc9c4bd0421c114c77601b039f6244e68e9ef271 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 16 Mar 2015 10:28:26 +0100 Subject: [PATCH 201/207] add prevent default in the save description --- app/coffee/modules/common/components.coffee | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/app/coffee/modules/common/components.coffee b/app/coffee/modules/common/components.coffee index 9b5ea62e..dd902037 100644 --- a/app/coffee/modules/common/components.coffee +++ b/app/coffee/modules/common/components.coffee @@ -536,7 +536,9 @@ EditableDescriptionDirective = ($rootscope, $repo, $confirm, $compile, $loading, $el.find('.view-description').hide() $el.find('textarea').focus() - $el.on "click", ".save", -> + $el.on "click", ".save", (e) -> + e.preventDefault() + description = $scope.item.description save(description) From 6bc207828473db72f3957aad34a3fe771ea2b147 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 16 Mar 2015 10:00:49 +0100 Subject: [PATCH 202/207] fix #2385 - refactor wysiwyg list insert --- app/coffee/modules/common/wisiwyg.coffee | 111 ++++++++++++++--------- 1 file changed, 66 insertions(+), 45 deletions(-) diff --git a/app/coffee/modules/common/wisiwyg.coffee b/app/coffee/modules/common/wisiwyg.coffee index 5b2cf079..1527ec01 100644 --- a/app/coffee/modules/common/wisiwyg.coffee +++ b/app/coffee/modules/common/wisiwyg.coffee @@ -24,6 +24,33 @@ bindOnce = @.taiga.bindOnce module = angular.module("taigaCommon") +# How to test lists (-, *, 1.) +# test it with text after & before the list +# + is the cursor position + +# CASE 1 +# - aa+ +# --> enter +# - aa +# - + + +# CASE 1 +# - + +# --> enter + +# + + +# CASE 3 +# - bb+cc +# --> enter +# - bb +# - cc + +# CASE 3 +# +- aa +# --> enter + +# - aa ############################################################################# ## WYSIWYG markitup editor directive @@ -64,35 +91,52 @@ tgMarkitupDirective = ($rootscope, $rs, $tr, $selectedText, $template) -> markdown.off(".preview") closePreviewMode() - markdownCaretPositon = false - - setCaretPosition = (elm, caretPos) -> - if elm.createTextRange - range = elm.createTextRange() - range.move("character", caretPos) + setCaretPosition = (textarea, caretPosition) -> + if textarea.createTextRange + range = textarea.createTextRange() + range.move("character", caretPosition) range.select() - else if elm.selectionStart - elm.focus() - elm.setSelectionRange(caretPos, caretPos) + else if textarea.selectionStart + textarea.focus() + textarea.setSelectionRange(caretPosition, caretPosition) - removeEmptyLine = (textarea, line, currentCaretPosition) -> + # Calculate the scroll position + totalLines = textarea.value.split("\n").length + line = textarea.value[0..(caretPosition - 1)].split("\n").length + scrollRelation = line / totalLines + $el.scrollTop((scrollRelation * $el[0].scrollHeight) - ($el.height() / 2)) + + addLine = (textarea, nline, replace) -> lines = textarea.value.split("\n") - removedLineLength = lines[line].length - lines[line] = "" + if replace + lines[nline] = replace + lines[nline] + else + lines[nline] = "" + + cursorPosition = 0 + + for line, key in lines + cursorPosition += line.length + 1 || 1 + + break if key == nline textarea.value = lines.join("\n") #return the new position - return currentCaretPosition - removedLineLength + 1 + if replace + return cursorPosition - lines[nline].length + replace.length - 1 + else + return cursorPosition markdownSettings = nameSpace: "markdown" onShiftEnter: {keepDefault:false, openWith:"\n\n"} onEnter: - keepDefault: false - replaceWith: (data) => + keepDefault: false, + replaceWith: () -> "\n" + afterInsert: (data) -> lines = data.textarea.value.split("\n") cursorLine = data.textarea.value[0..(data.caretPosition - 1)].split("\n").length newLineContent = data.textarea.value[data.caretPosition..].split("\n")[0] @@ -105,12 +149,9 @@ tgMarkitupDirective = ($rootscope, $rs, $tr, $selectedText, $template) -> emptyListItem = lastLine.match /^(\s*)\-\s$/ if emptyListItem - markdownCaretPositon = removeEmptyLine(data.textarea, lines.length - 1, data.caretPosition) + markdownCaretPositon = addLine(data.textarea, cursorLine - 1) else - breakLineAtBeginning = newLineContent.match /^(\s*)\-\s/ - - if !breakLineAtBeginning - return "\n#{match[1]}" if match + markdownCaretPositon = addLine(data.textarea, cursorLine, "#{match[1]}") # unordered list * match = lastLine.match /^(\s*\* ).*/ @@ -119,12 +160,9 @@ tgMarkitupDirective = ($rootscope, $rs, $tr, $selectedText, $template) -> emptyListItem = lastLine.match /^(\s*\* )$/ if emptyListItem - markdownCaretPositon = removeEmptyLine(data.textarea, lines.length - 1, data.caretPosition) + markdownCaretPositon = addLine(data.textarea, cursorLine - 1) else - breakLineAtBeginning = newLineContent.match /^(\s*)\*\s/ - - if !breakLineAtBeginning - return "\n#{match[1]}" if match + markdownCaretPositon = addLine(data.textarea, cursorLine, "#{match[1]}") # ordered list match = lastLine.match /^(\s*)(\d+)\.\s/ @@ -133,29 +171,12 @@ tgMarkitupDirective = ($rootscope, $rs, $tr, $selectedText, $template) -> emptyListItem = lastLine.match /^(\s*)(\d+)\.\s$/ if emptyListItem - markdownCaretPositon = removeEmptyLine(data.textarea, lines.length - 1, data.caretPosition) + markdownCaretPositon = addLine(data.textarea, cursorLine - 1) else - breakLineAtBeginning = newLineContent.match /^(\s*)(\d+)\.\s/ + markdownCaretPositon = addLine(data.textarea, cursorLine, "#{match[1] + (parseInt(match[2], 10) + 1)}. ") - if !breakLineAtBeginning - return "\n#{match[1] + (parseInt(match[2], 10) + 1)}. " - return "\n" - - afterInsert: (data) -> - # Calculate the scroll position - - if markdownCaretPositon - setCaretPosition(data.textarea, markdownCaretPositon) - caretPosition = markdownCaretPositon - markdownCaretPositon = false - else - caretPosition = data.caretPosition - - totalLines = data.textarea.value.split("\n").length - line = data.textarea.value[0..(caretPosition - 1)].split("\n").length - scrollRelation = line / totalLines - $el.scrollTop((scrollRelation * $el[0].scrollHeight) - ($el.height() / 2)) + setCaretPosition(data.textarea, markdownCaretPositon) if markdownCaretPositon markupSet: [ { From ed59aa46e638da4a2c7782b99452da957436a328 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 16 Mar 2015 14:27:52 +0100 Subject: [PATCH 203/207] fix class permission directive --- app/coffee/modules/common.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/common.coffee b/app/coffee/modules/common.coffee index 15514453..7c03560c 100644 --- a/app/coffee/modules/common.coffee +++ b/app/coffee/modules/common.coffee @@ -75,7 +75,7 @@ ClassPermissionDirective = -> if negation && project.my_permissions.indexOf(permission) == -1 $el.addClass(className) - else if project.my_permissions.indexOf(permission) != -1 + else if !negation && project.my_permissions.indexOf(permission) != -1 $el.addClass(className) else $el.removeClass(className) From 54deeefd1849818f56a9c4ca4603c118829548a2 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Mon, 16 Mar 2015 14:43:31 +0100 Subject: [PATCH 204/207] prevent closed sprints dissapear when the user drag and US to the current sprint --- app/coffee/modules/backlog/main.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/modules/backlog/main.coffee b/app/coffee/modules/backlog/main.coffee index ac1185bb..ab7773c8 100644 --- a/app/coffee/modules/backlog/main.coffee +++ b/app/coffee/modules/backlog/main.coffee @@ -170,7 +170,7 @@ class BacklogController extends mixOf(taiga.Controller, taiga.PageMixin, taiga.F @scope.sprints = sprints @scope.openSprints = _.filter(sprints, (sprint) => not sprint.closed).reverse() - @scope.closedSprints = [] + @scope.closedSprints = [] if !@scope.closedSprints @scope.sprintsCounter = sprints.length @scope.sprintsById = groupBy(sprints, (x) -> x.id) From 5b02d6fc322d890a1bbd4563547e68e355b458e1 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 17 Mar 2015 08:14:30 +0100 Subject: [PATCH 205/207] fix page change on IE when the user toggle a sprint --- app/coffee/modules/backlog/sprints.coffee | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/coffee/modules/backlog/sprints.coffee b/app/coffee/modules/backlog/sprints.coffee index 21e720ee..98419c65 100644 --- a/app/coffee/modules/backlog/sprints.coffee +++ b/app/coffee/modules/backlog/sprints.coffee @@ -61,6 +61,8 @@ BacklogSprintDirective = ($repo, $rootscope) -> # Event Handlers $el.on "click", ".sprint-name > .icon-arrow-up", (event) -> + event.preventDefault() + toggleSprint($el) $el.find(".sprint-table").slideToggle(slideOptions) From 66ed16e744afe2418bde9f31111f05b455d028b5 Mon Sep 17 00:00:00 2001 From: Juanfran Date: Tue, 17 Mar 2015 09:12:45 +0100 Subject: [PATCH 206/207] angular debug info disabled by default --- app/coffee/app.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/coffee/app.coffee b/app/coffee/app.coffee index 0f099adc..6858425d 100644 --- a/app/coffee/app.coffee +++ b/app/coffee/app.coffee @@ -234,7 +234,7 @@ configure = ($routeProvider, $locationProvider, $httpProvider, $provide, $tgEven linewidth: "The subject must have a maximum size of %s" }) - $compileProvider.debugInfoEnabled(window.taigaConfig.debugInfo) + $compileProvider.debugInfoEnabled(window.taigaConfig.debugInfo || false) init = ($log, $i18n, $config, $rootscope, $auth, $events, $analytics) -> $i18n.initialize($config.get("defaultLanguage")) From 31e57e195a8520b3f8e4479fddfd1fe052a6d504 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jes=C3=BAs=20Espino?= Date: Tue, 17 Mar 2015 10:57:01 +0100 Subject: [PATCH 207/207] Adding date to the changelog --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 99a3ff88..f4648024 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,7 @@ # Changelog # -## 1.6.0 Abies Bifolia (Unreleased) +## 1.6.0 Abies Bifolia (2015-03-17) ### Features - Added custom fields per project for user stories, tasks and issues.