US #3440 - Send notifications (live announcement) to the user through taiga-events

stable
Juanfran 2015-11-13 13:34:01 +01:00 committed by David Barragán Merino
parent 5184433116
commit c1e5eb285b
10 changed files with 202 additions and 7 deletions

View File

@ -4,6 +4,7 @@
## 1.9.1 Taiga Tribe (unreleased)
- [118n] Now taiga plugins can be translatable.
- New Taiga plugins system.
- Now superadmins can send notifications (live announcement) to the user (through taiga-events).
### Misc
- Statics folder hash to prevent cache problems when a new version is released.

View File

@ -27,7 +27,7 @@ module = angular.module("taigaEvents", [])
class EventsService
constructor: (@win, @log, @config, @auth) ->
constructor: (@win, @log, @config, @auth, @liveAnnouncementService, @rootScope) ->
bindMethods(@)
initialize: (sessionId) ->
@ -78,6 +78,11 @@ class EventsService
delete @.ws
notifications: ->
@.subscribe null, 'notifications', (data) =>
@liveAnnouncementService.show(data.title, data.desc)
@rootScope.$digest()
###########################################
# Heartbeat (Ping - Pong)
###########################################
@ -144,7 +149,12 @@ class EventsService
return
subscription = @.subscriptions[routingKey]
subscription.scope.$apply ->
if subscription.scope
subscription.scope.$apply ->
subscription.callback(data.data)
else
subscription.callback(data.data)
###########################################
@ -168,7 +178,8 @@ class EventsService
@.subscriptions[routingKey] = subscription
@.sendMessage(message)
scope.$on("$destroy", => @.unsubscribe(routingKey))
scope.$on("$destroy", => @.unsubscribe(routingKey)) if scope
unsubscribe: (routingKey) ->
if @.error
@ -189,6 +200,7 @@ class EventsService
onOpen: ->
@.connected = true
@.startHeartBeatMessages()
@.notifications()
@log.debug("WebSocket connection opened")
token = @auth.getToken()
@ -204,6 +216,7 @@ class EventsService
@.log.debug "WebSocket message received: #{event.data}"
data = JSON.parse(event.data)
if data.cmd == "pong"
@.processHeartBeatPongMessage(data)
else
@ -223,11 +236,18 @@ class EventsProvider
setSessionId: (sessionId) ->
@.sessionId = sessionId
$get: ($win, $log, $conf, $auth) ->
service = new EventsService($win, $log, $conf, $auth)
$get: ($win, $log, $conf, $auth, liveAnnouncementService, $rootScope) ->
service = new EventsService($win, $log, $conf, $auth, liveAnnouncementService, $rootScope)
service.initialize(@.sessionId)
return service
@.prototype.$get.$inject = ["$window", "$log", "$tgConfig", "$tgAuth"]
@.prototype.$get.$inject = [
"$window",
"$log",
"$tgConfig",
"$tgAuth",
"tgLiveAnnouncementService",
"$rootScope"
]
module.provider("$tgEvents", EventsProvider)

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

View File

@ -38,6 +38,7 @@ html(lang="en")
include partials/includes/components/notification-message
div(tg-joy-ride)
div(tg-live-announcement)
script(src="/#{v}/js/libs.js")
script(src="/#{v}/js/templates.js")

View File

@ -0,0 +1,54 @@
###
# Copyright (C) 2014-2015 Andrey Antukh <niwi@niwi.be>
# Copyright (C) 2014-2015 Jesús Espino Garcia <jespinog@gmail.com>
# Copyright (C) 2014-2015 David Barragán Merino <bameda@dbarragan.com>
#
# 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 <http://www.gnu.org/licenses/>.
#
# File: live-announcement.directive.coffee
###
LiveAnnouncementDirective = (liveAnnouncementService) ->
link = (scope, el, attrs) ->
return {
restrict: "AE",
scope: {},
controllerAs: 'vm',
controller: () ->
this.close = () ->
liveAnnouncementService.open = false
Object.defineProperties(this, {
open: {
get: () -> return liveAnnouncementService.open
},
title: {
get: () -> return liveAnnouncementService.title
},
desc: {
get: () -> return liveAnnouncementService.desc
}
})
link: link,
templateUrl: "components/live-announcement/live-announcement.html"
}
LiveAnnouncementDirective.$inject = [
"tgLiveAnnouncementService"
]
angular.module("taigaComponents")
.directive("tgLiveAnnouncement", LiveAnnouncementDirective)

View File

@ -0,0 +1,12 @@
.live-announcement(ng-class="{visible: vm.open}")
.live-announcement-inner
img.anouncement-decoration(src="/#{v}/images/notification-decoration.png", alt="Loading...")
.text
h2.title {{vm.title}}
p.warning(ng-bind-html="vm.desc")
a.close(
ng-click="vm.close()"
href=""
title="{{ COMMON.CLOSE | translate }}"
)
include ../../../svg/remove.svg

View File

@ -0,0 +1,72 @@
.live-announcement {
$animation-steps-duration: .5s;
align-content: center;
background: $tribe-primary;
display: flex;
height: 0;
justify-content: center;
overflow: hidden;
pointer-events: none;
position: fixed;
top: 0;
transition: width $animation-steps-duration, height $animation-steps-duration;
transition-delay: $animation-steps-duration;
width: 0;
z-index: 99;
.live-announcement-inner {
opacity: 0;
transition: opacity $animation-steps-duration;
width: 100%;
}
&.visible {
height: 146px;
pointer-events: auto;
transition-delay: 0s;
width: 100%;
.live-announcement-inner {
opacity: 1;
transition: opacity $animation-steps-duration $animation-steps-duration;
}
}
}
.live-announcement-inner {
display: flex;
max-width: 1200px;
.announcement-decoration {
align-self: flex-end;
margin-right: 1rem;
}
.text {
padding: 1.25rem 3rem 1.25rem 2rem;
position: relative;
width: 100%;
}
.title {
@extend %bold;
@extend %larger;
color: $tribe-secondary;
margin-bottom: .5rem;
}
.warning {
color: $tribe-secondary;
a {
@extend %bold;
color: $tribe-secondary;
}
}
.close {
height: 2.5rem;
position: absolute;
right: 0;
top: 1rem;
width: 2.5rem;
svg {
fill: lighten($tribe-secondary, 15%);
transition: fill .2s;
&:hover {
fill: $tribe-secondary;
}
}
}
}

View File

@ -0,0 +1,31 @@
###
# Copyright (C) 2014-2015 Taiga Agile LLC <taiga@taiga.io>
#
# 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 <http://www.gnu.org/licenses/>.
#
# File: notification.service.coffee
###
class LiveAnnouncementService extends taiga.Service
constructor: () ->
@.open = false
@.title = ""
@.desc = ""
show: (title, desc) ->
@.open = true
@.title = title
@.desc = desc
angular.module("taigaComponents").service("tgLiveAnnouncementService", LiveAnnouncementService)

View File

@ -1,6 +1,6 @@
div.wrapper
tg-project-menu
div.centered.single-project
div.single-project.centered
section.single-project-intro
div.intro-options
h1

View File

@ -31,6 +31,10 @@ $red-amaranth: #e43050;
$purple-eggplant: #810061;
$yellow-pear: #bbe831;
$tribe-primary: #98e0eb;
$tribe-secondary: #107a8a;
$top-icon-color: #11241f;
$dropdown-color: rgba(darken($grayer, 20%), 1);