views:

117

answers:

2

Hello. So im making a "delete" button to my commentsystem.. I want to make it smart, so it should run a ajax call to remove the comment.

Now I have tried out myself, this and have gotten this far:

<?php
echo "<a href='#' onclick='javascript:DoCommentWallRemove()' title='ta bort inlägg'> <span class='removeWallComment'></span> </a>";
?>
<script type="text/javascript">
    function DoCommentWallRemove(){
      var wrapperId = '#profileWall';
        $.ajax({ 
           type: "POST",
           url: "misc/removeWallComment.php",
        data: {
        value: 'y',
        commentwallid : "<?php echo $displayWall['id']; ?>",
        BuID : "<?php echo $v['id']; ?>",
        uID : "<?php echo $showU['id']; ?>"
        },
           success: function(msg){
    alert(msg);
            }
         });
    }
</script>

Now as my comments shows in a while(), I have placed the JS function is right under the link, so it should grab the actual comment id, but instead it gives the same ID to every comment.

But when i do a normal php <?php echo $displayWall['id']; ?> it shows different comment ids like it should do in the javascript.

+1  A: 

Eww, that's just gross! You probably want something like this:

function removeComment(id, obj) {
    $.post('misc/removeWallComment.php', {id: id}, function(msg) {
        alert(msg); // or do some useful stuff,
                    // like remove the comment from the page
                    // with 'obj' you'll know which comment to remove :)
    });
}

And then just something like this for each comment:

<a href="#" onclick="removeComment(id, this); return false;">delete comment</a>
GuidoH
Wouldn't having `{id: id}` in the AJAX result in something like `{101: 101} when triggered by `removeContent(101, this);`?
Lucanos
Nope, works fine. Used it many times like that. Just paste `javascript:a=10;alert({a:a}.a);` in your browser and you'll see.
GuidoH
You're right (never seen that before) - I stand corrected.
Lucanos
+2  A: 

I would suggest a similar solution to GuidoH, but with a few minor changes.

PHP Code for the Comment Thread:

<form method="post" action="misc/removeWallComment.php">
  <input type="hidden" name="value" value="y" />
  <input type="hidden" name="BuID" value="<?php echo $v['id']; ?>" />
  <input type="hidden" name="uID" value="<?php echo $showU['id']; ?>" />
  <div id="commentList">
  <?php
  foreach( $comments as $c ){
    echo '<div id="comment'.$c['id'].'">';
      echo $c['commentBody'];
      echo '<input class="delButton" type="submit" name="'.$c['id'].'" value="Delete Comment" />';
    echo '</div>';
  }
  ?>
  </div>
</form>

This will render as:

<form method="post" action="misc/removeWallComment.php">
  <input type="hidden" name="value" value="y" />
  <input type="hidden" name="BuID" value="ThisIsThe_BuID" />
  <input type="hidden" name="uID" value="ThisIsThe_uID" />
  <div id="commentList">
    <div id="comment001">
      This is Comment Number One
      <input class="delButton" type="submit" name="001" value="Delete Comment" />
    </div>
    <div id="comment002">
      And, This is Comment Number Two
      <input class="delButton" type="submit" name="002" value="Delete Comment" />
    </div>
  </div>
</form>

In the Javascript for the page holding the Comment thread:

<script>
$(document).ready(function(){

 /* Add a Handler for the Delete Button */
  $('div#commentList input.delButton').click(function(e){
   /* Stop the Link working */
    e.preventDefault();
   /* Alias the main jQuery Objects */
    $this = $(this);
    $comment = $this.closest('div');
    $form = $comment.closest('form');
   /* Grab the Comment Number from the Button's NAME attribute */
    commentID = $this.attr('name');

   /* Perform the AJAX Action */
    $.ajax({
      url : $form.attr('action') ,
      type : 'POST' ,
      data : {
               'value'         : $form.find( 'input[name="value"]' ).val() ,
               'commentwallid' : commentID ,
               'BuID'          : $form.find( 'input[name="BuID"]' ).val() ,
               'uID'           : $form.find( 'input[name="uID"]' ).val() ,
               'mode'          : 'ajax'
             } ,
      dataType : 'text' ,
      complete: function( XHR , status ){
        if( $.trim(status).toLowerCase()=='success'
            && $.trim(XHR.responseText).toLowerCase()=='comment deleted' ){
         /* Success - Hide, then Remove the Comment */
          $comment.hide().remove();
        }else{
         /* Something Went Wrong */
          alert('Deleting Comment #'+commentID+' Failed');
        }
      }
    });

  });

});
</script>

In the misc/removeWallComment.php file:

if( $_POST['mode']=='ajax' ){

 /* Perform the Action. Return 'Comment Deleted' is Successful */

}else{

 /* This is to Extract the Comment ID from the "Delete Comment" button */
  $_POST_REV = array_flip( $_POST );
  $_POST['commentwallid'] = $_POST_REV['Delete Comment'];

 /* Perform the Action.
    Return the Full Page, or Redirect, you want Non-Javascript Users to See. */

}

NOTE:

This advice is based on the assumption he BuID and uID variables are the same for any delete action performed by the user from the same page.

Edited:

Updated to provide Graceful Degradation in the event that the user does not allow Javascript to run, and to extract a number of variables from the HTML FORM, (rather than have to code them in twice).

Lucanos
I totally agree with your solution, it's a bit more advanced version of my solution. But I would show the delete button by default, so you could make it work without Javascript enabled. :)
GuidoH
Agreed, except your button would not work without Javascript enabled, as it is using the javascript onclick event to do anytthing - this way, no Javascript, no delete button at all. (Of course, if they wanted to use include graceful degradation, you would simply wrap the UL in a form, and have buttons for each comment, replaced by the jQuery AJAXifying.
Lucanos
Hello. This, $comment = $this.closest('li') line, what should i change it to if i want my "delete comment" here in this div:<div id='removeComment'> I WANT "DELETE COMMENT" HERE</div>
Karem
@Lucanos, And with return a string, is it just a echo "Comment Deleted" i should made do after insert to DB
Karem
The line `$delButton = $( '<a class="delButton" href="#">delete comment</a>' );` contains the code for the Delete Button. You simply change the text between **href="#">** and **</a>** to whatever you like.Within the PHP Script which interfaces with the Database, you simply have it echo 'Comment Deleted' on a successful transaction, and something else if it fails.
Lucanos
It should also be noted that using `<div id='removeComment'> I WANT "DELETE COMMENT" HERE</div>` as the code for the delete button for each comment will not work, as the **id** attribute must be unique to a page (if you have 5 comments, you cannot have 5 DIVs with the same ID).
Lucanos
Karem
Oh, OK. What you need to insert within the `$this.closest('#removeComment')` segment is a jQuery identifier for the element which will have an ID containing the Comment ID. In my Answer, I made it an Unordered List (UL) and the List Item (LI) was the element which contained the Comment ID within it's ID attribute. If you wanted to use DIVs, then you would either use `$this.closest('div')` if the DIV you wanted was the first one encountered as you work your way up the DOM, or maybe `$this.closest('div[id]')` if it was the first DIV with an ID attribute.
Lucanos
You are also still using `'<?php echo $displayWall['id']; ?>',` which was the root of your problem - please review my Answer and make the appropriate changes as otherwise the problem will continue to occur.
Lucanos
@Lucanos OK i changed it to this.closest('div') , now yes I was still using <?php echo displayWall['id']; ?> because i didnt understand the $commentID but now i do after looking again and my PHP and Javascript looks currently like this:http://phpbin.net/x/1909993694 So now you can see what everythings look like right now. What have I done wrong, I cant find where it goes wrong?
Karem
@Lucanos And my firebug says "1 error" missing ) after argument list[Break on this error] success( response , status , XHR){\n
Karem
@Lucanos Hope im not a too much of a problem asking all these questions because of the shortage of knowlegde.
Karem
@Karim: See the Above, amended, code and examples.
Lucanos
@Lucanos Ok, i get it the javascript, but right now im stuck in with the PHP code for the comment thread. Where's the while() loop, that displays comment after comment? Should the form be inside or outside the while loop?
Karem
@Karim: If you want to use a `while()` loop, simply substitute the `foreach( $comments as $c ){` loop in the code for it. So long as the rendered HTML is roughly the same as what I have detailed above.
Lucanos
@Lucanos almost got it to work, i just get id# comment failed. I entered if( $_POST['mode']=='ajax' ){ echo "Comment Deleted"; but it still doesnt go through and success
Karem
@Karim: 1) Are you using Firebug? If so, add `console.log( 'XHR Object %o' , XHR );` just after the `complete: function( XHR , status ){` line, and see what happens. 2) Change `alert('Deleting Comment #'+commentID+' Failed');` to `alert("Deleting Comment #'+commentID+' Failed\nStatus '"+status+"'\nResponse '"+XHR.responseText+"'");` - See what the Status and Response are. If the Status is not "success" and the Response is not "Comment Deleted" that is the crux of your problem.
Lucanos
response is Comment Deleted and status is Success.
Karem
@Karem: OK, made another couple of amendments to the solution (after the `complete: function(...` bit) to make the response-handler a little more sturdy. The prior solution would have failed if there were spaces before or after the "Comment Deleted" string (which, without being able to see/test myself, I would presume may have been the cause).
Lucanos
Thank you for your help! It works excellent now
Karem
@Karem: Happy to have been of assistance. Is that bounty for me? If so, can you award it, otherwise, if you don't do so within 7 days, half of it disappears. http://stackoverflow.com/faq#bounty
Lucanos
there you go...
Karem
Thanks Karem - Appreciate it.
Lucanos