Merge commit '0.3.1-RC3' into message-recipient
[Sone.git] / src / main / resources / static / javascript / sone.js
index 133e1d4..75facb3 100644 (file)
@@ -63,12 +63,13 @@ function registerInputTextareaSwap(inputElement, defaultText, inputFieldName, op
  * @param element
  *            The element to add a “comment” link to
  */
-function addCommentLink(postId, element) {
+function addCommentLink(postId, element, insertAfterThisElement) {
        if ($(element).find(".show-reply-form").length > 0) {
                return;
        }
        commentElement = (function(postId) {
                var commentElement = $("<div><span>Comment</span></div>").addClass("show-reply-form").click(function() {
+                       markPostAsKnown(getPostElement(this));
                        replyElement = $("#sone .post#" + postId + " .create-reply");
                        replyElement.removeClass("hidden");
                        replyElement.removeClass("light");
@@ -85,9 +86,7 @@ function addCommentLink(postId, element) {
                });
                return commentElement;
        })(postId);
-       $(element).find(".status-line .time").each(function() {
-               $(this).after(commentElement.clone(true));
-       });
+       $(insertAfterThisElement).after(commentElement.clone(true));
 }
 
 var translations = {};
@@ -299,7 +298,7 @@ function getPostId(element) {
 }
 
 function getPostTime(element) {
-       return getPostElement(element).find(".storage-time").text();
+       return getPostElement(element).find(".post-time").text();
 }
 
 function getReplyElement(element) {
@@ -311,7 +310,7 @@ function getReplyId(element) {
 }
 
 function getReplyTime(element) {
-       return getReplyElement(element).find(".storage-time").text();
+       return getReplyElement(element).find(".reply-time").text();
 }
 
 function likePost(postId) {
@@ -453,11 +452,9 @@ function ajaxifyPost(postElement) {
                $(inputField).val("");
                postReply(postId, text, function(success, error, replyId) {
                        if (success) {
-                               getReply(replyId, function(soneId, soneName, replyTime, replyDisplayTime, text, html) {
-                                       newReply = $(html).insertBefore("#sone .post#" + postId + " .create-reply");
-                                       $("#sone .post#" + postId + " .create-reply").addClass("hidden");
-                                       ajaxifyReply(newReply);
-                               });
+                               loadNewReply(replyId);
+                               markPostAsKnown(getPostElement(inputField));
+                               $("#sone .post#" + postId + " .create-reply").addClass("hidden");
                        } else {
                                alert(error);
                        }
@@ -476,13 +473,18 @@ function ajaxifyPost(postElement) {
        /* convert all “like” buttons to javascript functions. */
        $(postElement).find(".like-post").submit(function() {
                likePost(getPostId(this));
+               markPostAsKnown(getPostElement(this));
                return false;
        });
        $(postElement).find(".unlike-post").submit(function() {
                unlikePost(getPostId(this));
+               markPostAsKnown(getPostElement(this));
                return false;
        });
 
+       /* add “comment” link. */
+       addCommentLink(getPostId(postElement), postElement, $(postElement).find(".post-status-line .time"));
+
        /* process all replies. */
        $(postElement).find(".reply").each(function() {
                ajaxifyReply(this);
@@ -492,12 +494,13 @@ function ajaxifyPost(postElement) {
        getTranslation("WebInterface.DefaultText.Reply", function(text) {
                $(postElement).find("input.reply-input").each(function() {
                        registerInputTextareaSwap(this, text, "text", false, false);
-                       addCommentLink(getPostId(postElement), postElement);
                });
        });
 
-       /* add “comment” link. */
-       addCommentLink(getPostId(postElement), postElement);
+       /* mark everything as known on click. */
+       $(postElement).click(function() {
+               markPostAsKnown(this);
+       });
 
        /* hide reply input field. */
        $(postElement).find(".create-reply").addClass("hidden");
@@ -512,10 +515,12 @@ function ajaxifyPost(postElement) {
 function ajaxifyReply(replyElement) {
        $(replyElement).find(".like-reply").submit(function() {
                likeReply(getReplyId(this));
+               markPostAsKnown(getPostElement(this));
                return false;
        });
        $(replyElement).find(".unlike-reply").submit(function() {
                unlikeReply(getReplyId(this));
+               markPostAsKnown(getPostElement(this));
                return false;
        });
        (function(replyElement) {
@@ -525,7 +530,12 @@ function ajaxifyReply(replyElement) {
                        });
                });
        })(replyElement);
-       addCommentLink(getPostId(replyElement), replyElement);
+       addCommentLink(getPostId(replyElement), replyElement, $(replyElement).find(".reply-status-line .time"));
+
+       /* mark post and all replies as known on click. */
+       $(replyElement).click(function() {
+               markPostAsKnown(getPostElement(replyElement));
+       });
 }
 
 /**
@@ -566,6 +576,7 @@ function getStatus() {
                                        $("#sone #notification-area").append(notification);
                                        notification.slideDown();
                                }
+                               setActivity();
                        });
                        $.each(data.removedNotifications, function(index, value) {
                                $("#sone #notification-area .notification#" + value.id).slideUp();
@@ -601,7 +612,7 @@ function loadNewPost(postId) {
        $.getJSON("ajax/getPost.ajax", { "post" : postId }, function(data, textStatus) {
                if ((data != null) && data.success) {
                        var firstOlderPost = null;
-                       $("#sone #posts .post").each(function() {
+                       $("#sone .post").each(function() {
                                if (getPostTime(this) < data.post.time) {
                                        firstOlderPost = $(this);
                                        return false;
@@ -611,10 +622,11 @@ function loadNewPost(postId) {
                        if (firstOlderPost != null) {
                                newPost.insertBefore(firstOlderPost);
                        } else {
-                               $("#sone #posts .post:last").after(newPost);
+                               $("#sone #posts").append(newPost);
                        }
                        ajaxifyPost(newPost);
                        newPost.slideDown();
+                       setActivity();
                }
        });
 }
@@ -626,25 +638,76 @@ function loadNewReply(replyId) {
        loadedReplies[replyId] = true;
        $.getJSON("ajax/getReply.ajax", { "reply": replyId }, function(data, textStatus) {
                /* find post. */
-               $("#sone #posts .post#" + data.reply.postId).each(function() {
-                       var firstNewerReply = null;
-                       $(this).find(".replies .reply").each(function() {
-                               if (getReplyTime(this) > data.reply.time) {
-                                       firstNewerReply = $(this);
-                                       return false;
+               if ((data != null) && data.success) {
+                       $("#sone .post#" + data.reply.postId).each(function() {
+                               var firstNewerReply = null;
+                               $(this).find(".replies .reply").each(function() {
+                                       if (getReplyTime(this) > data.reply.time) {
+                                               firstNewerReply = $(this);
+                                               return false;
+                                       }
+                               });
+                               newReply = $(data.reply.html).addClass("hidden");
+                               if (firstNewerReply != null) {
+                                       newReply.insertBefore(firstNewerReply);
+                               } else {
+                                       if ($(this).find(".replies .create-reply")) {
+                                               $(this).find(".replies .create-reply").before(newReply);
+                                       } else {
+                                               $(this).find(".replies").append(newReply);
+                                       }
                                }
+                               ajaxifyReply(newReply);
+                               newReply.slideDown();
+                               setActivity();
                        });
-                       newReply = $(data.reply.html);
-                       if (firstNewerReply != null) {
-                               newReply.insertAfter(firstNewerReply);
-                       } else {
-                               $(this).find(".replies .reply:last").after(newReply);
-                       }
-                       ajaxifyReply(newReply);
-               });
+               }
        });
 }
 
+function markPostAsKnown(postElements) {
+       $(postElements).each(function() {
+               postElement = this;
+               if ($(postElement).hasClass("new")) {
+                       (function(postElement) {
+                               $.getJSON("ajax/markPostAsKnown.ajax", {"formPassword": getFormPassword(), "post": getPostId(postElement)}, function(data, textStatus) {
+                                       $(postElement).removeClass("new");
+                               });
+                       })(postElement);
+               }
+       });
+       markReplyAsKnown($(postElements).find(".reply"));
+}
+
+function markReplyAsKnown(replyElements) {
+       $(replyElements).each(function() {
+               replyElement = this;
+               if ($(replyElement).hasClass("new")) {
+                       (function(replyElement) {
+                               $.getJSON("ajax/markReplyAsKnown.ajax", {"formPassword": getFormPassword(), "reply": getReplyId(replyElement)}, function(data, textStatus) {
+                                       $(replyElement).removeClass("new");
+                               });
+                       })(replyElement);
+               }
+       });
+}
+
+function resetActivity() {
+       title = document.title;
+       if (title.indexOf('(') == 0) {
+               document.title = title.substr(title.indexOf(' ') + 1);
+       }
+}
+
+function setActivity() {
+       if (!focus) {
+               title = document.title;
+               if (title.indexOf('(') != 0) {
+                       document.title = "(!) " + title;
+               }
+       }
+}
+
 /**
  * Creates a new notification.
  *
@@ -671,6 +734,8 @@ function createNotification(id, text, dismissable) {
 // EVERYTHING BELOW HERE IS EXECUTED AFTER LOADING THE PAGE
 //
 
+var focus = true;
+
 $(document).ready(function() {
 
        /* this initializes the status update input field. */
@@ -688,6 +753,21 @@ $(document).ready(function() {
                });
        });
 
+       /* ajaxify input field on “view Sone” page. */
+       getTranslation("WebInterface.DefaultText.Message", function(defaultText) {
+               registerInputTextareaSwap("#sone #post-message input[name=text]", defaultText, "text", false, false);
+               $("#sone #post-message").submit(function() {
+                       text = $(this).find(":input:enabled").val();
+                       $.getJSON("ajax/createPost.ajax", { "formPassword": getFormPassword(), "recipient": $("#sone #sone-id").text(), "text": text }, function(data, textStatus) {
+                               if ((data != null) && data.success) {
+                                       loadNewPost(data.postId);
+                               }
+                       });
+                       $(this).find(":input:enabled").val("").blur();
+                       return false;
+               });
+       });
+
        /* Ajaxifies all posts. */
        /* calling getTranslation here will cache the necessary values. */
        getTranslation("WebInterface.Confirmation.DeletePostButton", function(text) {
@@ -770,4 +850,13 @@ $(document).ready(function() {
 
        /* activate status polling. */
        setTimeout(getStatus, 5000);
+
+       /* reset activity counter when the page has focus. */
+       $(window).focus(function() {
+               focus = true;
+               resetActivity();
+       }).blur(function() {
+               focus = false;
+       })
+
 });