PM functionality!

This commit is contained in:
Guangcong Luo 2013-04-30 02:29:41 -07:00
parent 61f838cc7e
commit c7a13d5e76
4 changed files with 273 additions and 56 deletions

View File

@ -10,7 +10,7 @@
'click .username': 'clickUsername'
},
initialize: function() {
var buf = '<ul class="userlist" style="display:none"></ul><div class="chat-log"><div class="inner"></div><div class="inner-after"></div></div><div class="chat-log-add">Connecting...</div>';
var buf = '<ul class="userlist" style="display:none"></ul><div class="chat-log"><div class="inner"></div></div></div><div class="chat-log-add">Connecting...</div>';
this.$el.addClass('ps-room-light').html(buf);
this.$chatAdd = this.$('.chat-log-add');
@ -46,6 +46,7 @@
this.$chatFrame.removeClass('hasuserlist');
this.$chatAdd.removeClass('hasuserlist');
}
this.$chatFrame.scrollTop(this.$chat.height());
},
show: function() {
Room.prototype.show.apply(this, arguments);
@ -56,7 +57,7 @@
e.stopPropagation();
},
keyPress: function(e) {
if (e.keyCode === 13) { // Enter
if (e.keyCode === 13 && !e.shiftKey) { // Enter
e.preventDefault();
e.stopPropagation();
var text;
@ -126,6 +127,16 @@
$children.slice(0,100).remove();
}
},
addPM: function(user, message, pm) {
var autoscroll = false;
if (this.$chatFrame.scrollTop() + 60 >= this.$chat.height() - this.$chatFrame.height()) {
autoscroll = true;
}
this.addChat(user, message, pm);
if (autoscroll) {
this.$chatFrame.scrollTop(this.$chat.height());
}
},
addRow: function(line) {
var name, name2, room, action, silent, oldid;
if (typeof line === 'string') {
@ -378,7 +389,7 @@
}
var highlight = isHighlighted ? ' style="background-color:#FDA;"' : '';
var chatDiv = '<div class="chat"' + highlight + '>';
var timestamp = this.getTimestamp('lobby');
var timestamp = ChatRoom.getTimestamp('lobby');
if (name.substr(0, 1) !== ' ') clickableName = '<small>' + Tools.escapeHTML(name.substr(0, 1)) + '</small>'+clickableName;
if (pm) {
var pmuserid = toUserid(pm);
@ -426,6 +437,8 @@
}
return id.match(/^battle\-([a-z0-9]*[a-z])[0-9]*$/);
},
markUserActive: function() {}
}, {
getTimestamp: function(section) {
var pref = Tools.prefs('timestamps') || {};
var sectionPref = ((section === 'pms') ? pref.pms : pref.lobby) || 'off';
@ -438,8 +451,7 @@
return '[' + components.map(
function(x) { return (x < 10) ? '0' + x : x; }
).join(':') + '] ';
},
markUserActive: function() {}
}
});
// user list

View File

@ -1,33 +1,112 @@
(function($) {
var MainMenuRoom = this.MainMenuRoom = this.Room.extend({
// minWidth: 480,
// maxWidth: 480,
minWidth: 345,
bestWidth: 345,
tinyWidth: 340,
bestWidth: 628,
events: {
'click .button': 'clickButton'
'click .button': 'clickButton',
'keydown textarea': 'keyPress',
'click .username': 'clickUsername',
'click .closebutton': 'closePM'
},
initialize: function() {
// left menu
var buf = '<div class="leftmenu"><div class="mainmenu"><p><button class="button big" value="search"><strong>Look for a battle</strong></button></p></div>';
buf += '<div class="mainmenu"><p><button class="button" value="teambuilder">Teambuilder</button></p><p><button class="button" value="ladder">Ladder</button></p></div></div>';
var buf = '<div class="leftmenu"><div class="activitymenu"><div class="pmbox"></div></div>';
buf += '<div class="mainmenu"><div class="menugroup"><p><button class="button big" value="search"><strong>Look for a battle</strong></button></p></div>';
buf += '<div class="menugroup"><p><button class="button" value="teambuilder">Teambuilder</button></p><p><button class="button" value="ladder">Ladder</button></p></div></div></div>';
// right menu
buf += '<div class="rightmenu"><div class="mainmenu"><p><button class="button" value="lobby">Join lobby chat</button></p></div></div>';
buf += '<div class="rightmenu"><div class="menugroup"><p><button class="button" value="lobby">Join lobby chat</button></p></div></div>';
this.$el.html(buf);
this.$activityMenu = $('.activitymenu');
this.$pmBox = this.$activityMenu.find('.pmbox');
app.on('init:formats', this.updateSearch, this);
this.updateSearch();
},
addPM: function(name, message, target) {
//
var oName = name;
if (toId(name) === app.user.get('userid')) {
oName = target;
}
var $pmWindow = this.openPM(oName);
var $chatFrame = $pmWindow.find('.pm-log');
var $chat = $pmWindow.find('.inner');
if ($chatFrame.scrollTop() + 60 >= $chat.height() - $chatFrame.height()) {
autoscroll = true;
}
var timestamp = ChatRoom.getTimestamp('pms');
var color = hashColor(toId(name));
var clickableName = '<span style="cursor:pointer" class="username" data-name="' + Tools.escapeHTML(name) + '">' + Tools.escapeHTML(name.substr(1)) + '</span>';
if (name.substr(0, 1) !== ' ') clickableName = '<small>' + Tools.escapeHTML(name.substr(0, 1)) + '</small>'+clickableName;
$chat.append('<div class="chat">' + timestamp + '<strong style="' + color + '">' + clickableName + ':</strong> <em' + (target === oName ? ' class="mine"' : '') + '>' + messageSanitize(message) + '</em></div>');
if (autoscroll) {
$chatFrame.scrollTop($chat.height());
}
},
openPM: function(name) {
var userid = toId(name);
var $pmWindow = this.$pmBox.find('.pm-window-'+userid);
if (!$pmWindow.length) {
var buf = '<div class="pm-window pm-window-'+userid+'" data-userid="'+userid+'"><h3><button class="closebutton" href="'+app.root+'teambuilder"><i class="icon-remove-sign"></i></button>'+Tools.escapeHTML(name)+'</h3><div class="pm-log"><div class="inner"></div></div>';
buf += '<div class="pm-log-add"><form class="chatbox nolabel"><textarea class="textbox" type="text" size="70" autocomplete="off"></textarea></form></div></div>';
$pmWindow = $(buf).prependTo(this.$pmBox);
$pmWindow.find('textarea').autoResize({
animateDuration: 100,
extraSpace: 0
});
} else {
$pmWindow.show();
}
return $pmWindow;
},
closePM: function(e) {
var userid;
if (e.currentTarget) {
e.preventDefault();
e.stopPropagation();
userid = $(e.currentTarget).closest('.pm-window').data('userid');
} else {
userid = toId(e);
}
this.$pmBox.find('.pm-window-'+userid).hide();
},
focusPM: function(name) {
this.openPM(name).find('textarea').focus();
},
keyPress: function(e) {
if (e.keyCode === 13 && !e.shiftKey) { // Enter
var $target = $(e.currentTarget);
e.preventDefault();
e.stopPropagation();
var text;
if ((text = $target.val())) {
// this.tabComplete.reset();
// this.chatHistory.push(text);
var userid = $target.closest('.pm-window').data('userid');
text = ('\n'+text).replace(/\n/g, '\n/pm '+userid+', ').substr(1);
this.send(text);
$(e.currentTarget).val('');
}
} else if (e.keyCode === 27) { // Esc
this.closePM(e);
}
},
clickUsername: function(e) {
e.stopPropagation();
var name = $(e.currentTarget).data('name');
app.addPopup('user', UserPopup, {name: name, sourceEl: e.currentTarget});
},
updateSearch: function() {
if (window.BattleFormats) {
this.$('button.big').html('<strong>Look for a battle</strong>').removeClass('disabled');
this.$('.mainmenu button.big').html('<strong>Look for a battle</strong>').removeClass('disabled');
} else {
this.$('button.big').html('<em>Connecting...</em>').addClass('disabled');
this.$('.mainmenu button.big').html('<em>Connecting...</em>').addClass('disabled');
}
},
updateRightMenu: function() {
@ -41,6 +120,9 @@
e.preventDefault();
var $target = $(e.currentTarget);
switch ($target.val()) {
case 'search':
alert('we don\'t support battles yet :(');
break;
case 'lobby':
app.joinRoom('lobby');
break;

View File

@ -368,7 +368,7 @@
// the only case we're going to handle
self.rooms[''].addPM(message.name, message.message, message.pm);
if (self.rooms['lobby']) {
self.rooms['lobby'].addChat(message.name, message.message, message.pm);
self.rooms['lobby'].addPM(message.name, message.message, message.pm);
}
} else {
self.receive(message.message);
@ -550,6 +550,13 @@
this.dismissPopups();
if (!this.sideRoom) {
this.curRoom.show('full');
if (this.curRoom.id === '') {
if ($('body').width() < this.curRoom.bestWidth) {
this.curRoom.$el.addClass('tiny-layout');
} else {
this.curRoom.$el.removeClass('tiny-layout');
}
}
this.topbar.updateTabbar();
return;
}
@ -558,11 +565,11 @@
var available = $('body').width();
if (this.curRoom.isSideRoom) {
// we're trying to focus a side room
if (available >= this.rooms[''].minWidth + leftMin) {
if (available >= this.rooms[''].tinyWidth + leftMin) {
// it fits to the right of the main menu, so do that
this.curSideRoom = this.sideRoom = this.curRoom;
this.curRoom = this.rooms[''];
leftMin = (this.curRoom.minWidth || this.curRoom.bestWidth);
leftMin = this.curRoom.tinyWidth;
rightMin = (this.sideRoom.minWidth || this.sideRoom.bestWidth);
} else if (this.sideRoom) {
// nooo
@ -574,6 +581,8 @@
this.topbar.updateTabbar();
return;
}
} else if (this.curRoom.id === '') {
leftMin = this.curRoom.tinyWidth;
}
if (available < leftMin + rightMin) {
if (this.curSideRoom) {
@ -585,6 +594,21 @@
return;
}
this.curSideRoom = this.sideRoom;
if (leftMin === this.curRoom.tinyWidth) {
if (available < this.curRoom.bestWidth + 570) {
// there's only room for the tiny layout :(
rightWidth = available - leftMin;
this.curRoom.show('left', rightWidth);
this.curRoom.$el.addClass('tiny-layout');
this.curSideRoom.show('right', rightWidth);
this.topbar.updateTabbar();
return;
}
leftMin = (this.curRoom.minWidth || this.curRoom.bestWidth);
this.curRoom.$el.removeClass('tiny-layout');
}
var leftMax = (this.curRoom.maxWidth || this.curRoom.bestWidth);
var rightMax = (this.sideRoom.maxWidth || this.sideRoom.bestWidth);
var rightWidth = rightMin;
@ -825,7 +849,7 @@
// other than the popup will still be possible (and will dismiss
// the popup).
type: 'normal',
width: 260,
width: 270,
constructor: function(data) {
if (data && data.sourceEl) {
@ -893,7 +917,7 @@
buf += '<small>' + (group || '&nbsp;') + '</small><br />';
buf += '</div>';
buf += '<div class="buttonbar"><button value="challenge" disabled>Challenge</button> <button value="pm" disabled>PM</button> <button value="close">Close</close></div>';
buf += '<div class="buttonbar"><button value="challenge" disabled>Challenge</button> <button value="pm">PM</button> <button value="close">Close</close></div>';
this.$el.html(buf);
},
@ -903,6 +927,9 @@
case 'challenge':
break;
case 'pm':
this.close();
app.focusRoom('');
app.rooms[''].focusPM(this.data.name);
break;
case 'close':
this.close();

View File

@ -201,24 +201,28 @@ body {
display: inline-block;
margin: 0 0 0 -17px;
width: 17px;
padding: 0;
border: 0;
position: relative;
z-index: 11;
top: -14px;
text-decoration: none;
font-size: 14px;
color: #999999;
text-shadow: none;
}
.tabbar a.cur + .closebutton {
top: -15px;
}
.tabbar .closebutton:hover {
.closebutton {
text-decoration: none;
font-size: 14px;
color: #999999;
text-shadow: none;
border: 0;
padding: 0;
margin: 0;
background: transparent;
cursor: pointer;
}
.closebutton:hover {
color: #BB2222;
}
.tabbar .closebutton:active {
.closebutton:active {
color: #661111;
}
@ -262,35 +266,102 @@ body {
*********************************************************/
.leftmenu {
float: left;
padding: 40px 0 0 0;
width: 324px;
}
.rightmenu {
position: absolute;
top: 40px;
right: 25px;
}
.activitymenu {
position: absolute;
left: 325px;
top: 40px;
}
.pmbox {
width: 270px;
margin: 0 auto;
min-height: 2px;
}
.pm-window {
margin-bottom: 12px;
}
.pm-window h3 {
background: #f8f8f8;
color: #777777;
margin: 0;
padding: 2px 5px;
font-size: 11pt;
border: 1px solid #AAAAAA;
border-top-left-radius: 5px;
border-top-right-radius: 5px;
}
.pm-window h3 .closebutton {
float: right;
}
.pm-log {
min-height: 100px;
max-height: 300px;
background: rgba(242,247,250,.925);
color: black;
word-wrap: break-word;
border: 1px solid #AAAAAA;
border-top: 0;
border-bottom: 0;
overflow: auto;
-webkit-overflow-scrolling: touch;
overflow-scrolling: touch;
}
.pm-log-add {
border: 1px solid #AAAAAA;
border-bottom-left-radius: 5px;
border-bottom-right-radius: 5px;
background: rgba(242,247,250,.85);
}
.pm-window.collapsed .pm-log,
.pm-window.collapsed .pm-log-add {
display: none;
}
.tiny-layout .leftmenu,
.tiny-layout .rightmenu,
.tiny-layout .mainmenu,
.tiny-layout .activitymenu {
position: static;
top: 0;
right: 0;
left: 0;
margin: 0;
padding: 0;
}
.tiny-layout .activitymenu {
padding-top: 38px;
}
.mainmessage,
.mainmenu {
.menugroup {
display: block;
padding: 10px 15px;
margin: 40px 25px 0 40px;
max-width: 350px;
padding: 10px 0;
margin: 0 27px 40px 27px;
max-width: 400px;
border-radius: 20px;
background: rgba(201, 207, 219, .6);
color: black;
}
.mainmenu {
.menugroup {
background: rgba(201, 207, 219, .4);
width: 240px;
text-align: center;
}
.rightmenu .mainmenu {
margin-left: 0;
}
.mainmessage p,
.mainmenu p {
.menugroup p {
margin: 10px 0;
}
.mainmenu .button {
.menugroup .button {
box-sizing: border-box;
font-size: 12pt;
font-family: Verdana, Helvetica, Arial, sans-serif;
@ -321,12 +392,12 @@ body {
border-color: hsl(210,40%,40%);
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#f6f6f6', endColorstr='#e3e3e3');
}
.mainmenu button.big {
.menugroup button.big {
width: 230px;
padding: 7px 7px 5px 7px;
font-size: 14pt;
}
.mainmenu .button:hover {
.menugroup .button:hover {
background: #5485B6;
background: hsl(210,40%,52%);
background: -webkit-gradient(linear, left top, left bottom, from(hsl(210,40%,62%)), to(hsl(210,40%,42%)));
@ -334,7 +405,7 @@ body {
background: linear-gradient(top, hsl(210,40%,62%), hsl(210,40%,42%));
border-color: hsl(210,40%,21%);
}
.mainmenu .button:active {
.menugroup .button:active {
box-shadow: 0 1px 2px rgba(0,0,0,.2), inset 0 -1px 1px rgba(255,255,255,.3), inset 0 1px 1px rgba(0,0,0,.4);
background: #406B96;
background: hsl(210,40%,42%);
@ -343,9 +414,9 @@ body {
background: linear-gradient(top, hsl(210,40%,42%), hsl(210,40%,58%));
border-color: hsl(210,40%,21%);
}
.mainmenu .button.disabled,
.mainmenu .button.disabled:hover,
.mainmenu .button.disabled:active {
.menugroup .button.disabled,
.menugroup .button.disabled:hover,
.menugroup .button.disabled:active {
background: #EEEEEE;
border: 1px solid #CCCCCC;
color: #BBBBBB;
@ -353,6 +424,26 @@ body {
box-shadow: 0 1px 2px rgba(0,0,0,.1);
}
.rightmenu {
width: 294px;
}
.rightmenu .menugroup .button {
width: 180px;
}
@media (max-width:895px) {
.rightmenu {
position: static;
top: 0;
right: 0;
}
.rightmenu {
width: 324px;
}
.rightmenu .menugroup .button {
width: 200px;
}
}
/*********************************************************
* Ladder
*********************************************************/
@ -393,6 +484,8 @@ body {
bottom: 40px;
font-size: 10pt;
background: rgba(242,247,250,.5);
color: black;
word-wrap: break-word;
overflow: auto;
-webkit-overflow-scrolling: touch;
@ -408,15 +501,16 @@ body {
border-top: 1px solid #AAAAAA;
}
.chat-log .message,
.chat-log .chat {
.chat-log .chat,
.pm-log .chat {
padding: 4px 0 2px 0;
font-size: 8pt;
}
.chat-log .chat em {
.chat em {
padding: 0 4px 0 3px;
font-style: normal;
}
.chat-log .chat small {
.chat small {
font-weight: normal;
font-size: 8pt;
color: #888888;
@ -424,17 +518,19 @@ body {
.message-pm {
color: #007100;
}
.chat-log .inner {
padding: 4px 8px 0px 8px;
}
.chat-log .inner-after {
margin-top: 0.5em;
.chat-log .inner,
.pm-log .inner {
padding: 4px 8px 6px 8px;
}
.chatbox {
margin: 0 10px 0 80px;
padding: 5px 0 0 0;
}
.chatbox.nolabel {
margin: 0 14px 0 6px;
padding: 5px 0 5px 0;
}
.chatbox label {
float: left;
margin-left: -78px;