//////////////////////////////////////////
//           ajaximrpg 5.00             //
//       AJAX Instant Messenger         //
//  Copyright (c) 2006-2008, 2010-2012  //
//      Do not remove this notice       //
//////////////////////////////////////////

/**
 * AjaxIM Class
 *
 * @author Joshua Gross
 **/
var AjaxIM = {
   /**
    * Sends a message to the server
    *
    * @arguments
    *   sender - who sent the message
    *   room - the room where the message will appear
    *   message - the message or command
    *
    * @author Joshua Gross
    **/
   sendMessage: function(sender, room, message) {
      // var s = document.createElement('script');
      // s.src = 'plugins/ajaximrpg/bsheet/bsheet.js?' + (new Date()).getTime();
      // s.type = 'text/javascript';
      // document.getElementsByTagName('head').item(0).appendChild(s);

      // find the plugins that have message() functions
      var plugins_a = makeArray(plugins);
      var plugins_idx = meetsCondition(plugins_a, function(arr, i) {
         return (typeof arr[i].message) == 'function';
      });
      plugins_a = makeValueArray(plugins_a, plugins_idx);

      // the default message handler
      var nextHandler = function() {
         if (message.indexOf('/share ') == 0) {
            if (sender == user) {
               var encodedLink = message;
               encodedLink = encodedLink.replace('+', '%2B');
               encodedLink = encodeURIComponent(encodedLink);
      
               var xhConn = new XHConn();
               xhConn.connect(pingTo, "POST", "call=share&to="+encodeURIComponent(room)+"&message="+encodedLink, function(xh) {
                  if (xh.outputText.substring(0, 7) == 'shared:') {
                     var parts = xh.outputText.substring(7).split(' ');
                     var href = parts[1];
                     var text = 'Link';
                     if (parts.length > 2) {
                        text = parts[2];
                        for (var p=3; p < parts.length; ++p) {
                           text += ' ' + parts[p];
                        }
                     }
                     var link = '<a href="'+href+'" target="_blank">'+text+'</a>';
                     $(Chatroom.windows[room].getId() + '_tree').tree.tree[0].insert(-1, link);
                  }
               });
            } else {
               var parts = message.split(' ');
               var href = parts[1];
               var text = 'Link';
               if (parts.length > 2) {
                  text = parts[2];
                  for (var p=3; p < parts.length; ++p) {
                     text += ' ' + parts[p];
                  }
               }
               var link = '<a href="'+href+'" target="_blank">'+text+'</a>';
               $(Chatroom.windows[room].getId() + '_tree').tree.tree[0].insert(-1, link);
            }
            return;
         }

         if (message.indexOf('/name ') == 0) {
            System.changeAlias(room, message.substring(6));
            return;
         }

         if ((message == '/?') || (message == '/help')) {
            var alias = getAlias(user, room);

            this.appendText(room, getHelpMessage(alias));
            return;
         }

         var encodedMessage = message;
         encodedMessage = encodedMessage.replace('+', '%2B');
         encodedMessage = encodeURIComponent(encodedMessage);

         var xhConn = new XHConn();
         xhConn.connect(pingTo, "POST", "call=send&to="+encodeURIComponent(room)+"&message="+encodedMessage, function(xh) {
            var error = '';
            var alias = getAlias(user, room);
            message = alias + ': ' + message + '<br />';
            if (xh.outputText.substring(0, 5) == 'sent:') {
               message = xh.outputText.substring(5);
               respText = 'sent';
            }

            switch(xh.outputText) {
               case 'sent_offline':
                  error = Languages.get('notifySentButOffline');
                  break;

               case 'not_online':
                  error = Languages.get('errorNotLoggedIn');
                  break;

               case 'too_long':
                  error = Languages.get('errorMsgTooLong');
                  break;

               case 'not_logged_in':
                  if (typeof System != 'undefined') {
                     System.logout();
                  } else {
                     self.opener.System.logout();
                  }
                  break;

               default:
                  break;
            }
            
            if (xh.errorText != '') {
               error += ((error != '')? '<br />':'') + xh.errorText;
            }

            Chatroom.windows[room].sendResult(message, error);
         });

         if (audioNotify) {
            soundManager.play('msg_out');
         }
      };

      // give the message to the plugins first, then the default handler
      for (var i=plugins_a.length-1; i >= 0; i--) {
         nextHandler = function(plugin, nextHandler) {
            return function() {
               plugin.message(sender, room, message, nextHandler);
            };
         }(plugins_a[i], nextHandler);
      }
      nextHandler();
   },

   /**
    * Adds text to this user's window (only).
    *
    * @arguments
    *   str - the text to add
    **/
   appendText: function(username, str) {
      var winId = Chatroom.windows[username].getId();
      var rcvdBox = $(winId + '_rcvd');

      rcvdBox.innerHTML += str;
      scrollToBottom(winId + '_rcvd');
   },

   /**
    * Replaces emotes with images
    *
    * @arguments
    *   str - the message to run replaces on
    *   itemsList - array of emotes
    **/
   emoteReplace: function(str, itemsList) {
      var r;
      for(var s in itemsList) {
         if (str.indexOf(s) > -1)
            str = str.replace(new RegExp(regExpEscape(s), 'g'), '<img src="themes/' + theme + '/emoticons/' + itemsList[s] + '" alt="' + itemsList[s] + '" title="' + s + '" />');
      }
      return str;
   },

   /**
    * @author Joshua Gross
    **/
   handleMinimize: function(eventName, win) {
      if (win.getId().indexOf('_im') == -1) return;
      
      var curIM = $(win.getId() + '_rcvd');
      curIM.scrollTop = curIM.scrollHeight - curIM.clientHeight + 6;
   },

   /**
    * Create a timestamp to use in a chat window based off the
    * configuration variable 'timestamp'
    *
    * @author Joshua Gross
    **/
   createTimestamp: function() {
      Stamp = new Date();
      var tH = String(Stamp.getHours()); var ti = String(Stamp.getMinutes()); var ts = String(Stamp.getSeconds());
      var th = tH > 12 ? tH - 12 : tH; var ta = tH > 12 ? 'pm' : 'am'; var tA = tH > 12 ? 'PM' : 'AM';
      var td = String(Stamp.getDate()); var tm = String(Stamp.getMonth() + 1);
      var tM = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'July', 'Aug', 'Sep', 'Nov', 'Dec'][tm - 1];
      var tY = String(Stamp.getFullYear()); var ty = tY.substring(2);
      
      tu = tm; tx = td; tQ = tH;
      
      tH = (tH.length > 1) ? tH : "0"+tH; ti = (ti.length > 1) ? ti : "0"+ti;
      tq = (th.length > 1) ? th : "0"+th; ts = (ts.length > 1) ? ts : "0"+ts;
      td = (td.length > 1) ? td : "0"+td; tm = (tm.length > 1) ? tm : "0"+tm;
      if (typeof timestamp == 'undefined') {
         timestamp = self.opener.timestamp;
      }
      return timestamp.replace(/H/, tH).replace(/h/, th).replace(/i/, ti).replace(/s/, ts)
                          .replace(/d/, td).replace(/Y/, tY).replace(/y/, ty).replace(/m/, tm)
                          .replace(/u/, tu).replace(/x/, tx).replace(/Q/, tQ).replace(/q/, tq)
                          .replace(/a/, ta).replace(/A/, tA).replace(/M/, tM);
   },

   /**
    * Add effects to a buddy icon.
    *
    * @arguments
    *   el - buddy icon element
    *
    * @author Benjamin Hutchins
    **/
   buddyIconHover: function(el) {
      /*var clone = new Element('img', {
      'src': $(el).src,
      //   'id': $(el).id + '_clone',
      //   'class': 'buddyIconClone',
       //  'alt': '' // valid XHTML
      }).insert(Element.getOffsetParent(el), 'content'); //.setStyle({'position': 'absolute', 'top': el.offsetTop, 'left': el.offsetLeft});
      //clonePosition(clone, el, {setLeft:true, setTop:true});*/
   },

   /**
    * Restore effects set by IM.buddyIconHover back to 'Normal'
    *
    * @arguments
    *   el - buddy icon element
    *
    * @author Benjamin Hutchins
    **/
   buddyIconNormal: function(el) {
      if ($(el.id + '_clone')) {
         $(el.id + '_clone').remove();
      }
   },

   /**
    * Proccess the leaving of a chatroom
    *
    * @arguments
    *   room - room name the user is leaving
    *
    * @author Joshua Gross
    **/
   getRoomName: function(username) {
      var users = [user, username];
      users.sort();
      return 'im_' + users[0] + '_' + users[1];
   }

};


/**
 * A class to mantain an IM Window's guts.
 *
 * @author Joshua Gross
 **/
var AjaxIMWindow = Class.create();
Object.extend(AjaxIMWindow.prototype, Window.prototype);
Object.extend(AjaxIMWindow.prototype, {
   send: function() {
      // do nothing here.
   },

   /**
    * After a message is sent to the server via IM.sendMessage(),
    * this function is ran to append the message to the user's window
    *
    * @arguments
    *   message - the message to send
    *   isBold - (bool) is the message bolded
    *   isItalic - (bool) is the message italicized
    *   isUnderline - (bool) is the message underlined
    *   fontName - font family for the message
    *   fontSize - font size for the message
    *   fontColor - font color for the message
    *
    * @author Joshua Gross
    * @update Benjamin Hutchins
    **/
   sendResult: function(message, result) {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
      var rcvdBox = $(winId + '_rcvd');
      var alias = getAlias(user, this.room);

      if (trim(message).length > 0) {
//         message = message.replace(/<br\/>/g, '\n').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/<([^>]+)>/ig, '').replace(/\n/g, '<br/>').replace(/(\s|\n|>|^)(\w+:\/\/[^<\s\n]+)/, '$1<a href="$2" target="_blank">$2</a>');
         message = IM.emoteReplace(message, smilies);
         rcvdBox.innerHTML += message;
      }

      if ((result != '') && (result != null)) {
         rcvdBox.innerHTML = rcvdBox.innerHTML + '<span class="imError">' + result + '</span><br>';
      }

      scrollToBottom(winId + '_rcvd');
   },

   /**
    * @author Joshua Gross
    **/
   toggleBold: function() {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
         
      sendBox.hide(); // horrah weird Opera 9 input refresh!
      if (sendBox.style.fontWeight == '400') {
         $(winId + '_bold').src = 'themes/' + theme + '/window/bold_on.png';
         sendBox.setStyle({fontWeight: '700'});
      } else {
         sendBox.setStyle({fontWeight: '400'});
         $(winId + '_bold').src = 'themes/' + theme + '/window/bold_off.png';
      }
      sendBox.show(); // horrah weird Opera 9 input refresh!
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
   },

   /**
    * @author Joshua Gross
    **/
   toggleItalic: function() {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
      
      sendBox.hide(); // horrah weird Opera 9 input refresh!

      if (sendBox.style.fontStyle == 'normal') {
         sendBox.setStyle({fontStyle: 'italic'});
         $(winId + '_italic').src = 'themes/' + theme + '/window/italic_on.png';
      } else {
         sendBox.setStyle({fontStyle: 'normal'});
         $(winId + '_italic').src = 'themes/' + theme + '/window/italic_off.png';
      }
      sendBox.show(); // horrah weird Opera 9 input refresh!
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
   },

   /**
    * @author Joshua Gross
    **/
   toggleUnderline: function() {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
      
      sendBox.hide(); // horrah weird Opera 9 input refresh!

      if (sendBox.style.textDecoration == 'none') {
         sendBox.setStyle({textDecoration: 'underline'});
         $(winId + '_underline').src = 'themes/' + theme + '/window/underline_on.png';
      } else {
         sendBox.setStyle({textDecoration: 'none'});
         $(winId + '_underline').src = 'themes/' + theme + '/window/underline_off.png';
      }
      sendBox.show(); // horrah weird Opera 9 input refresh!
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
   },

   /**
    * @author Joshua Gross
    **/
   toggleFontList: function() {
      var fL = $('fontsList');
      var fLBtn = $(this.getId() + '_setFont');
      
      $('emoticonList', 'fontColorList', 'fontSizeList').invoke('hide');

      if ($('fontsList').style.display == 'block') {
         fL.hide();
      } else {
         fL.setStyle({left:    Position.cumulativeOffset(fLBtn)[0] + 'px',
                      top:     (Position.cumulativeOffset(fLBtn)[1] + Element.getHeight(fLBtn) - 1) + 'px',
                      zIndex:  Windows.maxZIndex + 20,
                      display: 'block'});
                      
         IM.active = this;
      }
   },

   /**
    * @author Joshua Gross
    **/
   toggleFontSizeList: function() {
      var fsL = $('fontSizeList');
      var fsLBtn = $(this.getId() + '_setFontSize');
      
      $('emoticonList', 'fontsList', 'fontColorList').invoke('hide');

      if ($('fontSizeList').style.display == 'block') {
         $('fontSizeList').setStyle({display: 'none'});
      } else {
         fsL.setStyle({left:    Position.cumulativeOffset(fsLBtn)[0] + 'px',
                       top:     (Position.cumulativeOffset(fsLBtn)[1] + Element.getHeight(fsLBtn) - 1) + 'px',
                       zIndex:  Windows.maxZIndex + 20,
                       display: 'block'});

       IM.active = this;
      }
   },

   /**
    * @author Joshua Gross
    **/
   toggleEmoticonList: function() {
      var eL = $('emoticonList');
      var eLBtn = $(this.getId() + '_insertEmoticon');
      
      $('fontsList', 'fontSizeList', 'fontColorList').invoke('hide');

      if ($('emoticonList').style.display == 'block') {
         $('emoticonList').setStyle({display: 'none'});
      } else {
         eL.setStyle({left:    Position.cumulativeOffset(eLBtn)[0] + 'px',
                      top:     (Position.cumulativeOffset(eLBtn)[1] + Element.getHeight(eLBtn) - 1) + 'px',
                      zIndex:  Windows.maxZIndex + 20,
                      display: 'block'});

         IM.active = this;
      }
   },

   /**
    * @author Joshua Gross
    **/
   toggleFontColorList: function() {
      var fcL = $('fontColorList');
      var fcLBtn = $(this.getId() + '_setFontColor');
      
      $('fontsList', 'fontSizeList', 'emoticonList').invoke('hide');

      if ($('fontColorList').style.display == 'block') {
         $('fontColorList').setStyle({display: 'none'});
      } else {
         fcL.setStyle({left:    Position.cumulativeOffset(fcLBtn)[0] + 'px',
                       top:     (Position.cumulativeOffset(fcLBtn)[1] + Element.getHeight(fcLBtn) - 1) + 'px',
                       zIndex:  Windows.maxZIndex + 20,
                       display: 'block'});

         IM.active = this;
      }
   },

   /**
    * @author Joshua Gross
    **/
   setFont: function(fontname) {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');

      sendBox.hide();
      sendBox.setStyle({fontFamily: fontname + ', sans-serif'});
      sendBox.show();
      
      $(winId + '_setFont').innerHTML = fontname;
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
      this.toggleFontList('');
   },
   
   /**
    * @author Joshua Gross
    **/
   setFontSize: function(size) {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
      
      sendBox.hide();
      sendBox.setStyle({fontSize: size + 'px'});
      sendBox.show();
      
      $(winId + '_setFontSize').innerHTML = size;
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
      this.toggleFontSizeList('');
   },

   /**
    * @author Joshua Gross
    **/
   setFontColor: function(color) {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
      
      sendBox.setStyle({color: color});
      
      $(winId + '_setFontColorColor').setStyle({backgroundColor: color});
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
      this.toggleFontColorList('');
   },
   
   /**
    * Adds text to a windows' message box
    *
    * @author Joshua Gross
    **/
   insertText: function(tti) {
      var winId = this.getId();
      var sendBox = $(winId + '_sendBox');
      
      sendBox.value += tti;
      setTimeout("$('" + winId + "_sendBox').focus();", 125);
      this.toggleEmoticonList();
      return false;
   },

   /**
    * Checks for pressing on 'Return' or 'Enter'
    *
    * @author Joshua Gross
    * @update Benjamin Hutchins
    **/
   keyHandler: function(event) {
      event = event || window.event;
      var asc = document.all ? event.keyCode : event.which;
      var shift = event.shiftKey;

      if (useLingo) {
         var message = $(this.getId() + '_sendBox').value;
         if (trim(message).length > 0) {
            $(this.getId() + '_sendBox').value = Languages.lingoReplace(message, asc, shift);
         }
      }

      if (asc == 13 && !shift) {
         this.send();
         return false;
      }

      return true;
   },
   
   /**
    * Detaches an IM window to a new window
    *
    * @author Joshua Gross
    * @update Benjamin Hutchins
    **/
   detach: function() {
      var winId = this.getId();
      newWin = this.room;
      newWinRcvd = $(winId + '_rcvd').innerHTML;
      this.hide();
      this.popup = window.open('./popup.html', winId + '_im', 'left='+this.getLocation()['left']+',top='+this.getLocation()['top']+',width=320,height=335,toolbar=0,location=1,status=0,menubar=0,resizable=1,scrollbars=0');
      this.detached = true;
   }
});

