CodingForums.com

CodingForums.com (http://www.codingforums.com/index.php)
-   Ajax and Design (http://www.codingforums.com/forumdisplay.php?f=55)
-   -   Ajax Response Text Looping (Conditional) (http://www.codingforums.com/showthread.php?t=274784)

d'Anconia 09-30-2012 08:44 PM

Ajax Response Text Looping (Conditional)
 
Okay so I am trying to add a functionality to my website that more or less mimics the way that IMDb has a star-rating for movies. I'm using Ajax to submit a rating to the database when a star is clicked and currently the updating of the database is working BUT I am having a hard problem getting the stars to update to show the new user rating without reloading the page.

Essentially I have the response text to the Ajax call just give me the number rating (1-10) that was submitted once it was done so. I need to find out how to acquire that response text correctly and create an event that automatically updates the stars once that response text is received.

Here is my relevant javascript code:
Code:

/*
star_ratings.js
 */

window.onload = function() {
    'use strict';
    var entityId = <?php echo $entity_id; ?>;
    var username = <?php echo '"' . $current_username .'"'; ?>;
   
    U.addEvent(U.$('rating_star_1', 'click', function() {submitRating(1, "entity", "username")}));
   
   
  <?php
  //if there has already been a rating, create blue stars
  if (mysqli_num_rows($already_reviewed_query_result) == 1) {
        $review_score = $current_user_review_rows["review_score"];
        for ($l = 1; $l <= $review_score; $l++) {echo "document.getElementById('rating_star_" . $l . "').src ='../images/blue_star_17px.png'; "; }
    } //end of user review conditional / clause
   
   
    if ($current_username) { //if logged in
        for ($star_submit = 1; $star_submit <= 10; $star_submit++ ) {
            //get each rating_star_x and create event for starSubmitFxn on click with given parameters
            echo "U.addEvent(U.$('rating_star_" . $star_submit . "'), 'click', function(){ starSubmitFxn('" . $star_submit . "', '" . $current_username . "'); } );";
        }
    }
   
  ?>
         
   
  U.addEvent(U.$('rating_star_1'), 'mouseover', function(){ newStarRating(1, "yellow_full"); } );
  U.addEvent(U.$('rating_star_2'), 'mouseover', function(){ newStarRating(2, "yellow_full"); } );
  U.addEvent(U.$('rating_star_3'), 'mouseover', function(){ newStarRating(3, "yellow_full"); } );
  U.addEvent(U.$('rating_star_4'), 'mouseover', function(){ newStarRating(4, "yellow_full"); } );
  U.addEvent(U.$('rating_star_5'), 'mouseover', function(){ newStarRating(5, "yellow_full"); } );
  U.addEvent(U.$('rating_star_6'), 'mouseover', function(){ newStarRating(6, "yellow_full"); } );
  U.addEvent(U.$('rating_star_7'), 'mouseover', function(){ newStarRating(7, "yellow_full"); } );
  U.addEvent(U.$('rating_star_8'), 'mouseover', function(){ newStarRating(8, "yellow_full"); } );
  U.addEvent(U.$('rating_star_9'), 'mouseover', function(){ newStarRating(9, "yellow_full"); } );
  U.addEvent(U.$('rating_star_10'), 'mouseover', function(){ newStarRating(10, "yellow_full"); } );
  <?php
       
  if (mysqli_num_rows($already_reviewed_query_result) == 1) {
            echo "U.addEvent(U.$('star_rating_div'), 'mouseout', function(){ newStarRating(" . $current_user_review_rows['review_score'] .", 'blue'); } );";
        }
        else {
            echo "U.addEvent(U.$('star_rating_div'), 'mouseout', function(){ newStarRating(0, 'yellow_full'); } );";
            echo "/* \$already_reviewed_query is:*" . $already_reviewed_query . "*/";
        }
        mysqli_close($dbc);
    ?>
 
 }



function newStarRating(starNumber, color) {
        'use strict';
        var i = null;
        for (i = 1; i <= 10; i++) {
          document.getElementById('rating_star_' + i).src='../images/white_star_17px.png';
         
        } //end of star color reset
       
        var j = null;
        for (j = 1; j <= starNumber; j++) {
           
            document.getElementById('rating_star_' + j).src='../images/' + color + '_star_17px.png';
           
        }
       
    }

function starSubmitFxn(starNumber) {
    'use strict';
   
    //Get a reference (get element by ID) to the entered username value:
    var ajax = getXMLHttpRequestObject();
    if (ajax) {
    var currentUsername = '<?php echo $current_username; ?>';
    var currentEntityId = '<?php echo $entity_id; ?>';

                ajax.onreadystatechange = function() {
                    if (ajax.readyState === 4){
                        //Check the status code:
                        if ( (ajax.status >= 200 && ajax.status < 300) || (ajax.status === 304) ) {
                           
                            for ( var r = 1; r <= 10; r++){
                                if (ajax.responseText === 'r') {
                                    newStarRating(r, "blue");//end of newStarRating call
                                    } //end of response text check
                                } //end of loop
                       
                            } //end of Ajax connectivity check
                            else { //if Ajax status text is a failure
                                document.getElementById('ajax_status').innerHTML = 'Error:' + ajax.statusText;
                                }
                        } //end of Ajax ready state
                    }; //end of function for execution on ready state change
                   
                var data = 'currentUsername=' + encodeURIComponent(currentUsername) + '&currentEntityId=' + encodeURIComponent(currentEntityId) + '&starNumber=' + encodeURIComponent(starNumber);
                ajax.open('POST', '../resources/star_submit.php?' + data, true);
                ajax.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');

                ajax.send(data);
        }
        else {
            document.getElementById('ajax_status').innerHTML = "Error: Ajax object doesn't exist";
        }
        }

Here is the PHP code for the Ajax response:

PHP Code:

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

require_once ($_SERVER["DOCUMENT_ROOT"] . '/includes/config.inc.php');
if (
$_POST['currentUsername'] && $_POST['currentEntityId'] && $_POST['starNumber']) {
    require_once (
MYSQL);
    
$trimmed_username mysqli_escape_string($dbctrim($_POST['currentUsername']));
    
$trimmed_entity_id mysqli_escape_string($dbctrim($_POST['currentEntityId']));
    
$trimmed_star_number mysqli_escape_string($dbctrim($_POST['starNumber']));
    
$check_rating_query "SELECT entity_id, created_by_username, review_score FROM reviews WHERE 
                    created_by_username = '$trimmed_username' AND entity_id = '$trimmed_entity_id'
                            LIMIT 1"
;
    
$results mysqli_query($dbc$check_rating_query);
    
    if (
mysqli_num_rows($results) == 1) {

        
$update_rating_query "UPDATE reviews SET review_score = '$trimmed_star_number', date_of_submission = NOW() WHERE 
                                created_by_username = '$trimmed_username' AND entity_id = '$trimmed_entity_id'
                                LIMIT 1"
;
        
$update_results mysqli_query($dbc$update_rating_query);
        if (
mysqli_affected_rows ($dbc) == 1) {
            echo 
$trimmed_star_number;
            
            }
        }
        
    } 

And the HTML (produced by the server) in that area for reference:
PHP Code:

echo '<div id="star_rating_div" align="right" style="margin-top:5px; margin-right:166px; width:168px; margin-left:auto;">';
                                                                           
                                            
$star_constant 1;
                                            while (
$star_constant 11) {
                                                echo 
'<img src="/images/white_star_17px.png" alt="' $star_constant '" title="' $star_constant '"
                                                        id="rating_star_' 
$star_constant '" />';
                                                
$star_constant++;
                                                
                                            }
                                           echo 
'</div> <!-- end of star rating div-->'


Any help would be appreciated. I just need to know how to loop through the response text to check the rating number (1-10)

I am having problems finding the right way to debug this problem:
http://www.danconia.us/images/star_rating_issue.png

AndrewGSW 09-30-2012 08:59 PM

Just had a quick glance but:

Code:

if (ajax.responseText === 'r') {
you're currently looking for the letter 'r' whereas I assume the response is a number (1-10). Or, at least, a string which can be converted to a number.

You might do something like the following, rather than looping through 1-10:

Code:

var respond = ajax.responseText;
if (!isNaN(respond)) {
    respond = respond * 1;    // convert to a number, if required
} else {
    // invalid response received
}


d'Anconia 10-01-2012 07:42 PM

Will try and check back. Thank you.

d'Anconia 10-05-2012 04:02 AM

So now I'm getting an error telling me the following:
Code:

<div class="error"><p>An error occurred in script '/home/kylhur/danconia.us/resources/star_submit.php' on line 9: Undefined index: currentUsername
<br />Date/Time: 10-4-2012 19:36:02
<br /><pre>Array
(
    [GLOBALS] => Array
 *RECURSION*
    [HTTP_RAW_POST_DATA] => currentUsername=kylan_hurt_gmail&currentEntityId=117&starNumber=3
    [_POST] => Array
        (
        )

Apparently my post method is not working. Should the value for currentUsername be in quotes once it's in the data variable (that will be added to the URL and sent)?

When I check it in Chrome though, it says that I have an "unexpected token <". This is always a hard error to correct, especially when NetBeans doesn't find any parsing error.

d'Anconia 10-07-2012 06:23 AM

Once I fixed the unexpected token problem... which by the way I am still not sure how I fixed... I was able to keep debugging to find out how far my JSON (I switched it to JSON from originally being just text because I was running out of ideas).

First problem I think it was being returned as text and failing the !NaN test. Secondly, and perhaps more importantly, I forgot to remove the event that was added earlier that resets the blue stars to whatever rating the entity had from the user when the page was loaded. So now I remove that event and replace it with the next rating (as responded from the server upon success).

Final relevant code looked like this:

Code:

/*
star_ratings.js
 */

window.onload = function () {
    'use strict';
   
    var entityId = <?php echo $entity_id; ?>;
    var username = <?php echo '"' . $current_username .'"'; ?>;
    var ajax = getXMLHttpRequestObject();
   
   
  <?php
  //if there has already been a rating, create blue stars
  if (mysqli_num_rows($already_reviewed_query_result) == 1) {
        $review_score = $current_user_review_rows["review_score"];
        for ($l = 1; $l <= $review_score; $l++) {echo "document.getElementById('rating_star_" . $l . "').src ='../images/blue_star_17px.png'; \n"; }
    } //end of user review conditional / clause
   
   
    if ($current_username) { //if logged in
        for ($star_submit = 1; $star_submit <= 10; $star_submit++ ) {
            //get each rating_star_x and create event for starSubmitFxn on click with given parameters
            echo "U.addEvent(U.$('rating_star_" . $star_submit . "'), 'click', function(){ starSubmitFxn(" . $star_submit . ", '" . $current_username . "'); } ); \n";
        }
    }
   
  ?>
         
   
  U.addEvent(U.$('rating_star_1'), 'mouseover', function(){ newStarRating(1, "yellow_full"); } );
  U.addEvent(U.$('rating_star_2'), 'mouseover', function(){ newStarRating(2, "yellow_full"); } );
  U.addEvent(U.$('rating_star_3'), 'mouseover', function(){ newStarRating(3, "yellow_full"); } );
  U.addEvent(U.$('rating_star_4'), 'mouseover', function(){ newStarRating(4, "yellow_full"); } );
  U.addEvent(U.$('rating_star_5'), 'mouseover', function(){ newStarRating(5, "yellow_full"); } );
  U.addEvent(U.$('rating_star_6'), 'mouseover', function(){ newStarRating(6, "yellow_full"); } );
  U.addEvent(U.$('rating_star_7'), 'mouseover', function(){ newStarRating(7, "yellow_full"); } );
  U.addEvent(U.$('rating_star_8'), 'mouseover', function(){ newStarRating(8, "yellow_full"); } );
  U.addEvent(U.$('rating_star_9'), 'mouseover', function(){ newStarRating(9, "yellow_full"); } );
  U.addEvent(U.$('rating_star_10'), 'mouseover', function(){ newStarRating(10, "yellow_full"); } );
  <?php
       
  if (mysqli_num_rows($already_reviewed_query_result) == 1) {
            echo "U.addEvent(U.$('star_rating_div'), 'mouseout', function(){ newStarRating(" . $current_user_review_rows['review_score'] .", 'blue'); } );";
        }
        else {
            echo "U.addEvent(U.$('star_rating_div'), 'mouseout', function(){ newStarRating(0, 'yellow_full'); } );";
            echo "/* \$already_reviewed_query is:*" . $already_reviewed_query . "*/";
        }
       
    ?>
 
 }

function newStarRating(starNumber, color) {
        'use strict';
        var i = null;
        for (i = 1; i <= 10; i++) {
          document.getElementById('rating_star_' + i).src='../images/white_star_17px.png';
         
        } //end of star color reset
       
        var j = null;
        for (j = 1; j <= starNumber; j++) {
           
            document.getElementById('rating_star_' + j).src='../images/' + color + '_star_17px.png';
           
        }
       
    }

function starSubmitFxn(starNumber) {
    'use strict';
    var ajax = getXMLHttpRequestObject();
    if (ajax) {
                var currentUsername = '<?php echo $current_username; ?>';
                var currentEntityId = <?php echo $entity_id; ?>;
                // Create the Ajax object:
               
                ajax.onreadystatechange = function() {
                    if (ajax.readyState === 4){
                        //Check the status code:
                        if ( (ajax.status >= 200 && ajax.status < 300) || (ajax.status === 304) ) {
                           
                            //document.getElementById('ajax_status').innerHTML = ajax.responseText;
                           
                          var starResponse = JSON.parse(ajax.responseText);
                                                       
                            var starResponseNumber = parseInt(starResponse["1"].value);
                           
                            U.removeEvent(U.$('star_rating_div'), 'mouseout', function(){ newStarRating("<? echo $current_user_review_rows['review_score'] ?> ", 'blue'); } );
                            U.addEvent(U.$('star_rating_div'), 'mouseout', function(){ newStarRating(starResponseNumber, 'blue'); } );
                                if (!isNaN(starResponseNumber)) {
                                                                       
                                    //newStarRating(ratingNumber, "blue");//end of newStarRating call
                                       
                                        var i = null;
                                        for (i = 1; i <= 10; i++) {
                                        document.getElementById('rating_star_' + i).src='../images/white_star_17px.png';

                                        } //end of star color reset

                                        var j = null;
                                        for (j = 1; j <= starResponseNumber; j++) {

                                            document.getElementById('rating_star_' + j).src='../images/blue_star_17px.png';


                                        }
                                   
                                    } //end of response text check
                               
                       
                            } //end of Ajax connectivity check
                            else { //if Ajax status text is a failure
                               
                                }
                        } //end of Ajax ready state
                    }; //end of function for execution on ready state change
                   
                var data = 'currentUsername=' + encodeURIComponent(currentUsername) + '&currentEntityId=' + encodeURIComponent(currentEntityId) + '&starNumber=' + encodeURIComponent(starNumber);
                ajax.open('POST', '../resources/star_submit.php?' + data, true);
                ajax.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');

                ajax.send(data);
        } //end if ajax object exists
        else {
           
        } //end if it doesn't exist
    } //end of starSubmitFxn

And PHP:

PHP Code:


/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

require_once ($_SERVER["DOCUMENT_ROOT"] . '/includes/config.inc.php');
if (
$_POST['currentUsername'] && $_POST['currentEntityId'] && $_POST['starNumber']) {
    require_once (
MYSQL);
    
$trimmed_username mysqli_escape_string($dbctrim($_POST['currentUsername']));
    
$trimmed_entity_id mysqli_escape_string($dbctrim($_POST['currentEntityId']));
    
$trimmed_star_number mysqli_escape_string($dbctrim($_POST['starNumber']));
    
$check_rating_query "SELECT entity_id, created_by_username, review_score FROM reviews WHERE 
                    created_by_username = '$trimmed_username' AND entity_id = $trimmed_entity_id
                            LIMIT 1"
;
    
$results mysqli_query($dbc$check_rating_query);
    
    if (
mysqli_num_rows($results) == 1) {
        
        
$update_rating_query "UPDATE reviews SET review_score = $trimmed_star_number, date_of_submission = NOW() WHERE 
                                created_by_username = '$trimmed_username' AND entity_id = $trimmed_entity_id
                                LIMIT 1"
;
        
$update_results mysqli_query($dbc$update_rating_query);
        if (
mysqli_affected_rows ($dbc) == 1) {
            echo 
'var starResponse = {
                    "1": {  "value": "' 
$trimmed_star_number '" }
                    }'
;
            
            }
        }
        
    
    } 

And thank you AndrewGSW, I ended up using some of your code in my solution. I appreciate it!

rnd me 10-07-2012 06:52 PM

you should really look into using json_encode(phpArr) to format your data instead of building vars manually. it's faster, and the native feature are tested and patched, making them way more reliable when silly data works its way in, which is inevitable.

d'Anconia 10-12-2012 03:33 AM

Okay so for the record I found out why I get an "unexpected token <", it's from the PHP response when my PHP script has en error. Notice how the response from the server starts with an open braces (or whatever that character is called):

Code:

<div class="error"><p>An error occurred in script '/home/kylhur/danconia.us/resources/find_comments.php' on line 6: mysqli_escape_string() expects exactly 2 parameters, 1 given
<br />Date/Time: 10-11-2012 19:30:58
<br /><pre>Array



All times are GMT +1. The time now is 11:19 AM.

Powered by vBulletin®
Copyright ©2000 - 2013, Jelsoft Enterprises Ltd.