Merge pull request #708 from OZhurbenko/meteor-ui

Notifications and other fixes
This commit is contained in:
Chad Pilkey 2015-07-18 21:57:50 -04:00
commit dce6edfe32
13 changed files with 288 additions and 136 deletions

View File

@ -236,11 +236,20 @@ Handlebars.registerHelper 'whiteboardSize', (section) ->
if msg.message.from_userid is myUserId
new_msg_userid = msg.message.to_userid
chats = getInSession('chats')
if chats is undefined
initChats = [
userId: "PUBLIC_CHAT"
gotMail: false
number: 0;
]
setInSession 'chats', initChats
#insert the unique entries in the collection
for u in uniqueArray
chats = getInSession('chats')
if chats.filter((chat) -> chat.userId == u.userId).length is 0 and u.userId is new_msg_userid
chats.push {userId: u.userId, gotMail: false}
chats.push {userId: u.userId, gotMail: false, number: 0}
setInSession 'chats', chats
@toggleShield = ->
@ -382,9 +391,11 @@ Handlebars.registerHelper 'whiteboardSize', (section) ->
setInSession "display_chatbar", true
setInSession "display_whiteboard", true
setInSession "display_chatPane", true
setInSession "inChatWith", 'PUBLIC_CHAT'
#if it is a desktop version of the client
if isPortraitMobile() or isLandscapeMobile()
setInSession "messageFontSize", Meteor.config.app.mobileFont
#if this is a mobile version of the client
else
setInSession "messageFontSize", Meteor.config.app.desktopFont
setInSession 'display_slidingMenu', false
@ -394,13 +405,33 @@ Handlebars.registerHelper 'whiteboardSize', (section) ->
else
setInSession 'display_usersList', false
setInSession 'display_menu', false
#keep notifications and an opened private chat tab if page was refreshed
#reset to default if that's a new user
if loginOrRefresh()
initChats = [
userId: "PUBLIC_CHAT"
gotMail: false
number: 0
]
setInSession 'chats', initChats
setInSession "inChatWith", 'PUBLIC_CHAT'
TimeSync.loggingEnabled = false # suppresses the log messages from timesync
#true if it is a new user, false if the client was just refreshed
@loginOrRefresh = ->
userId = getInSession 'userId'
checkId = getInSession 'checkId'
if checkId is undefined
setInSession 'checkId', userId
return true
else if userId isnt checkId
setInSession 'checkId', userId
return true
else
return false
@onLoadComplete = ->
document.title = "BigBlueButton #{BBB.getMeetingName() ? 'HTML5'}"
setDefaultSettings()

View File

@ -1,5 +1,5 @@
<template name="header">
<nav id="navbar" class="myNavbar gradientBar top-bar" role="navigation">
<nav id="navbar" class="myNavbar top-bar" role="navigation">
{{> makeButton btn_class="btn toggleUserlistButton navbarButton sl-hamburger sl-ham-la-cw sl-portrait-mobile sl-portrait-keyboard" rel="tooltip" title="Toggle Userlist" span=true notification="all_chats"}}
{{#if amIInAudio}}

View File

@ -11,9 +11,21 @@
height: 45px;
min-height: 45px;
.btn {
&:hover {
color: #3896D3;
background-color:white;
border-bottom: 1px solid #E5E5E5;
}
&:focus {
background-color:white;
border-bottom: 1px solid #E5E5E5;
}
padding: 0.625rem 0.5rem 0.6875rem 0.5rem;
background-color: inherit;
margin: 0;
height: 45px;
outline: none;
min-width: 50px;
}
span {
position: relative;
@ -29,10 +41,26 @@
}
}
.privateChatName {
width: calc(~'100% - 105px');
min-width: 101px;
text-align: right;
float: right;
padding: 0.65rem 1.25rem 0.6rem 0.3rem;
font-family: "Helvetica Neue",Helvetica,Roboto,Arial,sans-serif;
font-size: 18px;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
}
.toPublic .unreadChatNumber {
@media @desktop-portrait, @landscape {
padding: 2px;
position: absolute;
top: 31%;
left: 100%;
margin: 0;
}
}
@ -175,16 +203,18 @@
#sendMessageButton {
width: 20%; /* 75% for the message input, 5% margin between the two */
color: extract(@black, 1);
background-color: extract(@white, 1);
background-color: #3896D3;
font-weight: bold;
height: 50px;
margin: 0px;
border: 1px solid extract(@lightGrey, 3);
@media @desktop-portrait {
width: 20%; /* 75% for the message input, 5% margin between the two */
font-size: 30px;
height: 60px;
&:hover {
background: #3A82D4;
}
}
@media @mobile-portrait {
width: 15vw;
@ -199,6 +229,9 @@
@media @landscape {
height: 50px;
padding: 0px;
&:hover {
background: #3A82D4;
}
}
}

View File

@ -38,15 +38,18 @@ body {
display: none;
}
}
.navbarButton .unreadChat {
.navbarButton {
color: #469DCF;
.unreadChat {
position: absolute;
z-index: 1;
background:red;
border-radius:50%;
border-radius:80%;
@media @desktop-portrait, @landscape {
top: 20%;
left: 65%;
width:20%;
width:19%;
height:20%;
}
@media @mobile-portrait {
@ -55,22 +58,17 @@ body {
width:25%;
height:25%;
}
}
.toPublic .unreadChat {
@media @desktop-portrait, @landscape {
position: absolute;
top: 39%;
left: 84%;
width:10px;
height:10px;
border-radius:5px;
background:red;
}
}
.myNavbar {
border-bottom: 0px;
&.gradientBar {
border-bottom: 1px;
@media @desktop-portrait, @landscape {
background-color: white;
border-bottom: 1px solid extract(@lightGrey, 1);
}
@media @mobile-portrait-with-keyboard, @mobile-portrait {
.linear-gradient(rgb(72,76,85), rgb(65,68,77));
}
.btn {
@ -80,13 +78,15 @@ body {
top: 0 !important;
padding-left: 1% !important;
padding-right: 1% !important;
background-color: white;
border-bottom: 1px solid extract(@lightGrey, 1);
}
@media @mobile-portrait-with-keyboard, @mobile-portrait {
height: 100px !important;
width: 10%;
min-width: 60px;
}
.linear-gradient(rgb(72,76,85), rgb(65,68,77));
}
.push-menu-icon {
.icon-bar {
margin-left: auto;
@ -106,7 +106,7 @@ body {
&.toggleUserlistButton, &.toggleMenuButton {
background: transparent;
}
span { background-color: white; }
span { background-color: #469DCF; }
}
@media @landscape {
min-width: 768px;
@ -122,17 +122,18 @@ body {
}
.navbarTitle {
color: extract(@white, 1);
font-weight: bold;
text-align: center;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
@media @landscape {
color: extract(@darkGrey, 1);
font-size: 16px;
width: 30% !important;
}
@media @mobile-portrait-with-keyboard, @mobile-portrait {
color: extract(@white, 1);
font-size: 30px;
padding-top: 30px;
padding-left: 5px;
@ -142,6 +143,7 @@ body {
margin-right: auto;
}
@media @desktop-portrait {
color: extract(@darkGrey, 1);
font-size: 16px;
width: calc(~'100% - 102.4px');
}
@ -176,30 +178,32 @@ body {
}
.meetingTitle {
text-align: center;
font-weight: bold;
line-height: 2em;
margin: 0;
@media @mobile-portrait, @mobile-portrait-with-keyboard, @desktop-portrait {
@media @mobile-portrait, @mobile-portrait-with-keyboard {
.linear-gradient(rgb(72,76,85), rgb(65,68,77));
padding-left: 140px;
padding-top: 20px;
color: white;
font-size: 4vw;
height: 110px;
}
@media @desktop-portrait {
.linear-gradient(rgb(72,76,85), rgb(65,68,77));
padding-top: 10px;
color: white;
}
@media @landscape {
border-bottom: 1px solid extract(@lightGrey, 1);
color: extract(@darkGrey, 1);
padding-bottom: 5px;
padding-left: 10px;
padding-top: 5px;
}
@media @desktop-portrait, @landscape {
font-size: 18px;
height: 50px;
}
@media @mobile-portrait, @mobile-portrait-with-keyboard {
font-size: 4vw;
height: 110px;
}
}
#container {
@ -338,6 +342,12 @@ body {
.signOutIcon {
@media @landscape {
&:hover {
color: #2A5E7C;
}
&:focus {
color: #2A5E7C;
}
height: 28px;
width: 75px;
margin-left: 10px;
@ -370,6 +380,12 @@ body {
.settingsIcon {
@media @landscape {
&:hover {
color: #2A5E7C;
}
&:focus {
color: #2A5E7C;
}
width: 57px;
margin-right: 5px;
}

View File

@ -1,12 +1,32 @@
@import "variables";
@import "mixins";
.usericon {
font-size: 16px;
.statusIcon {
font-size: 18px;
}
#usericons {
text-align: right;
color: white;
span i {
@media @landscape, @desktop-portrait {
margin-right: 10px;
font-size: 20px;
}
}
}
.unreadChatNumber {
@media @landscape, @desktop-portrait{
float: left;
margin-top: 5px;
width: 28px;
height: 18px;
border-radius: 41%;
font-size: 12px;
color: #fff;
text-align: center;
background: #3896D3;
}
}
.usernameEntry {
@ -16,13 +36,13 @@
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
width: 60%;
width: calc(~'100% - 130px');
@media @landscape {
height: 20px;
height: 27px;
font-size: 4.5mm;
}
@media @desktop-portrait {
height: 25px;
height: 27px;
font-size: 4.5mm;
}
@media @mobile-portrait, @mobile-portrait-with-keyboard {
@ -36,7 +56,6 @@
border-left: 0px;
border-top: 0px;
border-top-right-radius: 0px;
background-color: #FAFAFA;
}
@media @mobile-portrait-with-keyboard, @desktop-portrait, @mobile-portrait {
width: 100%;
@ -64,14 +83,17 @@
}
#user-contents {
height: 83vh; /* for the inside scrolling list to utilize as much room as possible, this surrounding window must also take up as much room as possible */
height: calc(~'100% - 50px'); /* user-contents = user-contens - meetingTitle */
@media @landscape, @desktop-portrait{
background-color: #34495E;
}
.userlist {
height: calc(~'100% - 29px'); /* height of user contents - user list */
max-height: 100% !important;
height: 100%;
#content:hover {
@media @landscape, @desktop-portrait {
background-color: #EEEEEE;
background-color: #2C4155;
}
}
#content {
@ -133,10 +155,17 @@
content: "\f461";
}
#content > .ion-ios-email-outline {
color: red;
.userName {
color: #E6E6E6;
line-height: 1.5;
}
.userName {
color: #666666;
.status {
float: left;
width: 15px;
min-width: 15px;
height: 27px;
margin-right: 10px;
font-size: 18px;
color: #FFFFFF;
}

View File

@ -7,6 +7,8 @@
border-top: 0px;
border-left: 0px;
border-right: 0px;
border-top-left-radius: 0;
border-top-right-radius: 0;
-webkit-order: 2;
order: 2;
-webkit-flex: 7 7 70%;
@ -126,6 +128,7 @@
}
.switchSlideButton {
outline: none;
width: 50px;
height: 100%;
margin-bottom: 0;
@ -200,11 +203,12 @@
margin-bottom: 0;
padding: 0;
border-radius: 50%;
background: rgba(0, 0, 0, 0.2);
background: #3896D3;
&:hover {
background: rgba(0, 0, 0, 0.4);
background: #3A82D4;
}
&:focus {
background: #3896D3;
outline:0;
}
i {

View File

@ -28,7 +28,9 @@
destinationTab = findDestinationTab()
if destinationTab isnt getInSession "inChatWith"
setInSession 'chats', getInSession('chats').map((tab) ->
tab.gotMail = true if tab.userId is destinationTab
if tab.userId is destinationTab
tab.gotMail = true
tab.number++
tab
)
comp.stop()
@ -127,7 +129,9 @@ Template.chatbar.events
'click .toPublic': (event) ->
setInSession 'inChatWith', 'PUBLIC_CHAT'
setInSession 'chats', getInSession('chats').map((chat) ->
chat.gotMail = false if chat.userId is "PUBLIC_CHAT"
if chat.userId is "PUBLIC_CHAT"
chat.gotMail = false
chat.number = 0
chat
)

View File

@ -23,7 +23,7 @@
<template name="privateChatTab">
<div class="privateChatTab">
{{> makeButton id="close" btn_class="secondary tiny round toPublic " i_class="ion-ios-arrow-left" rel="tooltip"
{{> makeButton id="close" btn_class="secondary tiny toPublic " i_class="ion-ios-arrow-left" rel="tooltip"
data_placement="bottom" title="Back to public" label="Public" notification="PUBLIC_CHAT"}}
<div class="privateChatName">
{{privateChatName}}

View File

@ -1,18 +1,33 @@
Template.makeButton.helpers
hasGotUnreadMail: (userId) ->
chats = getInSession('chats') if getInSession('chats') isnt undefined
flag = false
chats = getInSession('chats')
if chats isnt undefined
if userId is "all_chats"
chats.map((tabs) ->
flag = true if tabs.gotMail is true
tabs
)
for tabs in chats
if tabs.gotMail is true
return true
else if userId is "PUBLIC_CHAT"
chats.map((tabs) ->
flag = true if tabs.userId is userId and tabs.gotMail is true
tabs
)
if flag
return "gotUnreadMail"
for tabs in chats
if tabs.userId is userId and tabs.gotMail is true
return true
return false
getNumberOfUnreadMessages: (userId) ->
if userId is "all_chats"
return
else
return ""
chats = getInSession('chats')
if chats isnt undefined
for chat in chats
if chat.userId is userId and chat.gotMail
if chat.number > 9
return "9+"
else
return chat.number
return
getNotificationClass: (userId) ->
if userId is "all_chats"
return "unreadChat"
if userId is "PUBLIC_CHAT"
return "unreadChatNumber"

View File

@ -2,7 +2,7 @@
<button type="submit" id="{{id}}" class="btn {{btn_class}}" {{isDisabled}} rel="{{rel}}" data-placement="{{data_placement}}" title="{{title}}" style="{{style}}">
{{#if notification}}
{{#if hasGotUnreadMail notification }}
<div class="unreadChat"></div>
<div class="{{getNotificationClass notification}}">{{getNumberOfUnreadMessages notification}}</div>
{{/if}}
{{/if}}
{{#if i_class}}

View File

@ -39,28 +39,36 @@ Template.usernameEntry.events
'click .gotUnreadMail': (event) ->
_this = @
setInSession 'chats', getInSession('chats').map((chat) ->
chat.gotMail = false if chat.userId is _this.userId
chat
)
'click .gotUnreadPublic': (event) ->
setInSession 'chats', getInSession('chats').map((chat) ->
chat.gotMail = false if chat.userId is 'PUBLIC_CHAT'
chat
)
currentId = getInSession('userId')
if currentId isnt undefined and currentId is _this.userId
_id = "PUBLIC_CHAT"
else
_id = _this.userId
chats = getInSession('chats')
if chats isnt undefined
for chat in chats
if chat.userId is _id
chat.gotMail = false
chat.number = 0
break
setInSession 'chats', chats
Template.usernameEntry.helpers
hasGotUnreadMailClass: (userId) ->
chats = getInSession('chats') if getInSession('chats') isnt undefined
flag = false
chats.map((tab) ->
if tab.userId is userId
if tab.gotMail
flag = true
tab
)
if flag
return "gotUnreadMail"
chats = getInSession('chats')
if chats isnt undefined
for chat in chats
if chat.userId is userId and chat.gotMail
return true
return false
getNumberOfUnreadMessages: (userId) ->
chats = getInSession('chats')
if chats isnt undefined
for chat in chats
if chat.userId is userId and chat.gotMail
if chat.number > 9
return "9+"
else
return ""
return chat.number
return

View File

@ -54,37 +54,49 @@
<i class="icon fi-lock usericon"></i>
</span>
{{/if}}
</template>
<template name="usernameEntry">
<div class="status">
{{#if user.raise_hand}}
{{#if isCurrentUser userId}}
<span rel="tooltip" data-placement="bottom" title="Lower your hand">
<i class="icon ion-android-hand statusIcon"></i>
</span>
{{else}}
<span rel="tooltip" data-placement="bottom" title="{{user.name}} has raised their hand">
<i class="icon ion-android-hand statusIcon"></i>
</span>
{{/if}}
{{else}}
{{#if user.presenter}}
<span rel="tooltip" data-placement="bottom" title="{{user.name}} is the presenter">
<i class="icon fi-projection-screen usericon"></i>
<i class="icon fi-projection-screen statusIcon"></i>
</span>
{{else}}
{{#if equals user.role "MODERATOR"}}
<span rel="tooltip" data-placement="bottom" title="{{user.name}} is a moderator">
<i class="icon fi-torso usericon"></i>
<i class="icon fi-torso statusIcon"></i>
</span>
{{/if}}
{{/if}}
{{#if user.raise_hand}}
{{#if isCurrentUser userId}}
<span class="ion-android-hand usericon" rel="tooltip" data-placement="bottom" title="Lower your hand"></span>
{{else}}
<span class="ion-android-hand usericon" rel="tooltip" data-placement="bottom" title="{{user.name}} has raised their hand"></span>
{{/if}}
{{/if}}
</template>
</div>
<template name="usernameEntry">
{{#if isCurrentUser userId}}
<span class="userCurrent usernameEntry {{#if hasGotUnreadMailClass 'PUBLIC_CHAT' }} ion-ios-email-outline gotUnreadPublic{{/if}}" rel="tooltip" data-placement="bottom" title="{{user.name}} (you)">
<span class="userCurrent usernameEntry {{#if hasGotUnreadMailClass 'PUBLIC_CHAT'}}gotUnreadMail{{/if}}" rel="tooltip" data-placement="bottom" title="{{user.name}} (you)">
<span class="userName">{{user.name}} {{#if user.presenter}} (presenter) {{/if}} (you)</span>
</span>
{{#if hasGotUnreadMailClass 'PUBLIC_CHAT' }}
<div class="unreadChatNumber">{{getNumberOfUnreadMessages 'PUBLIC_CHAT'}}</div>
{{/if}}
{{else}}
<span class="usernameEntry {{#if hasGotUnreadMailClass user.userid }} ion-ios-email-outline gotUnreadMail{{/if}}" rel="tooltip" data-placement="bottom" title="{{user.name}}">
<span class="usernameEntry {{#if hasGotUnreadMailClass user.userid}}gotUnreadMail{{/if}}" rel="tooltip" data-placement="bottom" title="{{user.name}}">
<span class="userName"> {{user.name}} {{#if user.presenter}} (presenter) {{/if}}</span>
</span>
{{#if hasGotUnreadMailClass user.userid }}
<div class="unreadChatNumber">{{getNumberOfUnreadMessages user.userid}}</div>
{{/if}}
{{/if}}
</template>

View File

@ -1,5 +1,5 @@
<template name="whiteboard">
<div id="{{id}}" {{visibility name}} class="component gradientBar">
<div id="{{id}}" {{visibility name}} class="component">
{{#each getCurrentSlide}}
{{> slide}}
{{/each}}